이전글보기
[정보/Discord Bot] - [discord.py 2.0] 11. 메세지에 버튼 추가하기
[정보/Discord Bot] - [discord.py 2.0] 12. Select 기능 추가하기
[정보/Discord Bot] - [discord.py 2.0] 13. Modal 기능으로 사용자입력창 띄우기
[정보/Discord Bot] - [discord.py 2.0] 14. 오류 발생 시 예외 처리하기
[정보/Discord Bot] - [discord.py 2.0] 15. 로또복권 정보 출력하기 (beautifulsoup4 library) - #1 사전 library 준비
이전 포스팅에서 웹사이트 파싱을 위한 라이브러리를 설치하였으니 이번 포스팅에서는 설치한 라이브러리를 이용하여 웹사이트를 파싱하는것을 해보겠습니다 !
우선 로또기능을 담당할 기본적인 lottery.py 의 기본골자를 짜줍니다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
|
import discord
from discord.ext import commands
from bs4 import BeautifulSoup
import urllib.request
class LotteryFunction:
def __init__(self):
pass
class Lottery(commands.Cog):
def __init__(self, app):
self.app = app
self.lottery = LotteryFunction()
@commands.command(name="로또")
async def lottery(self, ctx):
await ctx.send('로또호출')
async def setup(app):
await app.add_cog(Lottery(app))
|
cs |
기본적인 Cogs 클래스(Lottery) 와 로또 파싱 기능을 전담할 함수(LotteryFunction)을 추가했습니다.
3~4line은 웹페이지의 정보를 읽어오기 위해 추가한 library 입니다.
다음으로 동행복권 홈페이지에 접속하여, 최신 로또번호가 출력되는 웹페이지 주소를 확인합니다.
접속해본 결과 주소는 다음과 같습니다
https://dhlottery.co.kr/gameResult.do?method=byWin
그리고 매번 로또 정보를 받아올 때 마다 재시작 할 수는 없으니, 필요할때마다 호출할 함수(parse_newest)를 하나 추가해줍니다.
1
2
3
4
|
def parse_newest(self):
url = 'https://dhlottery.co.kr/gameResult.do?method=byWin'
webpage = urllib.request.urlopen(url)
soup = BeautifulSoup(webpage, 'html.parser')
|
cs |
def parse_newest(self):
1 : parse_newest 함수를 새로 정의합니다
url = 'https://dhlottery.co.kr/gameResult.do?method=byWin'
webpage = urllib.request.urlopen(url)
2~3 : urllib을통해 url 주소의 정보를 불러옵니다.
soup = BeautifulSoup(webpage, 'html.parser')
4 : 읽어온 url 의 정보를 BeautifulSoup 라이브러리를 통해 html로 파싱합니다.
그러면 회차별 당첨번호 페이지에 대한 html 정보가 soup 변수에 저장이 됩니다.
하지만 우리는 동행복권의 사이트에서 가져온 모든정보가 필요한게 아닙니다.
회차와 당첨번호 등, 아주 일부만 필요할 뿐이죠.
다시 동행복권 페이지에서 필요한 정보(일단은 회차)에 마우스를 갖다댄 뒤, 우클릭을 하셔서 "검사" 버튼을 눌려줍니다
그럼 우측에 창이 추가로 출력되면서 선택된 요소(element)의 html 소스코드가 바로 출력됩니다
이 요소를 다시 우클릭하여 "복사 - selector 복사" 를 클릭합니다
다시 소스코드로 돌아와서, 위 소스코드의 4line 아래에 다음 코드를 추가합니다.
lastGame = soup.select_one('div > div.win_result > h4 > strong').get_text().split("회")[0]
메소드 단위로 설명을 드리자면,
soup.select_one("복사한 selector") => soup을 통해 parsing된 html소스코드 중에서 원하는 항목을 찾습니다.
.get_text() => 찾은 항목에서 html태그를 제외하고 내부의 텍스트만 불러옵니다.
.split("회")[0] => 불러온 텍스트가 "1033회" 이므로 회차를 숫자로 저장하기 위해 "회" 글씨를 제외시킵니다.
위 와 같이 필요한 데이터들을 모두 parsing 해서 저장합니다.
포스팅에서 사용할 값들은 회차, 추첨날짜, 번호 세가지만 일단 파싱해서 출력해보겠습니다.
우선 LotteryFunction 클래스 먼저 확인해봅시다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | class LotteryFunction: def __init__(self): self.lastGameCount = None self.lastGameDate = None self.lastGameNumbers = [] self.parse_newest() # 현재 회차 정보 파싱 def parse_newest(self): url = 'https://dhlottery.co.kr/gameResult.do?method=byWin' webpage = urllib.request.urlopen(url) soup = BeautifulSoup(webpage, 'html.parser') self.lastGameCount = soup.select_one('div.win_result > h4 > strong').get_text().split("회")[0] self.lastGameDate = soup.select_one('div.win_result > p').get_text() numberList = soup.select('div.win_result > div > .num > p .ball_645') for number in numberList: self.lastGameNumbers.append(number.get_text()) | cs |
self.lastGameCount = None
self.lastGameDate = None
self.lastGameNumbers = []
3~5 : 파싱한 최근게임 정보를 저장할 변수를 멤버변수로 선언해놓습니다.
self.parse_newest()
6 : 만들어놓은 최신게임 정보 parsing 메소드를 호출합니다.
self.lastGameCount = soup.select_one('div.win_result > h4 > strong').get_text().split("회")[0]
self.lastGameDate = soup.select_one('div.win_result > p').get_text()
13~14 : 회차정보와 추첨날짜를 각각 멤버변수에 저장합니다.
numberList = soup.select('div.win_result > div > .num > p .ball_645')
for number in numberList:
self.lastGameNumbers.append(number.get_text())
15 : 당첨번호의 경우, 당첨숫자,보너스번호 모두 가져올 수 있도록 selector 를 잘 ... 입력합니다.
selector의 내용까지 설명드리기엔 너무 길어질것 같아 그대로 사용해주시면 될듯합니다.
필요시 나중에 추가로 설명드리겠습니다.
16~17 : 15line 에서 각 숫자의 요소가 배열로 numberList에 저장되는데, 이 값들을 배열로 lastGameNumbers 멤버변수에 저장해줍니다.
위처럼 해주면, 이제 LotteryFunction 클래스의 멤버변수에는 최신로또 정보가 멤버변수로 저장이 되게 되었습니다.
완료된 lottery.py 의 소스코드는 다음과 같습니다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 | import discord from discord.ext import commands from bs4 import BeautifulSoup import urllib.request class LotteryFunction: def __init__(self): self.lastGameCount = None self.lastGameDate = None self.lastGameNumbers = [] self.parse_newest() # 현재 회차 정보 파싱 def parse_newest(self): self.lastGameNumbers.clear() url = 'https://dhlottery.co.kr/gameResult.do?method=byWin' webpage = urllib.request.urlopen(url) soup = BeautifulSoup(webpage, 'html.parser') self.lastGameCount = soup.select_one('div.win_result > h4 > strong').get_text().split("회")[0] self.lastGameDate = soup.select_one('div.win_result > p').get_text() numberList = soup.select('div.win_result > div > .num > p .ball_645') for number in numberList: self.lastGameNumbers.append(number.get_text()) class Lottery(commands.Cog): def __init__(self, app): self.app = app self.lottery = LotteryFunction() @commands.command(name="로또") async def lottery(self, ctx): self.lottery.parse_newest() embed = discord.Embed(title="로또 추첨 번호", description="최근 로또 번호를 출력합니다", colour=0xffffff) embed.set_thumbnail(url="https://dhlottery.co.kr/images/layout/logo-header.png") # 데이터로부터 추첨날짜 확인 embed.add_field(name="추첨날짜", value=self.lottery.lastGameDate, inline=True) # 데이터로부터 회차 확인 embed.add_field(name="회차", value=self.lottery.lastGameCount+"회", inline=True) embed.add_field(name="추첨번호", value=self.lottery.lastGameNumbers, inline=False) await ctx.send(embed=embed) async def setup(app): await app.add_cog(Lottery(app)) | cs |
결과는 Embed로 가볍게 꾸며보았습니다..
Embed 사용법은 [정보/Discord Bot] - [discord.py 2.0] 08. Embed 꾸미기 참조 바랍니다.
포스팅에 사용된 모든 소스코드는 아래 Github에서 확인하실 수 있습니다.
https://github.com/aochfl/ChoRi_TestBot
GitHub - aochfl/ChoRi_TestBot
Contribute to aochfl/ChoRi_TestBot development by creating an account on GitHub.
github.com
참고자료
https://discord.com/developers/docs/reference - ( Discord Developer API )
https://discordpy.readthedocs.io/en/latest/index.html - ( discord.py library 문서 )
'정보 > Discord Bot' 카테고리의 다른 글
[discord.py 2.0] 15. 로또복권 정보 출력하기 - #4 데이터로부터 데이터 가공하기 (1) | 2022.09.23 |
---|---|
[discord.py 2.0] 15. 로또복권 정보 출력하기 - #3 모든 당첨내역 다운로드하기 (1) | 2022.09.21 |
[discord.py 2.0] 15. 로또복권 정보 출력하기 (beautifulsoup4 library) - #1 사전 library 준비 (0) | 2022.09.19 |
[discord.py 2.0] 14. 오류 발생 시 예외 처리하기 (0) | 2022.09.16 |
[discord.py 2.0] 13. Modal 기능으로 사용자입력창 띄우기 (0) | 2022.09.15 |