AttributeError: module 'urllib' has no attribute 'parse'
Asked Answered
B

3

71

python 3.5.2

code 1

import urllib
s = urllib.parse.quote('"')
print(s) 

it gave this error:

AttributeError: module 'urllib' has no attribute 'parse'

code 2

from urllib.parse import quote  
# import urllib
# s = urllib.parse.quote('"')
s = quote('"')
print(s) 

it works...

code3

from flask import Flask
# from urllib.parse import quote  
# s = quote('"')
import urllib
s = urllib.parse.quote('"')
print(s) 

it works,too. because of flask?

Why I don't have the error anymore? is it a bug ?

Bursarial answered 6/1, 2017 at 8:19 Comment(3)
You must import urllib.parse. I would assume that Flask also imports urllib.parse, and that's why your third example works.Bootblack
For some reason this works in IPython just fine but fails in a Python script. $ ipython Python 3.7.1 (default, Dec 13 2018, 11:43:05) Type 'copyright', 'credits' or 'license' for more information IPython 7.2.0 -- An enhanced Interactive Python. Type '?' for help. In [1]: import urllib In [2]: urllib.parse.quote('foo bar') Out[2]: 'foo%20bar'. I'm unsure why it works there.Partly
@Bootblack Why do we need to import urllib.parse? Why can't we just import urllib? Is this way of importing applicable to every Python3 module?Jumpy
E
48

The urllib package serves as a namespace only. There are other modules under urllib like request and parse.
For optimization importing urllib doesn't import other modules under it. Because doing so would consume processor cycles and memory, but people may not need those other modules.
Individual modules under urllib must be imported separately depending on the needs.

Try these, the first one fails but the second succeeds because when flask is imported flask itself imports urllib.parse.

python3 -c 'import urllib, sys;print(sys.modules["urllib.parse"])'
python3 -c 'import flask, sys;print(sys.modules["urllib.parse"])'
Evangelistic answered 6/1, 2017 at 9:33 Comment(1)
This was blowing my mind because I practice REPL driven development at the bpython REPL. There, importing urllib is enough to use urllib.parse.unquote. But in straight python3, thanks to this answer, I have discovered that I need to import urllib.parse. Thank you!Provoke
S
35

For code 1 to work you need to import the urllib.parse module, not the function quote. This way you can refer to the quote function with full module qualifier. With this approach you can use any function defined in the parse module:

import urllib.parse
s = urllib.parse.quote('"')
print(s)

code 2 works, because you import only the parse function and refer to it without module qualifier, since it is not imported in the context of the module. With this approach you can use only the explicitly imported function from the parse module.

code 3 works, because flask imports implicitly the urllib.parse module. The parse module becomes available in the urllib module context. Once you import urllib, urllib.parse becomes readily available and you can use it as in code 1

Shandishandie answered 6/1, 2017 at 9:58 Comment(0)
D
10

I encountered a similar issue and realized it's a version problem. So here is my solution in case it helps anyone:

# For Python 2.X
urllib.quote_plus(query)

# For Python 3.x
urllib.parse.quote_plus(query)

Reference https://github.com/schollz/playlistfromsong/issues/36

Disdainful answered 30/4, 2020 at 20:49 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.