From unknown Thu Sep 11 10:42:23 2025 X-Loop: help-debbugs@gnu.org Subject: bug#79339: 31.0.50; [PATCH] php-ts-mode: support PHP 8.5 Resent-From: Vincenzo Pupillo Original-Sender: "Debbugs-submit" Resent-CC: bug-gnu-emacs@gnu.org Resent-Date: Fri, 29 Aug 2025 19:37:01 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: report 79339 X-GNU-PR-Package: emacs X-GNU-PR-Keywords: patch To: 79339@debbugs.gnu.org X-Debbugs-Original-To: bug-gnu-emacs@gnu.org Received: via spool by submit@debbugs.gnu.org id=B.175649620612693 (code B ref -1); Fri, 29 Aug 2025 19:37:01 +0000 Received: (at submit) by debbugs.gnu.org; 29 Aug 2025 19:36:46 +0000 Received: from localhost ([127.0.0.1]:43371 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1us4tw-0003IV-Gx for submit@debbugs.gnu.org; Fri, 29 Aug 2025 15:36:46 -0400 Received: from lists.gnu.org ([2001:470:142::17]:33682) by debbugs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.84_2) (envelope-from ) id 1us4ts-0003GB-Eo for submit@debbugs.gnu.org; Fri, 29 Aug 2025 15:36:42 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1us4tZ-0005pK-Kk for bug-gnu-emacs@gnu.org; Fri, 29 Aug 2025 15:36:24 -0400 Received: from mail-wm1-x331.google.com ([2a00:1450:4864:20::331]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1us4tU-0008Rv-Pc for bug-gnu-emacs@gnu.org; Fri, 29 Aug 2025 15:36:20 -0400 Received: by mail-wm1-x331.google.com with SMTP id 5b1f17b1804b1-45a1b0bde14so16049135e9.2 for ; Fri, 29 Aug 2025 12:36:11 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1756496170; x=1757100970; darn=gnu.org; h=content-transfer-encoding:mime-version:message-id:date:subject:to :from:from:to:cc:subject:date:message-id:reply-to; bh=153KCze0vkc89FFjzdMrWz07dJn46rHiF5oGC6ghE+c=; b=F5x6ey7RVdE25LEs2xSj2hxSC3mkfIzDgJ9dru1GQ+Pysj5Fx5uxmaMeTiy7S7zLjk DZBH1F0Iss38AdwzqT5vJV6TLAjKc/wY6dVTGNyCj4+ISFA02tozanxyK0YFRk1u69n7 hSihDo+F9Y63ATRS+No66fmFHnaW8W1nHQwVAeBkhtHMUqoAlL02X+Co6JXmj9AdxXVy iLsq83NKi/ycqMZDGoEoVMi+zkh241SfHWvvoBQME3AK2Stfmw7oze37kyMeYha8wwnX OwmUGkB/x5cU1zH7a9BeRUC7g7MKgui8qN+VH+UTqTUGRW87RNOlBMZduXhnW8Cv+vkR ymig== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1756496170; x=1757100970; h=content-transfer-encoding:mime-version:message-id:date:subject:to :from:x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=153KCze0vkc89FFjzdMrWz07dJn46rHiF5oGC6ghE+c=; b=gmP1FqgtSMMZI0WPmV4HrcKpr+hmTof6+Vta+7lT/dBfY4YiJfE3ioLWePRGj5ef5N BNhN0ihrPGZaZDItUrqAl33e7Xz5i6fGptdi1NGXEVXm2YiZC3vdlbH/xYsfAQKoNLfe JwBb5Bb5RkotLit1qIAO1rQeoeAXf6rF3qQxMAnQnUZtzY0OGsnlxarY3180bqUVoIj4 7rMYUyzSEIyyQitloQwHqwUQQDWGvbXw8uZimVWyj946RPt5aTfnkh8spmrS3Mltd29D nEQ9bYVhJsyvEKtSVkP7vF6VT/1VkTHd1zUOnkdOSmKxH1PJxntBxerb3vFN2WqroiLP NOdg== X-Gm-Message-State: AOJu0YxQj2fXT4S0Jz/6bPFoelJMlhU7u+rDndhomJSoLyVJ9k4tReV/ yuhxcicoeQUaMEPKiZZjaUEMfqQ5gHJlzBy5dhUuAjMQ40bkHc0aYspn84LCDw== X-Gm-Gg: ASbGncsUi27vLYmsV3Cc4WirGZmo/H7zRp+Y1t3NyViT2NTO+iuOOX647xfHT7nfkOu v5J0SWZcYHVwHFprtlsL8hpcuXk6gl4G80E004BQuOoa6+sDGmPQZZAXRJEQMBC7ZaQ3fZLozvQ ElsgJ7fMTsIPL1q/Dh35YkeCPgxQslJlMYNi0jndxHEhxjB2gagCGa+IyfiZrbNhgulm9W/mTYY T+z4M1SICTevoWl4Dj78zKNVE1rCxc/rcMXOXMZ/bv+Dx1OTfaL7fTXqVZoWXMb6CtBR35+662i 3UCjS9zAx+rqO/r/XZ2xNM+5h0id9SJE0befT8Jy5HYb6L0mn04PCuffexOVdrovSzraCd65PsZ 4b7oiJlxd3Lt01lLjYKjueOT5COc7YV/+8Pj4ds44JX2c3z9mcalgnvObAmcWvHEsBKPhjZMNMW 8brg80 X-Google-Smtp-Source: AGHT+IE19uSCtND5g94XODtdHThjd422dgAeub9FYuMdMPgabDnkWW/FUrkO6rtA3buC73z2gzwUXw== X-Received: by 2002:a05:600c:19cd:b0:456:db0:4f3d with SMTP id 5b1f17b1804b1-45b517b9571mr300505335e9.24.1756496169706; Fri, 29 Aug 2025 12:36:09 -0700 (PDT) Received: from fedora.localnet (93-41-67-195.ip80.fastwebnet.it. [93.41.67.195]) by smtp.gmail.com with ESMTPSA id 5b1f17b1804b1-45b66124355sm87079935e9.0.2025.08.29.12.36.08 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 29 Aug 2025 12:36:09 -0700 (PDT) From: Vincenzo Pupillo Date: Fri, 29 Aug 2025 21:36:07 +0200 Message-ID: <2815655.lGaqSPkdTl@fedora> MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="nextPart2627892.XAFRqVoOGU" Content-Transfer-Encoding: 7Bit Received-SPF: pass client-ip=2a00:1450:4864:20::331; envelope-from=v.pupillo@gmail.com; helo=mail-wm1-x331.google.com X-Spam_score_int: -20 X-Spam_score: -2.1 X-Spam_bar: -- X-Spam_report: (-2.1 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, FREEMAIL_FROM=0.001, RCVD_IN_DNSWL_NONE=-0.0001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-Spam-Score: 1.0 (+) X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.18 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: debbugs-submit-bounces@debbugs.gnu.org Sender: "Debbugs-submit" X-Spam-Score: -0.0 (/) This is a multi-part message in MIME format. --nextPart2627892.XAFRqVoOGU Content-Transfer-Encoding: 7Bit Content-Type: text/plain; charset="utf-8" Ciao, this patch add support for the version 24.2 of the grammar for PHP 8.5 (now in beta 2). In addition to this, there are some fixes for both indentation and syntax highlighting. Thanks. Vincenzo --nextPart2627892.XAFRqVoOGU Content-Disposition: attachment; filename="0001-Add-support-for-PHP-8.5.patch" Content-Transfer-Encoding: quoted-printable Content-Type: text/x-patch; charset="UTF-8"; name="0001-Add-support-for-PHP-8.5.patch" =46rom 68f5310214c72d0573e2c55d1f2c861439d9218e Mon Sep 17 00:00:00 2001 =46rom: Vincenzo Pupillo Date: Thu, 28 Aug 2025 23:29:30 +0200 Subject: [PATCH] Add support for PHP 8.5. MIME-Version: 1.0 Content-Type: text/plain; charset=3DUTF-8 Content-Transfer-Encoding: 8bit * lisp/progmodes/php-ts-mode.el: Doc string update. (php-ts-mode--language-source-alist): PHP grammar update. (php-ts-mode-find-sibling-rules): Doc string fix. (php-ts-mode--parent-html-heuristic): Handled the case where there is no HTML between two blocks of PHP code. (php-ts-mode--array-element-heuristic): Fix typo. (php-ts-mode--pipe-heuristic): New function that handle PHP's new pipe operator. (php-ts-mode--indent-styles): Removed commented code. More accurate indentation of =E2=80=98member_call_expression=E2=80=99. Use of new functio= n to handle pipe operator indentation. New rule for indenting =E2=80=98property_hook_li= st=E2=80=99. (php-ts-mode--test-yield-from-p): New predicate to check whether the 'yield from' keyword is supported by the PHP grammar. (php-ts-mode--test-pipe-p): New predicate to check whether the =E2=80=98pip= e=E2=80=99 operator is supported by the PHP grammar. (php-ts-mode--keywords): Use the new predicate 'php-ts-mode--test-yield-from-p'. (php-ts-mode--operators): Use the new predicate 'php-ts-mode--test-pipe-p'. (php-ts-mode--font-lock-settings): New rules for 'nullsafe_member_access_expression', 'callable' primitive type. New rule for the 'php_end_tag' if supported by the grammar. More precise rules for 'scoped_call_expression' and 'member_call_expression'. (php-ts-mode--inferior-php-process): Removed this unnecessary variable (inferior-php-ts-mode-startup): Removed the use of 'php-ts-mode--inferior-php-process'. (php-ts-mode-inferior--write-history): Removed the use of 'php-ts-mode--inferior-php-process'. =2D-- lisp/progmodes/php-ts-mode.el | 164 +++++++++++++++++++++------------- 1 file changed, 103 insertions(+), 61 deletions(-) diff --git a/lisp/progmodes/php-ts-mode.el b/lisp/progmodes/php-ts-mode.el index e23293bdd3b..ba8b7d01fac 100644 =2D-- a/lisp/progmodes/php-ts-mode.el +++ b/lisp/progmodes/php-ts-mode.el @@ -30,7 +30,7 @@ ;; - tree-sitter-jsdoc: v0.23.2 ;; - tree-sitter-javascript: v0.23.1-2-g108b2d4 ;; - tree-sitter-html: v0.23.2-1-gd9219ad =2D;; - tree-sitter-php: v0.23.12 +;; - tree-sitter-php: v0.24.2 ;; ;; We try our best to make builtin modes work with latest grammar ;; versions, so a more recent grammar has a good chance to work too. @@ -81,7 +81,7 @@ ;;; Install treesitter language parsers (defvar php-ts-mode--language-source-alist '((php "https://github.com/tree-sitter/tree-sitter-php" =2D :commit "f7cf7348737d8cff1b13407a0bfedce02ee7b046" + :commit "5b5627faaa290d89eb3d01b9bf47c3bb9e797dea" :source-dir "php/src") (phpdoc "https://github.com/claytonrcarter/tree-sitter-phpdoc" :commit "03bb10330704b0b371b044e937d5cc7cd40b4999")) @@ -238,8 +238,8 @@ php-ts-mode-inferior-history (defcustom php-ts-mode-find-sibling-rules (list (list (rx "src/" (group (+ not-newline) "/") (group (+ (not "/")))= ".php") "tests/\\1\\2Test.php") (list (rx "tests/" (group (+ not-newline) "/") (group (+ (not "/"))) "Tes= t.php") "src/\\1\\2.php")) =2D "Rules for finding sibling files. See `find-sibling-rules' for the =2D form of the value. + "Rules for finding sibling files. +See `find-sibling-rules' for the form of the value. As a default, the rules try to find the corresponding test of the current source file and vice versa. Source files are assumed to be in src/, and tests of in tests/. Many frameworks have a folder @@ -587,7 +587,11 @@ php-ts-mode--parent-html-heuristic ((eq php-ts-mode-html-relative-indent 'ignore) (line-beginning-positi= on)) ((search-backward "" (treesit-node-start parent) t 1) (line-be= ginning-position)) ((null node) (apply (alist-get 'prev-sibling treesit-simple-indent-pr= esets) node parent bol nil)) =2D (t (when-let* ((html-node (treesit-search-forward node "text" t)) + (t (when-let* ((html-node (treesit-search-forward + node + (lambda (node) + (equal (treesit-node-type node) "text")) + t)) (end-html (treesit-node-end html-node))) (goto-char end-html) ;; go to the start of the last tag @@ -622,7 +626,7 @@ php-ts-mode--array-element-heuristic (defun php-ts-mode--anchor-first-sibling (_node parent _bol &rest _) "Return the start of the first child of a sibling of PARENT. =20 =2DIf the fist sibling of PARENT and the first child of the sibling are +If the first sibling of PARENT and the first child of the sibling are on the same line return the start position of the first child of the sibling. Otherwise return the start of the first sibling. PARENT is NODE's parent, BOL is the beginning of non-whitespace @@ -663,12 +667,27 @@ php-ts-mode--anchor-prev-sibling (treesit-node-prev-sibling prev-sibling))))) (treesit-node-start prev-sibling))) =20 +(defun php-ts-mode--pipe-heuristic (node parent _bol &rest _) + "Return the start of the previous pipe to the current pipe NODE. +Otherwise return the beginning of line of the previous non pipe NODE. + +PARENT is NODE's parent, BOL is the beginning of non-whitespace +characters of the current line." + (save-excursion + (let* ((parent-start (treesit-node-start parent)) + (node-start (treesit-node-start node)) + (bound (progn + (goto-char parent-start) + (beginning-of-line 1) + (point)))) + (goto-char node-start) + (let ((previous-pipe (search-backward "|>" bound t nil))) + (or previous-pipe (+ bound php-ts-mode-indent-offset)))))) + (defun php-ts-mode--indent-styles () "Indent rules supported by `php-ts-mode'." (let ((common `(;; Handle indentation relatives to HTML. =2D ;; ((parent-is "program") php-ts-mode--parent-html-heuristic 0) =2D ;; ((parent-is "text_interpolation") php-ts-mode--parent-html-heuris= tic 0) ((or (parent-is "program") (parent-is "text_interpolation")) php-ts-mode--parent-html-heuristic 0) @@ -709,12 +728,14 @@ php-ts-mode--indent-styles (parent-is "use_list")) parent-bol php-ts-mode-indent-offset) ((parent-is "function_definition") parent-bol 0) =2D ((parent-is "member_call_expression") first-sibling php-ts-mode-inde= nt-offset) + ((parent-is "member_call_expression") parent-bol php-ts-mode-indent-of= fset) ((parent-is "conditional_expression") parent-bol php-ts-mode-indent-of= fset) ((parent-is "assignment_expression") parent-bol php-ts-mode-indent-off= set) ((parent-is "array_creation_expression") parent-bol php-ts-mode-indent= =2Doffset) ((parent-is "attribute_group") parent-bol php-ts-mode-indent-offset) ((parent-is "parenthesized_expression") first-sibling 1) + + ((node-is "|>") php-ts-mode--pipe-heuristic 0) ((parent-is "binary_expression") parent 0) ((or (parent-is "arguments") (parent-is "formal_parameters")) @@ -742,6 +763,7 @@ php-ts-mode--indent-styles ((parent-is "declaration_list") column-0 php-ts-mode-indent-offset) =20 ((parent-is "initializer_list") parent-bol php-ts-mode-indent-offset) + ((parent-is "property_hook_list") parent-bol php-ts-mode-indent-offset) =20 ;; Statement in {} blocks. ((or (and (or (parent-is "compound_statement") @@ -827,24 +849,66 @@ php-ts-mode--phpdoc-indent-rules =0C ;;; Font-lock =20 +(defun php-ts-mode--test-namespace-name-as-prefix-p () + "Return t if namespace_name_as_prefix is a named node, nil otherwise." + (treesit-query-valid-p 'php "(namespace_name_as_prefix)")) + +(defun php-ts-mode--test-namespace-aliasing-clause-p () + "Return t if namespace_aliasing_clause is a named node, nil otherwise." + (treesit-query-valid-p 'php "(namespace_aliasing_clause)")) + +(defun php-ts-mode--test-namespace-use-group-clause-p () + "Return t if namespace_use_group_clause is a named node, nil otherwise." + (treesit-query-valid-p 'php "(namespace_use_group_clause)")) + +(defun php-ts-mode--test-visibility-modifier-operation-p () + "Return t if (visibility_modifier (operation)) is defined, nil otherwise= =2E" + (treesit-query-valid-p 'php "(visibility_modifier (operation))")) + +(defun php-ts-mode--test-property-hook-p () + "Return t if property_hook is a named node, nil otherwise." + (treesit-query-valid-p 'php "(property_hook)")) + +(defun php-ts-mode--test-relative-name-p () + "Return t if relative_name is a named node, nil otherwise." + (treesit-query-valid-p 'php "(relative_name)")) + +(defun php-ts-mode--test-php-end-tag-p () + "Return t if php_end_tag is a named node, nil otherwise." + (treesit-query-valid-p 'php "(php_end_tag)")) + +(defun php-ts-mode--test-yield-from-p () + "Return t if the keyword `yield from' is defined, nil otherwise." + (treesit-query-valid-p 'php '("yield from"))) + +(defun php-ts-mode--test-pipe-p () + "Return t if the operator '|>' is defined, nil otherwise." + (treesit-query-valid-p 'php '("|>"))) + (defconst php-ts-mode--keywords =2D '("abstract" "and" "array" "as" "break" "callable" "case" "catch" =2D "class" "clone" "const" "continue" "declare" "default" "do" "echo" =2D "else" "elseif" "enddeclare" "endfor" "endforeach" "endif" =2D "endswitch" "endwhile" "enum" "exit" "extends" "final" "finally" "fn" =2D "for" "foreach" "from" "function" "global" "goto" "if" "implements" =2D "include" "include_once" "instanceof" "insteadof" "interface" =2D "list" "match" "namespace" "new" "null" "or" "print" "private" =2D "protected" "public" "readonly" "require" "require_once" "return" =2D "static" "switch" "throw" "trait" "try" "unset" "use" "while" "xor" =2D "yield") + (when (treesit-available-p) + (append + '("abstract" "and" "array" "as" "break" "case" "catch" + "class" "clone" "const" "continue" "declare" "default" "do" "echo" + "else" "elseif" "enddeclare" "endfor" "endforeach" "endif" + "endswitch" "endwhile" "enum" "exit" "extends" "final" "finally" "f= n" + "for" "foreach" "function" "global" "goto" "if" "implements" + "include" "include_once" "instanceof" "insteadof" "interface" + "list" "match" "namespace" "new" "null" "or" "print" "private" + "protected" "public" "readonly" "require" "require_once" "return" + "static" "switch" "throw" "trait" "try" "unset" "use" "while" "xor" + "yield") + (if (php-ts-mode--test-yield-from-p) '("yield from") '("from")))) "PHP keywords for tree-sitter font-locking.") =20 (defconst php-ts-mode--operators =2D '("--" "**=3D" "*=3D" "/=3D" "%=3D" "+=3D" "-=3D" ".=3D" "<<=3D" ">>= =3D" "&=3D" "^=3D" =2D "|=3D" "??" "??=3D" "||" "&&" "|" "^" "&" "=3D=3D" "!=3D" "<>" "=3D= =3D=3D" "!=3D=3D" =2D "<" ">" "<=3D" ">=3D" "<=3D>" "<<" ">>" "+" "-" "." "*" "**" "/" "%" =2D "->" "?->" "...") + (when (treesit-available-p) + (append + '("--" "**=3D" "*=3D" "/=3D" "%=3D" "+=3D" "-=3D" ".=3D" "<<=3D" ">>= =3D" "&=3D" "^=3D" + "|=3D" "??" "??=3D" "||" "&&" "|" "^" "&" "=3D=3D" "!=3D" "<>" "= =3D=3D=3D" "!=3D=3D" + "<" ">" "<=3D" ">=3D" "<=3D>" "<<" ">>" "+" "-" "." "*" "**" "/" "%" + "->" "?->" "...") + (when (php-ts-mode--test-pipe-p) '("|>")))) "PHP operators for tree-sitter font-locking.") =20 (defconst php-ts-mode--predefined-constant @@ -890,30 +954,6 @@ php-ts-mode--prettify-symbols-alist ("::" . ?=E2=88=B7)) "Value for `prettify-symbols-alist' in `php-ts-mode'.") =20 =2D(defun php-ts-mode--test-namespace-name-as-prefix-p () =2D "Return t if namespace_name_as_prefix is a named node, nil otherwise." =2D (treesit-query-valid-p 'php "(namespace_name_as_prefix)")) =2D =2D(defun php-ts-mode--test-namespace-aliasing-clause-p () =2D "Return t if namespace_aliasing_clause is a named node, nil otherwise." =2D (treesit-query-valid-p 'php "(namespace_aliasing_clause)")) =2D =2D(defun php-ts-mode--test-namespace-use-group-clause-p () =2D "Return t if namespace_use_group_clause is a named node, nil otherwise= =2E" =2D (treesit-query-valid-p 'php "(namespace_use_group_clause)")) =2D =2D(defun php-ts-mode--test-visibility-modifier-operation-p () =2D "Return t if (visibility_modifier (operation)) is defined, nil otherwi= se." =2D (treesit-query-valid-p 'php "(visibility_modifier (operation))")) =2D =2D(defun php-ts-mode--test-property-hook-p () =2D "Return t if property_hook is a named node, nil otherwise." =2D (treesit-query-valid-p 'php "(property_hook)")) =2D =2D(defun php-ts-mode--test-relative-name-p () =2D "Return t if relative_name is a named node, nil otherwise." =2D (treesit-query-valid-p 'php "(relative_name)")) =2D (defun php-ts-mode--font-lock-settings () "Tree-sitter font-lock settings." (treesit-font-lock-rules @@ -974,6 +1014,7 @@ php-ts-mode--font-lock-settings name: (_) @font-lock-variable-name-face) (scoped_property_access_expression scope: (name) @font-lock-constant-face) + (nullsafe_member_access_expression (name) @font-lock-variable-name-fa= ce) (error_suppression_expression (name) @font-lock-property-name-face)) =20 :language 'php @@ -1002,6 +1043,8 @@ php-ts-mode--font-lock-settings (union_type) @font-lock-type-face (bottom_type) @font-lock-type-face (primitive_type) @font-lock-type-face + ((primitive_type) @font-lock-keyword-face + (:equal "callable" @font-lock-keyword-face)) (cast_type) @font-lock-type-face (named_type) @font-lock-type-face (optional_type) @font-lock-type-face) @@ -1010,7 +1053,9 @@ php-ts-mode--font-lock-settings :feature 'definition :override t `((php_tag) @font-lock-preprocessor-face =2D ("?>") @font-lock-preprocessor-face + ,@(if (php-ts-mode--test-php-end-tag-p) + '((php_end_tag) @font-lock-preprocessor-face) + '(("?>") @font-lock-preprocessor-face)) ;; Highlights identifiers in declarations. (class_declaration name: (_) @font-lock-type-face) @@ -1067,9 +1112,9 @@ php-ts-mode--font-lock-settings '((function_call_expression function: (name) @font-lock-function-call-face) (scoped_call_expression =2D name: (_) @font-lock-function-call-face) + name: (name) @font-lock-function-call-face) (member_call_expression =2D name: (_) @font-lock-function-call-face) + name: (name) @font-lock-function-call-face) (nullsafe_member_call_expression name: (_) @font-lock-function-call-face)) =20 @@ -1792,9 +1837,6 @@ inferior-php-ts-mode =0C ;;; Inferior PHP process. =20 =2D(defvar php-ts-mode--inferior-php-process nil =2D "The PHP inferior process associated to `php-ts-mode-inferior-php-buff= er'.") =2D ;;;###autoload (defun run-php (&optional cmd config) "Run an PHP interpreter as a inferior process. @@ -1829,8 +1871,7 @@ inferior-php-ts-mode-startup "Start an inferior PHP process with command CMD and init file CONFIG. CMD is the command to run. Optional CONFIG, if supplied, is the php.ini file to use." =2D (setq-local php-ts-mode--inferior-php-process =2D (apply #'make-comint-in-buffer + (apply #'make-comint-in-buffer (string-replace "*" "" php-ts-mode-inferior-php-buffer) php-ts-mode-inferior-php-buffer cmd @@ -1840,7 +1881,7 @@ inferior-php-ts-mode-startup (list (when config (format "-c %s" config)) =2D "-a")))) + "-a"))) (add-hook 'comint-preoutput-filter-functions (lambda (string) (let ((prompt (concat php-ts-mode--inferior-prompt " "))) @@ -1865,7 +1906,7 @@ inferior-php-ts-mode-startup nil t) (when php-ts-mode-inferior-history (set-process-sentinel =2D (get-buffer-process php-ts-mode-inferior-php-buffer) + (get-buffer-process php-ts-mode-inferior-php-buffer) 'php-ts-mode-inferior--write-history))) =20 ;; taken and adapted from lua-ts-mode @@ -1880,14 +1921,15 @@ php-ts-mode-inferior--write-history (defun php-ts-mode-send-region (beg end) "Send region between BEG and END to the inferior PHP process." (interactive "r") =2D (if (buffer-live-p php-ts-mode--inferior-php-process) + (if-let* ((php-process + (get-buffer-process php-ts-mode-inferior-php-buffer))) (progn (php-ts-mode-show-process-buffer) =2D (comint-send-string php-ts-mode--inferior-php-process "\n") + (comint-send-string php-process "\n") (comint-send-string =2D php-ts-mode--inferior-php-process + php-process (buffer-substring-no-properties beg end)) =2D (comint-send-string php-ts-mode--inferior-php-process "\n")) + (comint-send-string php-process "\n")) (message "Invoke run-php first!"))) =20 (defun php-ts-mode-send-buffer () =2D-=20 2.51.0 --nextPart2627892.XAFRqVoOGU-- From unknown Thu Sep 11 10:42:23 2025 X-Loop: help-debbugs@gnu.org Subject: bug#79339: 31.0.50; [PATCH] php-ts-mode: support PHP 8.5 Resent-From: Eli Zaretskii Original-Sender: "Debbugs-submit" Resent-CC: bug-gnu-emacs@gnu.org Resent-Date: Sat, 06 Sep 2025 08:58:02 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: followup 79339 X-GNU-PR-Package: emacs X-GNU-PR-Keywords: patch To: Vincenzo Pupillo Cc: 79339@debbugs.gnu.org Received: via spool by 79339-submit@debbugs.gnu.org id=B79339.175714902818030 (code B ref 79339); Sat, 06 Sep 2025 08:58:02 +0000 Received: (at 79339) by debbugs.gnu.org; 6 Sep 2025 08:57:08 +0000 Received: from localhost ([127.0.0.1]:34339 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1uuojL-0004gj-EG for submit@debbugs.gnu.org; Sat, 06 Sep 2025 04:57:08 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:59826) by debbugs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.84_2) (envelope-from ) id 1uuojB-0004g2-6X for 79339@debbugs.gnu.org; Sat, 06 Sep 2025 04:56:58 -0400 Received: from fencepost.gnu.org ([2001:470:142:3::e]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1uuoj5-0000Fq-A1; Sat, 06 Sep 2025 04:56:51 -0400 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=gnu.org; s=fencepost-gnu-org; h=References:Subject:In-Reply-To:To:From:Date: mime-version; bh=UWda2H608qeMDPUuxIg4rzQet8MRsCEmh7LM+XW6oJ8=; b=hmhz3oXEqxE2 N9PZddAkphpVLsBBfuUmJdFCi8/kK3XfQBCSrq++QiikPTuxTebnbmtyrsuOERfKQ4K0jcJtVDyfS 3VTuFsjUuozgKteq/EkEhN3IElm6XUVj6Iy1OzinBBOsOD4Jid8cEB5EMrwN90wBmA9n8FvltWpS3 1eRYjjHQJzRI6QKu7OLftlwQxBziRK4kXrXWKtjg++Bca6vjTv+5xqUsu+dr44Inu1okpLZWqPFck MPbPgnLgUe+UBIGuWm9ODzvGgIeIPx5Uh1Q7THxuw6TnSeQiqi+IoDTV182iss8fp7H1IwW8Vgb6z xwJJNUpK++FNnr65vJ/Vxg==; Date: Sat, 06 Sep 2025 11:56:47 +0300 Message-Id: <86wm6cez74.fsf@gnu.org> From: Eli Zaretskii In-Reply-To: <2815655.lGaqSPkdTl@fedora> (message from Vincenzo Pupillo on Fri, 29 Aug 2025 21:36:07 +0200) References: <2815655.lGaqSPkdTl@fedora> X-Spam-Score: -2.3 (--) X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.18 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: debbugs-submit-bounces@debbugs.gnu.org Sender: "Debbugs-submit" X-Spam-Score: -3.3 (---) > From: Vincenzo Pupillo > Date: Fri, 29 Aug 2025 21:36:07 +0200 > > Ciao, > this patch add support for the version 24.2 of the grammar for PHP 8.5 (now in > beta 2). > In addition to this, there are some fixes for both indentation and syntax > highlighting. Thanks. Is this supposed to keep working with older versions of the grammar? > (defconst php-ts-mode--keywords > - '("abstract" "and" "array" "as" "break" "callable" "case" "catch" > - "class" "clone" "const" "continue" "declare" "default" "do" "echo" > - "else" "elseif" "enddeclare" "endfor" "endforeach" "endif" > - "endswitch" "endwhile" "enum" "exit" "extends" "final" "finally" "fn" > - "for" "foreach" "from" "function" "global" "goto" "if" "implements" > - "include" "include_once" "instanceof" "insteadof" "interface" > - "list" "match" "namespace" "new" "null" "or" "print" "private" > - "protected" "public" "readonly" "require" "require_once" "return" > - "static" "switch" "throw" "trait" "try" "unset" "use" "while" "xor" > - "yield") > + (when (treesit-available-p) > + (append > + '("abstract" "and" "array" "as" "break" "case" "catch" > + "class" "clone" "const" "continue" "declare" "default" "do" "echo" > + "else" "elseif" "enddeclare" "endfor" "endforeach" "endif" > + "endswitch" "endwhile" "enum" "exit" "extends" "final" "finally" "fn" > + "for" "foreach" "function" "global" "goto" "if" "implements" > + "include" "include_once" "instanceof" "insteadof" "interface" > + "list" "match" "namespace" "new" "null" "or" "print" "private" > + "protected" "public" "readonly" "require" "require_once" "return" > + "static" "switch" "throw" "trait" "try" "unset" "use" "while" "xor" > + "yield") > + (if (php-ts-mode--test-yield-from-p) '("yield from") '("from")))) > "PHP keywords for tree-sitter font-locking.") > > (defconst php-ts-mode--operators > - '("--" "**=" "*=" "/=" "%=" "+=" "-=" ".=" "<<=" ">>=" "&=" "^=" > - "|=" "??" "??=" "||" "&&" "|" "^" "&" "==" "!=" "<>" "===" "!==" > - "<" ">" "<=" ">=" "<=>" "<<" ">>" "+" "-" "." "*" "**" "/" "%" > - "->" "?->" "...") > + (when (treesit-available-p) > + (append > + '("--" "**=" "*=" "/=" "%=" "+=" "-=" ".=" "<<=" ">>=" "&=" "^=" > + "|=" "??" "??=" "||" "&&" "|" "^" "&" "==" "!=" "<>" "===" "!==" > + "<" ">" "<=" ">=" "<=>" "<<" ">>" "+" "-" "." "*" "**" "/" "%" > + "->" "?->" "...") > + (when (php-ts-mode--test-pipe-p) '("|>")))) > "PHP operators for tree-sitter font-locking.") Since these two are defconsts, is it wise to have their value depend on something that could change with the grammar version? Doing so might mean that the byte-compiled value includes traces of the grammar library installed on the system where the file was byte-compiled, which might cause trouble if the system on which the code is run has a different grammar version. Or am I missing something? From unknown Thu Sep 11 10:42:23 2025 X-Loop: help-debbugs@gnu.org Subject: bug#79339: 31.0.50; [PATCH] php-ts-mode: support PHP 8.5 Resent-From: Vincenzo Pupillo Original-Sender: "Debbugs-submit" Resent-CC: bug-gnu-emacs@gnu.org Resent-Date: Sun, 07 Sep 2025 17:22:01 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: followup 79339 X-GNU-PR-Package: emacs X-GNU-PR-Keywords: patch To: Eli Zaretskii Cc: 79339@debbugs.gnu.org Received: via spool by 79339-submit@debbugs.gnu.org id=B79339.175726566818831 (code B ref 79339); Sun, 07 Sep 2025 17:22:01 +0000 Received: (at 79339) by debbugs.gnu.org; 7 Sep 2025 17:21:08 +0000 Received: from localhost ([127.0.0.1]:45553 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1uvJ4c-0004tY-IS for submit@debbugs.gnu.org; Sun, 07 Sep 2025 13:21:08 -0400 Received: from mail-wm1-x329.google.com ([2a00:1450:4864:20::329]:53266) by debbugs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.84_2) (envelope-from ) id 1uvJ4V-0004sd-6Q for 79339@debbugs.gnu.org; Sun, 07 Sep 2025 13:21:00 -0400 Received: by mail-wm1-x329.google.com with SMTP id 5b1f17b1804b1-45de1e6d76fso7072545e9.2 for <79339@debbugs.gnu.org>; Sun, 07 Sep 2025 10:20:59 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1757265652; x=1757870452; darn=debbugs.gnu.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=xMqL1xCPO2ztgWZkNfoLAj2MwKfoxSF9SVY8jCzIYzE=; b=hYhH+3guO5BlvwPWb3tCgsO624YyJbcTLXacCoYsP4BSwrftqKM9UIC1wXJrw0hPtD OIjYuHX9KIEvdt002b7LdMfN6hZNsD3OB+CfJXZE4ZhM0IvN92F1gB2oAe4cmH6keYuX h85voqFC28qMUQ3XlSZ6MzC84CUuXKwU+eQ4tAFPmw8dh8UH8DtNYqZ7w+VdiPBfSHws FaDGiJU/fprqQb7bTsA+9tYr3lkovkN8K9Rej7ho3m7OvYn3guJGwDzkN4MsOT6dOKhv +bkMwgZTJ7xvb5/md96dKH089QckpFTrXnetRKxZJ2Pq05n864Z759cI4Q1p8oQIlU8n QIzQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1757265652; x=1757870452; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=xMqL1xCPO2ztgWZkNfoLAj2MwKfoxSF9SVY8jCzIYzE=; b=loqM1cn6QZFQ7miSw4N9vazg1Z0CfZrjxyrPuXQgErkawPE0zRA9D4b24X/XFKVr+d 1YkvK362DUhaW31zFWJmFXuYB7ZEyUXrnPgW1PNF2+n+eYL/HFqANTDE4m8zvE+wV30Z IL6lVaNzWykZEfzrlxNggCJdbZA+6ZfRqL2HV2aQT5HnN1Z64ez/LnZjJEt6ozBuRCqg +axLBJrn+ZoH9NJl6wtSeu4/ehZc9dNVBL/fENYbYqOCJT+tVqjr+7Y6IiNNqrrSIYEj dipMte5HkO6wlxCy1917dm6dcp2876XoC9+ClFoTaoX7I9p8GsZbjrjKpViLaf+GEQVV QAyQ== X-Gm-Message-State: AOJu0YyTSb5P0YZWeLYKwZM1dkUdW4N8ScUMo1inEAaUy6WC38dcF458 f9CO7N3mduOsNkM0fTJFahoq4C41NFwA96+fRkKu26ofgU2WLTgQseYpDuwf8Q== X-Gm-Gg: ASbGncsOfI5LNvWHoii07pSQPIkgnNAu5MLy0WZHt1fU3UXtY5IxnznFzmnWg0Q0PcH UZ/vVsGK5gWIMDC/Amq7TApBsll++28v21JbQZ84z1Zu4mLgSpPWB9q97cRs9TY2YH48qIIrRRO dMO9WjXaCf4GGiqJw7g9xax2uWV1dZzBLUjKwEv9bdJ7Wha406lvITROxxzuWFuxUtd7BS49LWF N/Dno96Zw52YMv8Fed+QsYiSBzWX9hjIomCUbMEUvZ9hetOnhv+emdRMsyqqvChiuQCFMqERt8n TSWegNBvgRe/sMMiifWgtEUYXjfbjxuxYKKGEzcxB32s8YsO60kwIEzr15GYn+xhyzk1JHJRdrZ JuyfllVHNrZFTLnj9B6ZGv3stptkSP0nvigG3yNGllsqR0ix2hmuDaPfDXoqwt4U= X-Google-Smtp-Source: AGHT+IFuLd3BJDzqNcnjryiCOL7DJ2+lAMpLf4e3xBVy64zzC7D/0hKo4hKbKdXoHqTnlQoY1qHGsg== X-Received: by 2002:a05:6000:178e:b0:3d8:3eca:a978 with SMTP id ffacd0b85a97d-3e642e99b04mr3433261f8f.21.1757265651604; Sun, 07 Sep 2025 10:20:51 -0700 (PDT) Received: from fedora.localnet (2-230-139-124.ip202.fastwebnet.it. [2.230.139.124]) by smtp.gmail.com with ESMTPSA id ffacd0b85a97d-3e5100eba33sm7533219f8f.9.2025.09.07.10.20.50 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Sun, 07 Sep 2025 10:20:51 -0700 (PDT) From: Vincenzo Pupillo Date: Sun, 07 Sep 2025 19:20:49 +0200 Message-ID: <2197981.9o76ZdvQCi@fedora> In-Reply-To: <86wm6cez74.fsf@gnu.org> References: <2815655.lGaqSPkdTl@fedora> <86wm6cez74.fsf@gnu.org> MIME-Version: 1.0 Content-Type: multipart/mixed; boundary="nextPart2769377.vuYhMxLoTh" Content-Transfer-Encoding: 7Bit X-Spam-Score: 0.0 (/) X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.18 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: debbugs-submit-bounces@debbugs.gnu.org Sender: "Debbugs-submit" X-Spam-Score: -1.0 (-) This is a multi-part message in MIME format. --nextPart2769377.vuYhMxLoTh Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" In data sabato 6 settembre 2025 10:56:47 Ora legale dell=E2=80=99Europa cen= trale, Eli=20 Zaretskii ha scritto: > > From: Vincenzo Pupillo > > Date: Fri, 29 Aug 2025 21:36:07 +0200 > >=20 > > Ciao, > > this patch add support for the version 24.2 of the grammar for PHP 8.5 > > (now in beta 2). > > In addition to this, there are some fixes for both indentation and synt= ax > > highlighting. >=20 > Thanks. >=20 > Is this supposed to keep working with older versions of the grammar? Yes. I used this patch for a week with the old grammar and didn't encounter= =20 any problems. >=20 > > (defconst php-ts-mode--keywords > >=20 > > - '("abstract" "and" "array" "as" "break" "callable" "case" "catch" > > - "class" "clone" "const" "continue" "declare" "default" "do" "echo" > > - "else" "elseif" "enddeclare" "endfor" "endforeach" "endif" > > - "endswitch" "endwhile" "enum" "exit" "extends" "final" "finally" "= fn" > > - "for" "foreach" "from" "function" "global" "goto" "if" "implements" > > - "include" "include_once" "instanceof" "insteadof" "interface" > > - "list" "match" "namespace" "new" "null" "or" "print" "private" > > - "protected" "public" "readonly" "require" "require_once" "return" > > - "static" "switch" "throw" "trait" "try" "unset" "use" "while" "xor" > > - "yield") > > + (when (treesit-available-p) > > + (append > > + '("abstract" "and" "array" "as" "break" "case" "catch" > > + "class" "clone" "const" "continue" "declare" "default" "do" "ec= ho" > > + "else" "elseif" "enddeclare" "endfor" "endforeach" "endif" > > + "endswitch" "endwhile" "enum" "exit" "extends" "final" "finally" > > "fn" + "for" "foreach" "function" "global" "goto" "if" "implement= s" > > + "include" "include_once" "instanceof" "insteadof" "interface" += =20 > > "list" "match" "namespace" "new" "null" "or" "print" "private" + = =20 > > "protected" "public" "readonly" "require" "require_once" "return" + = =20 > > "static" "switch" "throw" "trait" "try" "unset" "use" "while" "xor" + = =20 > > "yield") > > + (if (php-ts-mode--test-yield-from-p) '("yield from") '("from")))) > >=20 > > "PHP keywords for tree-sitter font-locking.") > > =20 > > (defconst php-ts-mode--operators > >=20 > > - '("--" "**=3D" "*=3D" "/=3D" "%=3D" "+=3D" "-=3D" ".=3D" "<<=3D" ">>= =3D" "&=3D" "^=3D" > > - "|=3D" "??" "??=3D" "||" "&&" "|" "^" "&" "=3D=3D" "!=3D" "<>" "= =3D=3D=3D" "!=3D=3D" > > - "<" ">" "<=3D" ">=3D" "<=3D>" "<<" ">>" "+" "-" "." "*" "**" "/" "= %" > > - "->" "?->" "...") > > + (when (treesit-available-p) > > + (append > > + '("--" "**=3D" "*=3D" "/=3D" "%=3D" "+=3D" "-=3D" ".=3D" "<<=3D" = ">>=3D" "&=3D" "^=3D" > > + "|=3D" "??" "??=3D" "||" "&&" "|" "^" "&" "=3D=3D" "!=3D" "<>"= "=3D=3D=3D" "!=3D=3D" > > + "<" ">" "<=3D" ">=3D" "<=3D>" "<<" ">>" "+" "-" "." "*" "**" "/= " "%" > > + "->" "?->" "...") > > + (when (php-ts-mode--test-pipe-p) '("|>")))) > >=20 > > "PHP operators for tree-sitter font-locking.") >=20 > Since these two are defconsts, is it wise to have their value depend > on something that could change with the grammar version? Doing so > might mean that the byte-compiled value includes traces of the grammar > library installed on the system where the file was byte-compiled, > which might cause trouble if the system on which the code is run has a > different grammar version. Or am I missing something? No, you're right. Here is the new version attached. Now the constants are=20 variables. Thank you. Vincenzo --nextPart2769377.vuYhMxLoTh Content-Disposition: attachment; filename="0001-Add-support-for-PHP-8.5.patch" Content-Transfer-Encoding: quoted-printable Content-Type: text/x-patch; charset="UTF-8"; name="0001-Add-support-for-PHP-8.5.patch" =46rom 2286cf033075a49893f569d3d25a26ecd95348ae Mon Sep 17 00:00:00 2001 =46rom: Vincenzo Pupillo Date: Thu, 28 Aug 2025 23:29:30 +0200 Subject: [PATCH] Add support for PHP 8.5. MIME-Version: 1.0 Content-Type: text/plain; charset=3DUTF-8 Content-Transfer-Encoding: 8bit * lisp/progmodes/php-ts-mode.el: Doc string update. (php-ts-mode--language-source-alist): PHP grammar update. (php-ts-mode-find-sibling-rules): Doc string fix. (php-ts-mode--parent-html-heuristic): Handled the case where there is no HTML between two blocks of PHP code. (php-ts-mode--array-element-heuristic): Fix typo. (php-ts-mode--pipe-heuristic): New function that handle PHP's new pipe operator. (php-ts-mode--indent-styles): Removed commented code. More accurate indentation of =E2=80=98member_call_expression=E2=80=99. Use of new functio= n to handle pipe operator indentation. New rule for indenting =E2=80=98property_hook_li= st=E2=80=99. (php-ts-mode--test-yield-from-p): New predicate to check whether the 'yield from' keyword is supported by the PHP grammar. (php-ts-mode--test-pipe-p): New predicate to check whether the =E2=80=98pip= e=E2=80=99 operator is supported by the PHP grammar. (php-ts-mode--keywords): Use the new predicate 'php-ts-mode--test-yield-from-p'. Now it is a var instead of a const. (php-ts-mode--operators): Use the new predicate 'php-ts-mode--test-pipe-p'. Now it is a var instead of a const. (php-ts-mode--font-lock-settings): New rules for 'nullsafe_member_access_expression', 'callable' primitive type. New rule for the 'php_end_tag' if supported by the grammar. More precise rules for 'scoped_call_expression' and 'member_call_expression'. (php-ts-mode--inferior-php-process): Removed this unnecessary variable (inferior-php-ts-mode-startup): Removed the use of 'php-ts-mode--inferior-php-process'. (php-ts-mode-inferior--write-history): Removed the use of 'php-ts-mode--inferior-php-process'. =2D-- lisp/progmodes/php-ts-mode.el | 168 +++++++++++++++++++++------------- 1 file changed, 105 insertions(+), 63 deletions(-) diff --git a/lisp/progmodes/php-ts-mode.el b/lisp/progmodes/php-ts-mode.el index e23293bdd3b..3c9cb2ba8d0 100644 =2D-- a/lisp/progmodes/php-ts-mode.el +++ b/lisp/progmodes/php-ts-mode.el @@ -30,7 +30,7 @@ ;; - tree-sitter-jsdoc: v0.23.2 ;; - tree-sitter-javascript: v0.23.1-2-g108b2d4 ;; - tree-sitter-html: v0.23.2-1-gd9219ad =2D;; - tree-sitter-php: v0.23.12 +;; - tree-sitter-php: v0.24.2 ;; ;; We try our best to make builtin modes work with latest grammar ;; versions, so a more recent grammar has a good chance to work too. @@ -81,7 +81,7 @@ ;;; Install treesitter language parsers (defvar php-ts-mode--language-source-alist '((php "https://github.com/tree-sitter/tree-sitter-php" =2D :commit "f7cf7348737d8cff1b13407a0bfedce02ee7b046" + :commit "5b5627faaa290d89eb3d01b9bf47c3bb9e797dea" :source-dir "php/src") (phpdoc "https://github.com/claytonrcarter/tree-sitter-phpdoc" :commit "03bb10330704b0b371b044e937d5cc7cd40b4999")) @@ -238,8 +238,8 @@ php-ts-mode-inferior-history (defcustom php-ts-mode-find-sibling-rules (list (list (rx "src/" (group (+ not-newline) "/") (group (+ (not "/")))= ".php") "tests/\\1\\2Test.php") (list (rx "tests/" (group (+ not-newline) "/") (group (+ (not "/"))) "Tes= t.php") "src/\\1\\2.php")) =2D "Rules for finding sibling files. See `find-sibling-rules' for the =2D form of the value. + "Rules for finding sibling files. +See `find-sibling-rules' for the form of the value. As a default, the rules try to find the corresponding test of the current source file and vice versa. Source files are assumed to be in src/, and tests of in tests/. Many frameworks have a folder @@ -587,7 +587,11 @@ php-ts-mode--parent-html-heuristic ((eq php-ts-mode-html-relative-indent 'ignore) (line-beginning-positi= on)) ((search-backward "" (treesit-node-start parent) t 1) (line-be= ginning-position)) ((null node) (apply (alist-get 'prev-sibling treesit-simple-indent-pr= esets) node parent bol nil)) =2D (t (when-let* ((html-node (treesit-search-forward node "text" t)) + (t (when-let* ((html-node (treesit-search-forward + node + (lambda (node) + (equal (treesit-node-type node) "text")) + t)) (end-html (treesit-node-end html-node))) (goto-char end-html) ;; go to the start of the last tag @@ -622,7 +626,7 @@ php-ts-mode--array-element-heuristic (defun php-ts-mode--anchor-first-sibling (_node parent _bol &rest _) "Return the start of the first child of a sibling of PARENT. =20 =2DIf the fist sibling of PARENT and the first child of the sibling are +If the first sibling of PARENT and the first child of the sibling are on the same line return the start position of the first child of the sibling. Otherwise return the start of the first sibling. PARENT is NODE's parent, BOL is the beginning of non-whitespace @@ -663,12 +667,27 @@ php-ts-mode--anchor-prev-sibling (treesit-node-prev-sibling prev-sibling))))) (treesit-node-start prev-sibling))) =20 +(defun php-ts-mode--pipe-heuristic (node parent _bol &rest _) + "Return the start of the previous pipe to the current pipe NODE. +Otherwise return the beginning of line of the previous non pipe NODE. + +PARENT is NODE's parent, BOL is the beginning of non-whitespace +characters of the current line." + (save-excursion + (let* ((parent-start (treesit-node-start parent)) + (node-start (treesit-node-start node)) + (bound (progn + (goto-char parent-start) + (beginning-of-line 1) + (point)))) + (goto-char node-start) + (let ((previous-pipe (search-backward "|>" bound t nil))) + (or previous-pipe (+ bound php-ts-mode-indent-offset)))))) + (defun php-ts-mode--indent-styles () "Indent rules supported by `php-ts-mode'." (let ((common `(;; Handle indentation relatives to HTML. =2D ;; ((parent-is "program") php-ts-mode--parent-html-heuristic 0) =2D ;; ((parent-is "text_interpolation") php-ts-mode--parent-html-heuris= tic 0) ((or (parent-is "program") (parent-is "text_interpolation")) php-ts-mode--parent-html-heuristic 0) @@ -709,12 +728,14 @@ php-ts-mode--indent-styles (parent-is "use_list")) parent-bol php-ts-mode-indent-offset) ((parent-is "function_definition") parent-bol 0) =2D ((parent-is "member_call_expression") first-sibling php-ts-mode-inde= nt-offset) + ((parent-is "member_call_expression") parent-bol php-ts-mode-indent-of= fset) ((parent-is "conditional_expression") parent-bol php-ts-mode-indent-of= fset) ((parent-is "assignment_expression") parent-bol php-ts-mode-indent-off= set) ((parent-is "array_creation_expression") parent-bol php-ts-mode-indent= =2Doffset) ((parent-is "attribute_group") parent-bol php-ts-mode-indent-offset) ((parent-is "parenthesized_expression") first-sibling 1) + + ((node-is "|>") php-ts-mode--pipe-heuristic 0) ((parent-is "binary_expression") parent 0) ((or (parent-is "arguments") (parent-is "formal_parameters")) @@ -742,6 +763,7 @@ php-ts-mode--indent-styles ((parent-is "declaration_list") column-0 php-ts-mode-indent-offset) =20 ((parent-is "initializer_list") parent-bol php-ts-mode-indent-offset) + ((parent-is "property_hook_list") parent-bol php-ts-mode-indent-offset) =20 ;; Statement in {} blocks. ((or (and (or (parent-is "compound_statement") @@ -827,24 +849,66 @@ php-ts-mode--phpdoc-indent-rules =0C ;;; Font-lock =20 =2D(defconst php-ts-mode--keywords =2D '("abstract" "and" "array" "as" "break" "callable" "case" "catch" =2D "class" "clone" "const" "continue" "declare" "default" "do" "echo" =2D "else" "elseif" "enddeclare" "endfor" "endforeach" "endif" =2D "endswitch" "endwhile" "enum" "exit" "extends" "final" "finally" "fn" =2D "for" "foreach" "from" "function" "global" "goto" "if" "implements" =2D "include" "include_once" "instanceof" "insteadof" "interface" =2D "list" "match" "namespace" "new" "null" "or" "print" "private" =2D "protected" "public" "readonly" "require" "require_once" "return" =2D "static" "switch" "throw" "trait" "try" "unset" "use" "while" "xor" =2D "yield") +(defun php-ts-mode--test-namespace-name-as-prefix-p () + "Return t if namespace_name_as_prefix is a named node, nil otherwise." + (treesit-query-valid-p 'php "(namespace_name_as_prefix)")) + +(defun php-ts-mode--test-namespace-aliasing-clause-p () + "Return t if namespace_aliasing_clause is a named node, nil otherwise." + (treesit-query-valid-p 'php "(namespace_aliasing_clause)")) + +(defun php-ts-mode--test-namespace-use-group-clause-p () + "Return t if namespace_use_group_clause is a named node, nil otherwise." + (treesit-query-valid-p 'php "(namespace_use_group_clause)")) + +(defun php-ts-mode--test-visibility-modifier-operation-p () + "Return t if (visibility_modifier (operation)) is defined, nil otherwise= =2E" + (treesit-query-valid-p 'php "(visibility_modifier (operation))")) + +(defun php-ts-mode--test-property-hook-p () + "Return t if property_hook is a named node, nil otherwise." + (treesit-query-valid-p 'php "(property_hook)")) + +(defun php-ts-mode--test-relative-name-p () + "Return t if relative_name is a named node, nil otherwise." + (treesit-query-valid-p 'php "(relative_name)")) + +(defun php-ts-mode--test-php-end-tag-p () + "Return t if php_end_tag is a named node, nil otherwise." + (treesit-query-valid-p 'php "(php_end_tag)")) + +(defun php-ts-mode--test-yield-from-p () + "Return t if the keyword `yield from' is defined, nil otherwise." + (treesit-query-valid-p 'php '("yield from"))) + +(defun php-ts-mode--test-pipe-p () + "Return t if the operator '|>' is defined, nil otherwise." + (treesit-query-valid-p 'php '("|>"))) + +(defvar php-ts-mode--keywords + (when (treesit-available-p) + (append + '("abstract" "and" "array" "as" "break" "case" "catch" + "class" "clone" "const" "continue" "declare" "default" "do" "echo" + "else" "elseif" "enddeclare" "endfor" "endforeach" "endif" + "endswitch" "endwhile" "enum" "exit" "extends" "final" "finally" "f= n" + "for" "foreach" "function" "global" "goto" "if" "implements" + "include" "include_once" "instanceof" "insteadof" "interface" + "list" "match" "namespace" "new" "null" "or" "print" "private" + "protected" "public" "readonly" "require" "require_once" "return" + "static" "switch" "throw" "trait" "try" "unset" "use" "while" "xor" + "yield") + (if (php-ts-mode--test-yield-from-p) '("yield from") '("from")))) "PHP keywords for tree-sitter font-locking.") =20 =2D(defconst php-ts-mode--operators =2D '("--" "**=3D" "*=3D" "/=3D" "%=3D" "+=3D" "-=3D" ".=3D" "<<=3D" ">>= =3D" "&=3D" "^=3D" =2D "|=3D" "??" "??=3D" "||" "&&" "|" "^" "&" "=3D=3D" "!=3D" "<>" "=3D= =3D=3D" "!=3D=3D" =2D "<" ">" "<=3D" ">=3D" "<=3D>" "<<" ">>" "+" "-" "." "*" "**" "/" "%" =2D "->" "?->" "...") +(defvar php-ts-mode--operators + (when (treesit-available-p) + (append + '("--" "**=3D" "*=3D" "/=3D" "%=3D" "+=3D" "-=3D" ".=3D" "<<=3D" ">>= =3D" "&=3D" "^=3D" + "|=3D" "??" "??=3D" "||" "&&" "|" "^" "&" "=3D=3D" "!=3D" "<>" "= =3D=3D=3D" "!=3D=3D" + "<" ">" "<=3D" ">=3D" "<=3D>" "<<" ">>" "+" "-" "." "*" "**" "/" "%" + "->" "?->" "...") + (when (php-ts-mode--test-pipe-p) '("|>")))) "PHP operators for tree-sitter font-locking.") =20 (defconst php-ts-mode--predefined-constant @@ -890,30 +954,6 @@ php-ts-mode--prettify-symbols-alist ("::" . ?=E2=88=B7)) "Value for `prettify-symbols-alist' in `php-ts-mode'.") =20 =2D(defun php-ts-mode--test-namespace-name-as-prefix-p () =2D "Return t if namespace_name_as_prefix is a named node, nil otherwise." =2D (treesit-query-valid-p 'php "(namespace_name_as_prefix)")) =2D =2D(defun php-ts-mode--test-namespace-aliasing-clause-p () =2D "Return t if namespace_aliasing_clause is a named node, nil otherwise." =2D (treesit-query-valid-p 'php "(namespace_aliasing_clause)")) =2D =2D(defun php-ts-mode--test-namespace-use-group-clause-p () =2D "Return t if namespace_use_group_clause is a named node, nil otherwise= =2E" =2D (treesit-query-valid-p 'php "(namespace_use_group_clause)")) =2D =2D(defun php-ts-mode--test-visibility-modifier-operation-p () =2D "Return t if (visibility_modifier (operation)) is defined, nil otherwi= se." =2D (treesit-query-valid-p 'php "(visibility_modifier (operation))")) =2D =2D(defun php-ts-mode--test-property-hook-p () =2D "Return t if property_hook is a named node, nil otherwise." =2D (treesit-query-valid-p 'php "(property_hook)")) =2D =2D(defun php-ts-mode--test-relative-name-p () =2D "Return t if relative_name is a named node, nil otherwise." =2D (treesit-query-valid-p 'php "(relative_name)")) =2D (defun php-ts-mode--font-lock-settings () "Tree-sitter font-lock settings." (treesit-font-lock-rules @@ -974,6 +1014,7 @@ php-ts-mode--font-lock-settings name: (_) @font-lock-variable-name-face) (scoped_property_access_expression scope: (name) @font-lock-constant-face) + (nullsafe_member_access_expression (name) @font-lock-variable-name-fa= ce) (error_suppression_expression (name) @font-lock-property-name-face)) =20 :language 'php @@ -1002,6 +1043,8 @@ php-ts-mode--font-lock-settings (union_type) @font-lock-type-face (bottom_type) @font-lock-type-face (primitive_type) @font-lock-type-face + ((primitive_type) @font-lock-keyword-face + (:equal "callable" @font-lock-keyword-face)) (cast_type) @font-lock-type-face (named_type) @font-lock-type-face (optional_type) @font-lock-type-face) @@ -1010,7 +1053,9 @@ php-ts-mode--font-lock-settings :feature 'definition :override t `((php_tag) @font-lock-preprocessor-face =2D ("?>") @font-lock-preprocessor-face + ,@(if (php-ts-mode--test-php-end-tag-p) + '((php_end_tag) @font-lock-preprocessor-face) + '(("?>") @font-lock-preprocessor-face)) ;; Highlights identifiers in declarations. (class_declaration name: (_) @font-lock-type-face) @@ -1067,9 +1112,9 @@ php-ts-mode--font-lock-settings '((function_call_expression function: (name) @font-lock-function-call-face) (scoped_call_expression =2D name: (_) @font-lock-function-call-face) + name: (name) @font-lock-function-call-face) (member_call_expression =2D name: (_) @font-lock-function-call-face) + name: (name) @font-lock-function-call-face) (nullsafe_member_call_expression name: (_) @font-lock-function-call-face)) =20 @@ -1792,9 +1837,6 @@ inferior-php-ts-mode =0C ;;; Inferior PHP process. =20 =2D(defvar php-ts-mode--inferior-php-process nil =2D "The PHP inferior process associated to `php-ts-mode-inferior-php-buff= er'.") =2D ;;;###autoload (defun run-php (&optional cmd config) "Run an PHP interpreter as a inferior process. @@ -1829,8 +1871,7 @@ inferior-php-ts-mode-startup "Start an inferior PHP process with command CMD and init file CONFIG. CMD is the command to run. Optional CONFIG, if supplied, is the php.ini file to use." =2D (setq-local php-ts-mode--inferior-php-process =2D (apply #'make-comint-in-buffer + (apply #'make-comint-in-buffer (string-replace "*" "" php-ts-mode-inferior-php-buffer) php-ts-mode-inferior-php-buffer cmd @@ -1840,7 +1881,7 @@ inferior-php-ts-mode-startup (list (when config (format "-c %s" config)) =2D "-a")))) + "-a"))) (add-hook 'comint-preoutput-filter-functions (lambda (string) (let ((prompt (concat php-ts-mode--inferior-prompt " "))) @@ -1865,7 +1906,7 @@ inferior-php-ts-mode-startup nil t) (when php-ts-mode-inferior-history (set-process-sentinel =2D (get-buffer-process php-ts-mode-inferior-php-buffer) + (get-buffer-process php-ts-mode-inferior-php-buffer) 'php-ts-mode-inferior--write-history))) =20 ;; taken and adapted from lua-ts-mode @@ -1880,14 +1921,15 @@ php-ts-mode-inferior--write-history (defun php-ts-mode-send-region (beg end) "Send region between BEG and END to the inferior PHP process." (interactive "r") =2D (if (buffer-live-p php-ts-mode--inferior-php-process) + (if-let* ((php-process + (get-buffer-process php-ts-mode-inferior-php-buffer))) (progn (php-ts-mode-show-process-buffer) =2D (comint-send-string php-ts-mode--inferior-php-process "\n") + (comint-send-string php-process "\n") (comint-send-string =2D php-ts-mode--inferior-php-process + php-process (buffer-substring-no-properties beg end)) =2D (comint-send-string php-ts-mode--inferior-php-process "\n")) + (comint-send-string php-process "\n")) (message "Invoke run-php first!"))) =20 (defun php-ts-mode-send-buffer () =2D-=20 2.51.0 --nextPart2769377.vuYhMxLoTh--