fgallina / python.el

Python's flying circus support for Emacs
GNU General Public License v3.0
267 stars 53 forks source link

Clash with goto-address-prog-mode #131

Closed purcell closed 11 years ago

purcell commented 11 years ago

Hi! I like to use goto-address-prog-mode to make links inside comments/strings clickable. However, python.el's fontification sometimes breaks. In the snippet below, goto-address-prog-mode causes fontification of the triple-quoted string to extend down into the __init__ function.

The code in goto-addr looks broadly reasonable -- any idea what might be causing this clash?

(This is with the python.el and goto-addr.el shipped with recent Emacs HEAD snapshots.)

-Steve

class PageGrabber:
    """Grabs content of pages on sites for which a log-in is required.

    Register log-ins for known sites using the register_login() method,
    then use open_url() or save_url_as() to retrieve or save pages for
    which log-ins are required:

      >>> from pagegrab import PageGrabber
      >>> grabber = PageGrabber()
      >>> grabber.register_login('myphotosite.com', 'http://www.myphotosite.com/login', 'logged in', {'login':'whoever', 'password':'topsecret'})
      >>> grabber.save_url_as('http://www.myphotosite.com/edit_gallery/32', '/tmp/gallery32')

    If multiple pages are requested from one site, only one log-in will be
    made.  Works only with cookie-based log-ins; sites such as Amazon that
    encode session IDs into URLs are not supported.
    """

    def __init__(self):
        self.known_domains = {}
        self.logged_into_domains = {}
fgallina commented 11 years ago

I feel there's something else needed in this recipe, since a file with only those contents and enabling goto-address-prog-mode is not replicating it.

purcell commented 11 years ago

Hmm, yes. Let me see if I can clarify the recipe for reproducing the misbehaviour...

purcell commented 11 years ago

Okay, here's a working recipe.

Fire up an emacs -Q, then eval the following in *scratch*:

(add-hook 'prog-mode-hook 'goto-address-prog-mode)

Now open a new file, /tmp/p.py, and paste in the following:

#!/usr/bin/env python
"""
Retrieves and saves HTML content from password-protected sites.
"""

import urllib, urllib2, urlparse, re, sys, os
sys.path.insert(0, 'ClientCookie-0.9.4a')
import ClientCookie

class LoginError(Exception):
    pass

class PageGrabber:
    """Grabs content of pages on sites for which a log-in is required.

    Register log-ins for known sites using the register_login() method,
    then use open_url() or save_url_as() to retrieve or save pages for
    which log-ins are required:

      >>> from pagegrab import PageGrabber
      >>> grabber = PageGrabber()
      >>> grabber.register_login('myphotosite.com', 'http://www.myphotosite.com/login', 'logged in', {'login':'whoever', 'password':'topsecret'})
      >>> grabber.save_url_as('http://www.myphotosite.com/edit_gallery/32', '/tmp/gallery32')

    If multiple pages are requested from one site, only one log-in will be
    made.  Works only with cookie-based log-ins; sites such as Amazon that
    encode session IDs into URLs are not supported.
    """

    def __init__(self):
        self.known_domains = {}
        self.logged_into_domains = {}

    def register_login(self, domain, login_url, confirmation_pattern, form_fields):
        """Store the log-in details for a particular site.

          domain               -> The domain for which the log-in is valid
          login_url            -> The URL that the log-in form posts to (see
                                  the 'action' attribute of the <form> tag)
          confirmation_pattern -> A regular expression string that matches
                                  something found in the page displayed after a
                                  successful log-in (e.g. 'Logout')
          form_fields          -> The parameters values that are passed from
                                  the login form to the URL it posts to (see
                                  the <input> tags in the login <form>)
        """
        confirmation_pattern = re.compile(confirmation_pattern)
        self.known_domains[domain] = (login_url, confirmation_pattern, form_fields)
fgallina commented 11 years ago

The recipe is good and I'm able to replicate this, unfortunately syntax-propertize stuff is hard and wasn't able to find a quick solution right-away. My hope is to be able put this fix before Emacs 24.3 is released.

fgallina commented 11 years ago

Stefan Monnier fixed this bug in the emacs-24 bzr branch at revno 111263.

This bug was a goto-address-prog-mode thing.

purcell commented 11 years ago

Great news -- thanks for following up!

-Steve