branch: externals/phpinspect commit e35caa7e15d3e79e53353a56dd701075d3e367b4 Author: Hugo Thunnissen <de...@hugot.nl> Commit: Hugo Thunnissen <de...@hugot.nl>
Fix a variety of bugs - phpinspect--index-tokens no longer errors upon unexpected return annotation values - phpinspect-fixt-imports now also fixes imports outside of classes - Functions are no longer included in statements when deriving types --- phpinspect-buffer.el | 10 +++++++++ phpinspect-eldoc.el | 4 +--- phpinspect-imports.el | 49 +++++++++++++++++++++++++++----------------- phpinspect-index.el | 26 ++++++++++++++++------- phpinspect-resolve.el | 22 +++++++++++++------- phpinspect-resolvecontext.el | 4 ++-- 6 files changed, 77 insertions(+), 38 deletions(-) diff --git a/phpinspect-buffer.el b/phpinspect-buffer.el index 96596ea55a..7a46fd966b 100644 --- a/phpinspect-buffer.el +++ b/phpinspect-buffer.el @@ -76,6 +76,7 @@ linked with." (unless (or no-index (not (phpinspect-buffer-project buffer))) + (phpinspect--log "Adding buffer index to project") (phpinspect-project-add-index (phpinspect-buffer-project buffer) (phpinspect--index-tokens tree nil (phpinspect-buffer-location-resolver buffer)) @@ -141,4 +142,13 @@ use." (insert (pp-to-string (phpinspect-buffer-parse buffer 'no-interrupt))) (read-only-mode)))) +(defun phpinspect-display-buffer-index () + (interactive) + (when phpinspect-current-buffer + (let ((buffer phpinspect-current-buffer)) + (pop-to-buffer (generate-new-buffer "phpinspect-buffer-tree")) + (insert (pp-to-string (phpinspect--index-tokens (phpinspect-buffer-parse buffer 'no-interrupt)))) + (read-only-mode)))) + + (provide 'phpinspect-buffer) diff --git a/phpinspect-eldoc.el b/phpinspect-eldoc.el index 225746c285..d0ac7f4272 100644 --- a/phpinspect-eldoc.el +++ b/phpinspect-eldoc.el @@ -92,7 +92,6 @@ be implemented for return values of `phpinspect-eld-strategy-execute'") (setq result (phpinspect-make-function-doc :fn method)))))) result))))) - (cl-defstruct (phpinspect-eld-function-args (:constructor phpinspect-make-eld-function-args)) "Eldoc strategy for function arguments.") @@ -136,8 +135,7 @@ be implemented for return values of `phpinspect-eld-strategy-execute'") (while (and left-sibling - (not (or (phpinspect-return-p (phpinspect-meta-token left-sibling)) - (phpinspect-end-of-statement-p (phpinspect-meta-token left-sibling))))) + (not (phpinspect-statement-introduction-p (phpinspect-meta-token left-sibling)))) (push left-sibling statement) (setq left-sibling (phpinspect-meta-find-left-sibling left-sibling))) diff --git a/phpinspect-imports.el b/phpinspect-imports.el index db74413ff4..8aad8ee3f7 100644 --- a/phpinspect-imports.el +++ b/phpinspect-imports.el @@ -113,6 +113,28 @@ buffer position to insert the use statement at." (defalias 'phpinspect-fix-uses-interactive #'phpinspect-fix-imports "Alias for backwards compatibility") +(defun phpinspect-namespace-name (namespace) + (or (and (phpinspect-namespace-p namespace) + (phpinspect-word-p (cadr namespace)) + (cadadr namespace)) + "")) + +(defun phpinspect-add-use-statements-for-missing-types (types buffer imports project parent-token) + (let (namespace) + (dolist (type types) + (setq namespace (phpinspect-meta-find-parent-matching-token + parent-token #'phpinspect-namespace-p) + namespace-name (phpinspect-namespace-name namespace)) + ;; Add use statements for types that aren't imported or already referenced + ;; with a fully qualified name. + (unless (or (or (alist-get type imports)) + (gethash (phpinspect-intern-name + (concat namespace-name "\\" (symbol-name type))) + (phpinspect-autoloader-types + (phpinspect-project-autoload project)))) + (phpinspect-add-use-interactive type buffer project namespace) + (phpinspect-buffer-parse buffer 'no-interrupt))))) + (defun phpinspect-fix-imports () "Find types that are used in the current buffer and make sure that there are import (\"use\") statements for them." @@ -126,7 +148,12 @@ that there are import (\"use\") statements for them." (imports (alist-get 'imports index)) (project (phpinspect--cache-get-project-create (phpinspect--get-or-create-global-cache) - (phpinspect-current-project-root)))) + (phpinspect-current-project-root))) + (used-types (alist-get 'used-types index))) + + (phpinspect-add-use-statements-for-missing-types + used-types buffer imports project (phpinspect-buffer-root-meta buffer)) + (dolist (class classes) (let* ((class-imports (alist-get 'imports class)) (used-types (alist-get 'used-types class)) @@ -143,23 +170,7 @@ that there are import (\"use\") statements for them." (unless token-meta (error "Unable to find token for class %s" class-name)) - - - (dolist (type used-types) - (setq namespace (phpinspect-meta-find-parent-matching-token - token-meta #'phpinspect-namespace-p)) - ;; Add use statements for types that aren't imported. - (unless (or (or (alist-get type class-imports) - (alist-get type imports)) - (gethash (phpinspect-intern-name - (concat (phpinspect-namespace-part-of-typename - (phpinspect--type-name (alist-get 'class-name class))) - "\\" - (symbol-name type))) - (phpinspect-autoloader-types - (phpinspect-project-autoload project)))) - (phpinspect-add-use-interactive - type buffer project namespace) - (phpinspect-buffer-parse buffer 'no-interrupt)))))))) + (phpinspect-add-use-statements-for-missing-types + used-types buffer (append imports class-imports) project token-meta)))))) (provide 'phpinspect-imports) diff --git a/phpinspect-index.el b/phpinspect-index.el index d76b2d5899..7dc8df1161 100644 --- a/phpinspect-index.el +++ b/phpinspect-index.el @@ -81,11 +81,15 @@ function (think \"new\" statements, return types etc.)." (phpinspect--log "found return annotation %s in %s when type is %s" return-annotation-type comment-before type) - (when (string-suffix-p "[]" return-annotation-type) - (setq is-collection t) - (setq return-annotation-type (string-trim-right return-annotation-type "\\[\\]"))) + (unless (stringp return-annotation-type) + (phpinspect--log "Discarding invalid return annotation type %s" return-annotation-type) + (setq return-annotation-type nil)) (when return-annotation-type + (when (string-suffix-p "[]" return-annotation-type) + (setq is-collection t) + (setq return-annotation-type (string-trim-right return-annotation-type "\\[\\]"))) + (cond ((phpinspect--should-prefer-return-annotation type) (setq type (funcall type-resolver (phpinspect--make-type :name return-annotation-type)))) @@ -487,14 +491,22 @@ Return value is a list of the types that are \"newed\"." (alist-get 'classes namespace-index) (phpinspect--index-classes-in-tokens imports tokens type-resolver-factory location-resolver))) - (used-types ,@(append - (alist-get 'used-types namespace-index) - (phpinspect--find-used-types-in-tokens tokens))) + (used-types ,@(mapcar #'phpinspect-intern-name + (seq-uniq + (append + (alist-get 'used-types namespace-index) + (phpinspect--find-used-types-in-tokens tokens)) + #'string=))) (functions . ,(append (alist-get 'functions namespace-index) (phpinspect--index-functions-in-tokens tokens type-resolver-factory imports)))))) - (t (phpinspect--log "phpinspect--index-tokens failed: %s" err) nil)) + (t + (phpinspect--log "phpinspect--index-tokens failed: %s. Enable debug-on-error for backtrace." err) + (when debug-on-error + (require 'backtrace) + (backtrace)) + nil)) '(phpinspect--root-index))) (defun phpinspect-get-or-create-cached-project-class (project-root class-fqn) diff --git a/phpinspect-resolve.el b/phpinspect-resolve.el index b3efb2467e..76e2159249 100644 --- a/phpinspect-resolve.el +++ b/phpinspect-resolve.el @@ -36,6 +36,13 @@ :type phpinspect-token :documentation "The token that is assigned from")) +(define-inline phpinspect-statement-introduction-p (token) + (inline-letevals (token) + (inline-quote + (or (phpinspect-return-p ,token) + (phpinspect-end-of-statement-p ,token) + (phpinspect-function-p ,token))))) + (defsubst phpinspect-block-or-list-p (token) (or (phpinspect-block-p token) (phpinspect-list-p token))) @@ -227,12 +234,13 @@ $variable = $variable->method();" :name (cadr first-token)))) ;; No bare word, assume we're dealing with a variable. - (phpinspect-get-variable-type-in-block - resolvecontext - (cadr first-token) - php-block - type-resolver - function-arg-list)))) + (when (phpinspect-variable-p first-token) + (phpinspect-get-variable-type-in-block + resolvecontext + (cadr first-token) + php-block + type-resolver + function-arg-list))))) (phpinspect--log "Statement: %s" statement) (phpinspect--log "Starting attribute type: %s" previous-attribute-type) @@ -371,7 +379,7 @@ determine whether a token delimits a statement." (let ((sublists) (current-sublist)) (dolist (thing tokens) - (if (or (phpinspect-end-of-statement-p thing) + (if (or (phpinspect-statement-introduction-p thing) (when predicate (funcall predicate thing))) (when current-sublist (when (phpinspect-block-p thing) diff --git a/phpinspect-resolvecontext.el b/phpinspect-resolvecontext.el index 9c5ec4ede2..9128132d35 100644 --- a/phpinspect-resolvecontext.el +++ b/phpinspect-resolvecontext.el @@ -55,6 +55,7 @@ (push enclosing-token (phpinspect--resolvecontext-enclosing-tokens resolvecontext))) + (defsubst phpinspect-blocklike-p (token) (or (phpinspect-block-p token) (phpinspect-function-p token) @@ -76,8 +77,7 @@ (if (and (not previous-siblings) (phpinspect-blocklike-p token)) (progn (throw 'return (phpinspect-find-statement-before-point bmap child point))) - (when (or (phpinspect-return-p token) - (phpinspect-end-of-statement-p token)) + (when (phpinspect-statement-introduction-p token) (throw 'return previous-siblings)) (push child previous-siblings))))) previous-siblings))