代码之家  ›  专栏  ›  技术社区  ›  u0b34a0f6ae

使用URLPRASE(Python)解析自定义URI

  •  13
  • u0b34a0f6ae  · 技术社区  · 15 年前

    我的应用程序创建自定义URI(或URL?)来标识对象并解析它们。问题在于Python的urlparse模块拒绝像解析http一样解析未知的URL方案。

    如果我不调整urlparse的使用列表,我会得到以下结果:

    >>> urlparse.urlparse("qqqq://base/id#hint")
    ('qqqq', '', '//base/id#hint', '', '', '')
    >>> urlparse.urlparse("http://base/id#hint")
    ('http', 'base', '/id', '', '', 'hint')
    

    以下是我所做的,我想知道是否有更好的方法:

    import urlparse
    
    SCHEME = "qqqq"
    
    # One would hope that there was a better way to do this
    urlparse.uses_netloc.append(SCHEME)
    urlparse.uses_fragment.append(SCHEME)
    

    为什么没有更好的方法?

    6 回复  |  直到 8 年前
        1
  •  22
  •   toothygoose    13 年前

    您还可以向URLPASSE注册自定义处理程序:

    import urlparse
    
    def register_scheme(scheme):
        for method in filter(lambda s: s.startswith('uses_'), dir(urlparse)):
            getattr(urlparse, method).append(scheme)
    
    register_scheme('moose')
    

    这会将您的url方案附加到列表中:

    uses_fragment
    uses_netloc
    uses_params
    uses_query
    uses_relative
    

    然后,uri将被视为类似http的,并将正确返回路径、片段、用户名/密码等。

    urlparse.urlparse('moose://username:password@hostname:port/path?query=value#fragment')._asdict()
    => {'fragment': 'fragment', 'netloc': 'username:password@hostname:port', 'params': '', 'query': 'query=value', 'path': '/path', 'scheme': 'moose'}
    
        2
  •  3
  •   Ned Batchelder    15 年前

    我认为问题在于URI在方案之后并不都有一个通用的格式。例如,mailto:url的结构与http:url不同。

    我将使用第一次解析的结果,然后合成一个http url并再次解析它:

    parts = urlparse.urlparse("qqqq://base/id#hint")
    fake_url = "http:" + parts[2]
    parts2 = urlparse.urlparse(fake_url)
    
        3
  •  3
  •   sumid    11 年前

    还有一个图书馆叫 furl 这将为您提供所需的结果:

    >>>import furl
    >>>f=furl.furl("qqqq://base/id#hint");
    >>>f.scheme
    'qqqq' 
    
    >>> f.host
    'base'  
    >>> f.path
    Path('/id')
    >>>  f.path.segments
    ['id']
    >>> f.fragment                                                                                                                                                                                                                                                                 
    Fragment('hint')   
    >>> f.fragmentstr                                                                                                                                                                                                                                                              
    'hint'
    
        4
  •  2
  •   OrangeDog    9 年前

    这个问题似乎过时了。因为至少Python2.7没有问题。

    Python 2.7.10 (default, May 23 2015, 09:40:32) [MSC v.1500 32 bit (Intel)] on win32
    >>> import urlparse
    >>> urlparse.urlparse("qqqq://base/id#hint")
    ParseResult(scheme='qqqq', netloc='base', path='/id', params='', query='', fragment='hint')
    
        5
  •  1
  •   Joe Crobak    14 年前

    >>> SCHEME="qqqq"
    >>> url="qqqq://base/id#hint"[len(SCHEME)+1:]
    >>> url
    '//base/id#hint'
    >>> urlparse.urlparse(url)
    ('', 'base', '/id', '', '', 'hint')
    

    在urlparse结果中没有该方案,但您知道该方案。

    还要注意,Python 2.6似乎可以很好地处理这个url(除了片段):

    $ python2.6 -c 'import urlparse; print urlparse.urlparse("qqqq://base/id#hint")'
    ParseResult(scheme='qqqq', netloc='base', path='/id#hint', params='', query='', fragment='')
    
        6
  •  0
  •   homm    11 年前

    你可以用 yurl 图书馆与purl或furl不同,它不会试图修复urlparse错误。它是与RFC 3986实现兼容的新版本。

    >>> import yurl
    >>> yurl.URL('qqqq://base/id#hint')
    URLBase(scheme='qqqq', userinfo=u'', host='base', port='', path='/id', query='', fragment='hint')