Python 3 웹 스크랩에서 HTTP 오류 403


100

연습을 위해 웹 사이트를 스크랩하려고했지만 계속해서 HTTP 오류 403 (내가 봇이라고 생각합니까?)이 표시됩니까?

내 코드는 다음과 같습니다.

#import requests
import urllib.request
from bs4 import BeautifulSoup
#from urllib import urlopen
import re

webpage = urllib.request.urlopen('http://www.cmegroup.com/trading/products/#sortField=oi&sortAsc=false&venues=3&page=1&cleared=1&group=1').read
findrows = re.compile('<tr class="- banding(?:On|Off)>(.*?)</tr>')
findlink = re.compile('<a href =">(.*)</a>')

row_array = re.findall(findrows, webpage)
links = re.finall(findlink, webpate)

print(len(row_array))

iterator = []

내가 얻는 오류는 다음과 같습니다.

 File "C:\Python33\lib\urllib\request.py", line 160, in urlopen
    return opener.open(url, data, timeout)
  File "C:\Python33\lib\urllib\request.py", line 479, in open
    response = meth(req, response)
  File "C:\Python33\lib\urllib\request.py", line 591, in http_response
    'http', request, response, code, msg, hdrs)
  File "C:\Python33\lib\urllib\request.py", line 517, in error
    return self._call_chain(*args)
  File "C:\Python33\lib\urllib\request.py", line 451, in _call_chain
    result = func(*args)
  File "C:\Python33\lib\urllib\request.py", line 599, in http_error_default
    raise HTTPError(req.full_url, code, msg, hdrs, fp)
urllib.error.HTTPError: HTTP Error 403: Forbidden

답변:


206

이것은 아마도 때문이다 mod_security(블록 거미 / 봇 사용자 에이전트 알려진 몇 가지 유사한 서버 보안 기능 또는 urllib같이 사용 무언가 python urllib/3.3.0그것을 쉽게 감지 것). 다음을 사용하여 알려진 브라우저 사용자 에이전트를 설정해보십시오.

from urllib.request import Request, urlopen

req = Request('http://www.cmegroup.com/trading/products/#sortField=oi&sortAsc=false&venues=3&page=1&cleared=1&group=1', headers={'User-Agent': 'Mozilla/5.0'})
webpage = urlopen(req).read()

이것은 나를 위해 작동합니다.

그건 그렇고, 당신의 코드에서 당신은 누락 ()후 .read의를urlopen 라인,하지만 난 그게 오타가 있다고 생각합니다.

팁 : 이것은 운동이므로 다른 비 제한적인 사이트를 선택하십시오. urllib왠지 막고 있을지도 ...


req여러 urlopen호출 에 재사용 하는 것이 안전하다고 가정 합니다.
— Acumenus

그것은 조금 늦게 될 수도 있지만 나는 이미 내 코드에서 사용자 에이전트가, 여전히 나에게 준다Error 404: Access denied
— Reema Parakh

그들은 블록 봇에 좋은 이유가 있어야합니다 같은이 작품은 그러나 나는 느낌이 나는 서비스 약관을 위반하고있어
— xjcl

39

확실히 사용자 에이전트를 기반으로 urllib를 사용하기 때문에 차단됩니다. OfferUp에서도 이와 똑같은 일이 발생합니다. Mozilla로 사용자 에이전트를 재정의하는 AppURLopener라는 새 클래스를 만들 수 있습니다.

import urllib.request

class AppURLopener(urllib.request.FancyURLopener):
    version = "Mozilla/5.0"

opener = AppURLopener()
response = opener.open('http://httpbin.org/user-agent')

출처


2
귀하의 답변은 저에게 효과적이지 않았습니다. 감사합니다!
— Tarun Uday

이것은 잘 작동하지만 SSL 구성을 여기에 연결해야합니다. 어떻게해야합니까? 두 번째 매개 변수 (urlopen (request, context = ctx))로 추가하기 전에
— Hauke

2
열린 것처럼 보이지만 'ValueError : read of closed file'이라고 표시됩니다.
— Martian2049

@zeta OfferUp을 스크랩하고 스크립트에서 검색을 수행하는 데 필요한 지리적 좌표를 어떻게 제공 했습니까?
— CJ Travis

@CJTravis, OfferUp을 긁지 않았습니다. 항목의 정확한 URL을 기반으로 항목 값을 검색했습니다. 그것은 나를 위해 어떤 지리적 좌표도 필요하지 않았습니다
— zeta

13

"이것은 아마도 mod_security 또는 알려진 것을 차단하는 유사한 서버 보안 기능 때문일 것입니다.

거미 / 봇

사용자 에이전트 (urllib는 python urllib / 3.3.0과 같은 것을 사용하며 쉽게 감지 됨) "-이미 Stefano Sanfilippo에서 언급했듯이

from urllib.request import Request, urlopen
url="https://stackoverflow.com/search?q=html+error+403"
req = Request(url, headers={'User-Agent': 'Mozilla/5.0'})

web_byte = urlopen(req).read()

webpage = web_byte.decode('utf-8')

web_byte는 서버와 웹 페이지의 콘텐츠 형식 존재에 의해 반환 된 바이트 객체 인 대부분이다 UTF-8 . 따라서 디코딩 방법을 사용하여 web_byte 를 디코딩 해야합니다 .

이것은 PyCharm을 사용하여 웹 사이트에서 스크랩을 시도하는 동안 완전한 문제를 해결합니다.

추신-> 파이썬 3.4를 사용합니다.


1

페이지가 브라우저에서 작동하고 파이썬 프로그램 내에서 호출 할 때 작동하지 않기 때문에 해당 URL 을 제공하는 웹 앱이 은 브라우저가 아닌 콘텐츠를 요청한 것으로 인식하는 .

데모:

curl --dump-header r.txt http://www.cmegroup.com/trading/products/#sortField=oi&sortAsc=false&venues=3&page=1&cleared=1&group=1

...
<HTML><HEAD>
<TITLE>Access Denied</TITLE>
</HEAD><BODY>
<H1>Access Denied</H1>
You don't have permission to access ...
</HTML>

r.txt의 내용에는 상태 줄이 있습니다.

HTTP/1.1 403 Forbidden

웹 클라이언트 를 위조 하는 'User-Agent'헤더를 게시 해보세요 .

참고 : 페이지에는 구문 분석하려는 테이블을 생성하는 Ajax 호출이 포함되어 있습니다. 페이지의 자바 스크립트 로직을 확인하거나 단순히 브라우저 디버거 (예 : Firebug / Net 탭)를 사용하여 테이블의 콘텐츠를 가져 오기 위해 호출해야하는 URL을 확인해야합니다.


1

두 가지 방법으로 시도 할 수 있습니다. 자세한 내용은이 링크에 있습니다.

1) 핍을 통해

pip 설치-인증서 업그레이드

2) 작동하지 않으면 Mac 용 Python 3. *에 번들로 제공되는 Cerificates.command 를 실행 해보십시오 . (python 설치 위치로 이동하여 파일을 두 번 클릭하십시오)

/ Applications / Python \ 3. * / Install \ Certificates.command를 엽니 다.


1

이전 답변에 따르면

from urllib.request import Request, urlopen       
#specify url
url = 'https://xyz/xyz'
req = Request(url, headers={'User-Agent': 'XYZ/3.0'})
response = urlopen(req, timeout=20).read()

이것은 시간 제한을 연장하여 나를 위해 일했습니다.


0

사용자 에이전트를 Mozilla (Stefano의 최상위 답변에있는 주석)로 위장하는 것에 대해 죄책감을 느끼면 비 urllib 사용자 에이전트에서도 작동 할 수 있습니다. 이것은 내가 참조하는 사이트에서 작동했습니다.

    req = urlrequest.Request(link, headers={'User-Agent': 'XYZ/3.0'})
    urlrequest.urlopen(req, timeout=10).read()

내 응용 프로그램은 내 기사에서 참조하는 특정 링크를 스크랩하여 유효성을 테스트하는 것입니다. 일반 스크레이퍼가 아닙니다.


0

이전 답변을 기반으로 이것은 Python 3.7에서 저에게 효과적이었습니다.

from urllib.request import Request, urlopen

req = Request('Url_Link', headers={'User-Agent': 'XYZ/3.0'})
webpage = urlopen(req, timeout=10).read()

print(webpage)
당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.