unofficial mirror of bug-gnu-emacs@gnu.org 
 help / color / mirror / code / Atom feed
From: "João Távora" <joaotavora@gmail.com>
To: Jim Porter <jporterbugs@gmail.com>
Cc: 49518@debbugs.gnu.org, Stephen Berman <stephen.berman@gmx.net>,
	Daniel Fleischer <danflscr@gmail.com>,
	monnier@iro.umontreal.ca
Subject: bug#49518: 28.0.50; electric-pair-mode skip-self fails for single-quotes in python-mode
Date: Sun, 19 Sep 2021 11:44:47 +0100	[thread overview]
Message-ID: <87o88oc09s.fsf@gmail.com> (raw)
In-Reply-To: <eb92b0b4-5b89-ba7e-5547-c44aa1382ea9@gmail.com> (Jim Porter's message of "Sat, 18 Sep 2021 18:55:06 -0700")

[Stefan, I'm CC-ing you to assist with a python.el syntax propertization
bug and a patch for it at the end of this mail]

Jim Porter <jporterbugs@gmail.com> writes:

> On 9/18/2021 5:20 PM, João Távora wrote:
>> Here is the patch.  Give it a shot.
>> diff --git a/lisp/elec-pair.el b/lisp/elec-pair.el
>> index d8c377a2ef..b8b8a97651 100644
>> --- a/lisp/elec-pair.el
>> +++ b/lisp/elec-pair.el
>> @@ -198,7 +198,9 @@ electric-pair-syntax-info
>>   inside a comment or string."
>>     (let* ((pre-string-or-comment (or (bobp)
>>                                       (nth 8 (save-excursion
>> -                                             (syntax-ppss (1- (point)))))))
>> +                                             (skip-chars-backward
>> +                                              (string command-event))
>> +                                             (syntax-ppss (point))))))
>>            (post-string-or-comment (nth 8 (syntax-ppss (point))))
>>            (string-or-comment (and post-string-or-comment
>>                                    pre-string-or-comment))
>> 
>
> Thanks, this patch works for me. 
>> Maybe better less brittle solutions can probably be found within the
>> syntax tables framework.
> I agree that something less brittle would be nice, but that might be
> tricky. I had tried a few options when I filed this bug, but nothing
> worked quite right.

The point of 'electric-pair-syntax-info's STRING-OR-COMMENT-START return
value is to tell if both the current and the pre-insertion point are and
were inside a string or a comment.  It seems reasonable (i.e. not crazy)
to skip the same syntax _and_ char backwards to discover that.  Ideally
this would be remembered from before the insertion, it's true.  But
again, the fact that the patch passes all demanding tests is a good
sign: they are quite strict.  Notice, for example, that if the patch
were the seemingly also reasonable:

       (let* ((pre-string-or-comment (or (bobp)
                                         (nth 8 (save-excursion
    -                                             (skip-chars-backward
    -                                              (string command-event))
    +                                             (skip-syntax-backward
    +                                              (string (char-syntax command-event)))
                                                  (syntax-ppss (point))))))
              (post-string-or-comment (nth 8 (syntax-ppss (point))))
              (string-or-comment (and post-string-or-comment

There would be one single test failure in a ruby-mode "mixed quote"
situation.

> As for Stephen's desired behavior, the code snippet I posted above[1]
> mostly fixes it (just the `python-electric-pair-string-delimiter' part
> is necessary after your patch). However, that code doesn't work right
> if `electric-pair-skip-self' is set to nil, so I'd need to be a bit
> smarter with the implementation if I wanted to merge it into
> Emacs. Perhaps there's an even cleaner solution though.

I think the cleaner solution is to fix a bug in python.el.  Here's the
reproduction for that bug (no electric pair mode involved)

    emacs -Q something.py
    type two single quotes
    M-: (nth 3 (syntax-ppss))
    notice how the return value says you're outside a string, correctly
    type another quote
    M-: (nth 3 (syntax-ppss))
    notice how the return value says you're inside a string, correctly
    backspace the quote just entered
    M-: (nth 3 (syntax-ppss))
    notice how the return value says you're inside a string, incorrectly

When this bug is fixed, I'm confident that Stephen's case will start
working.

In fact, it's possible that if this python.el bug were fixed, we
wouldn't need the above patch at all, becasue backtracking one char into
just before the third quote of a triple quote should _also_ yield a nil
(nth 3 (syntax-ppss)).

In fact, I have tried a patch for python.el that could fix _all_ of this
(but would need some heavy testing probably):
 
     (defvar python-mode-syntax-tablediff --git a/lisp/progmodes/python.el b/lisp/progmodes/python.el
    index 19b79b6919..da7b92ae42 100644
    --- a/lisp/progmodes/python.el
    +++ b/lisp/progmodes/python.el
    @@ -775,12 +775,14 @@ python-syntax-stringify
                ;; The first quote is escaped, so it's not part of a triple quote!
                (goto-char (1+ quote-starting-pos)))
               ((null string-start)
    -           ;; This set of quotes delimit the start of a string.
    -           (put-text-property quote-starting-pos (1+ quote-starting-pos)
    +           ;; This set of quotes delimit the start of a string.  Put
    +           ;; the delimiter syntax in the last of the three quotes.
    +           (put-text-property (1- quote-ending-pos) quote-ending-pos
                                   'syntax-table (string-to-syntax "|")))
               (t
    -           ;; This set of quotes delimit the end of a string.
    -           (put-text-property (1- quote-ending-pos) quote-ending-pos
    +           ;; This set of quotes delimit the end of a string.  Put the
    +           ;; delimiter syntax in the first of the three quotess.
    +           (put-text-property quote-starting-pos (1+ quote-starting-pos)
                                   'syntax-table (string-to-syntax "|"))))))
     
     (defvar python-mode-syntax-table

João





  reply	other threads:[~2021-09-19 10:44 UTC|newest]

Thread overview: 12+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-07-11  1:32 bug#49518: 28.0.50; electric-pair-mode skip-self fails for single-quotes in python-mode Jim Porter
2021-07-11  8:11 ` Stephen Berman
2021-07-11 17:34   ` Jim Porter
2021-09-18 12:55     ` Daniel Fleischer
2021-09-18 16:56       ` Jim Porter
2021-09-18 23:43         ` João Távora
2021-09-19  0:20           ` João Távora
2021-09-19  1:55             ` Jim Porter
2021-09-19 10:44               ` João Távora [this message]
2021-09-19 16:35                 ` João Távora
2021-09-21  9:59                   ` João Távora
2021-09-22 20:04                     ` Jim Porter

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: https://www.gnu.org/software/emacs/

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=87o88oc09s.fsf@gmail.com \
    --to=joaotavora@gmail.com \
    --cc=49518@debbugs.gnu.org \
    --cc=danflscr@gmail.com \
    --cc=jporterbugs@gmail.com \
    --cc=monnier@iro.umontreal.ca \
    --cc=stephen.berman@gmx.net \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).