Skip to content

Commit ac5d5a0

Browse files
ephphathaorsenthil
authored andcommitted
Allow passing a Request instance for the url parameter
1 parent 639a552 commit ac5d5a0

2 files changed

Lines changed: 65 additions & 1 deletion

File tree

Lib/test/test_robotparser.py

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -773,6 +773,65 @@ def testServiceUnavailable(self):
773773
self.assertFalse(parser.can_fetch("*", url + '/path/file.html'))
774774

775775

776+
class UserAgentRobotHandler(BaseHTTPRequestHandler):
777+
778+
def do_GET(self):
779+
if self.headers.get('User-Agent').startswith('Python-urllib'):
780+
self.send_error(403, "Forbidden access")
781+
else:
782+
self.send_response(200)
783+
self.end_headers()
784+
self.wfile.write(b"User-agent: *\nDisallow:")
785+
786+
def log_message(self, format, *args):
787+
pass
788+
789+
790+
@unittest.skipUnless(
791+
support.has_socket_support,
792+
"Socket server requires working socket."
793+
)
794+
class UserAgentSiteTestCase(unittest.TestCase):
795+
796+
def setUp(self):
797+
# clear _opener global variable
798+
self.addCleanup(urllib.request.urlcleanup)
799+
800+
self.server = HTTPServer((socket_helper.HOST, 0), UserAgentRobotHandler)
801+
802+
self.t = threading.Thread(
803+
name='HTTPServer serving',
804+
target=self.server.serve_forever,
805+
# Short poll interval to make the test finish quickly.
806+
# Time between requests is short enough that we won't wake
807+
# up spuriously too many times.
808+
kwargs={'poll_interval':0.01})
809+
self.t.daemon = True # In case this function raises.
810+
self.t.start()
811+
812+
def tearDown(self):
813+
self.server.shutdown()
814+
self.t.join()
815+
self.server.server_close()
816+
817+
@threading_helper.reap_threads
818+
def testUserAgentFilteringSite(self):
819+
addr = self.server.server_address
820+
url = 'http://' + socket_helper.HOST + ':' + str(addr[1])
821+
robots_url = url + "/robots.txt"
822+
file_url = url + "/document"
823+
parser = urllib.robotparser.RobotFileParser()
824+
parser.set_url(robots_url)
825+
parser.read()
826+
self.assertTrue(parser.disallow_all)
827+
self.assertFalse(parser.can_fetch("*", file_url))
828+
parser = urllib.robotparser.RobotFileParser()
829+
parser.set_url(urllib.request.Request(robots_url, headers={'User-Agent': 'cybermapper'}))
830+
parser.read()
831+
self.assertFalse(parser.disallow_all)
832+
self.assertTrue(parser.can_fetch("*", file_url))
833+
834+
776835
@support.requires_working_socket()
777836
class NetworkTestCase(unittest.TestCase):
778837

Lib/urllib/robotparser.py

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,12 @@ def modified(self):
5757
def set_url(self, url):
5858
"""Sets the URL referring to a robots.txt file."""
5959
self.url = url
60-
self.host, self.path = urllib.parse.urlsplit(url)[1:3]
60+
61+
if isinstance(url, urllib.request.Request):
62+
self.host = url.host
63+
self.path = url.selector
64+
else:
65+
self.host, self.path = urllib.parse.urlparse(url)[1:3]
6166

6267
def read(self):
6368
"""Reads the robots.txt URL and feeds it to the parser."""

0 commit comments

Comments
 (0)