branch: externals/phpinspect commit 42ccef5493b3f2bae491da17fa03bf9c61afdb31 Author: Hugo Thunnissen <de...@hugot.nl> Commit: Hugo Thunnissen <de...@hugot.nl>
Explicitly test application of trait configuration + fix bugs --- phpinspect-typedef.el | 51 +++++++++++++++++++++++++++++---------------------- test/test-typedef.el | 44 +++++++++++++++++++++++++++++++++++++++++--- 2 files changed, 70 insertions(+), 25 deletions(-) diff --git a/phpinspect-typedef.el b/phpinspect-typedef.el index a3f827c539..db57c3e815 100644 --- a/phpinspect-typedef.el +++ b/phpinspect-typedef.el @@ -107,22 +107,25 @@ structure returned by `phpinspect--index-trait-use'." (push (cons type overrides) (phpi-ma-overrides ma))))) (defun phpi-ma-add (ma mcol method &optional overwrite) - (if-let ((overrides (phpi-ma-get-overrides ma (phpi-method-origin-type method))) - (aliases (phpi-ma-get-aliases ma (phpi-method-origin-type method)))) - (progn - (if-let ((override (alist-get (phpi-method-name method) overrides))) - ;; Override basically just means insert and overwrite without checking - (phpi-mcol-add mcol method 'overwrite) - ;; Can't alias if overriding, can't override if aliasing - (when-let ((alias (alist-get (phpi-method-name method) aliases)) - (copy (phpi-copy-method method))) - ;; Rename method to alias, record original name in aliased-from slot - (setf (phpi-method-aliased-from method) (phpi-method-name method) - (phpi-method-name method) alias)))) - - ;; Not dealing with aliases or overrides, just add the methods (unless they - ;; already exist) - (phpi-mcol-add mcol method overwrite))) + + (let ((overrides (phpi-ma-get-overrides ma (phpi-method-origin-type method))) + (aliases (phpi-ma-get-aliases ma (phpi-method-origin-type method))) + alias override) + + ;; Can't alias if overriding, can't override if aliasing + (cond ((and overrides (setq override (alist-get (phpi-method-name method) overrides))) + ;; Override basically just means insert and overwrite without checking + (phpi-mcol-add mcol method 'overwrite)) + ((and aliases (setq alias (alist-get (phpi-method-name method) aliases))) + (let ((copy (phpi-copy-method method))) + ;; Rename method to alias, record original name in aliased-from slot + (setf (phpi-method-aliased-from copy) (phpi-method-name method) + (phpi-method-name copy) alias) + (phpi-mcol-add mcol copy overwrite))) + (t + ;; Not dealing with aliases or overrides, just add the methods, + ;; respecting `overwrite'. + (phpi-mcol-add mcol method overwrite))))) (defun phpi-typedef-get-methods (def) (phpi-mcol-list-active (phpi-typedef-methods def))) @@ -185,17 +188,21 @@ structure returned by `phpinspect--index-trait-use'." (phpi--typedef-edit def (let ((existing-config (phpi-typedef-trait-config def)) types) - (if existing-config + ;; A configuration that is exactly the same doesn't need to be applied twice + (unless (equal config existing-config) + (when existing-config ;; This can probably be made more sophisticated by only applying the ;; difference, but just deleting all incorporated methods will do for ;; an initial implementation. (dolist (use existing-config) - (phpi-mcol-delete-for-type (phpi-typedef-methods def) (car use))) + (when-let ((fd (phpi--typedef-get-foreign-type def (car use)))) + (phpi-typedef-unsubscribe-from-foreign-typedef def fd)))) ;; Apply new config - (progn - (phpi-ma-set-config (phpi-typedef-method-adder def) config) - (dolist (cons config) - (push (car cons) types)))) + (phpi-ma-set-config (phpi-typedef-method-adder def) config)) + (dolist (cons config) + (push (car cons) types)) + + (setf (phpi-typedef-trait-config def) config) ;; return all types that were in config types))) diff --git a/test/test-typedef.el b/test/test-typedef.el index 63344ed89c..86687a78df 100644 --- a/test/test-typedef.el +++ b/test/test-typedef.el @@ -158,9 +158,6 @@ (should-not method)))) - - - (ert-deftest phpinspect-typedef-variables () (let ((def (phpinspect-make-typedef (phpinspect--make-type :name "\\test")))) @@ -209,3 +206,44 @@ (should static-method) (should (eq (phpinspect-intern-name "test") (phpi-method-name static-method)))))) + +(ert-deftest phpinspect-typedef-set-index-trait-config () + (let* ((code "class A { use \\AAA; function B(): C {} }") + (index (phpinspect--index-tokens (phpinspect-parse-string code))) + (class (cdar (alist-get 'classes index))) + (def1 (phpinspect-make-typedef (alist-get 'class-name class))) + (def2 (phpinspect-make-typedef (phpinspect--make-type :name "\\AAA"))) + (retriever (lambda (type) + (cond ((phpinspect--type= type (phpi-typedef-name def1)) + def1) + ((phpinspect--type= type (phpi-typedef-name def2)) + def2))))) + + (setf (phpi-typedef-retriever def1) retriever + (phpi-typedef-retriever def2) retriever) + + (phpi-typedef-set-index def1 class) + (phpi-typedef-set-index + def2 (cdar (alist-get 'classes (phpinspect--index-tokens + (phpinspect-parse-string + "class AAA { function b(): string {} }"))))) + + + (should (= 2 (length (phpi-typedef-get-methods def1)))) + + (let ((method (phpi-typedef-get-method def1 "b"))) + (should (string= "b" (phpi-fn-name method))) + (should (phpinspect--type= (phpinspect--make-type :name "\\string") + (phpi-fn-return-type method)))) + + (phpi-typedef-set-index + def1 (cdar (alist-get 'classes (phpinspect--index-tokens + (phpinspect-parse-string + "class A { use \\AAA { \\AAA::b as boo } function B(): C {} }"))))) + + (should-not (phpi-typedef-get-method def1 "b")) + + (let ((method (phpi-typedef-get-method def1 "boo"))) + (should (string= "boo" (phpi-fn-name method))) + (should (phpinspect--type= (phpinspect--make-type :name "\\string") + (phpi-fn-return-type method))))))