XML API를 파이썬에서 처리할 때 핵심은 데이터를 dict처럼 접근하는 게 아니라, 태그를 찾아 들어가는 방식으로 접근해야 한다는 것이다.
이때 가장 많이 쓰는 도구가 BeautifulSoup이고, 특히 find()와 find_all()의 차이를 이해하는 것이 XML 파싱의 기본이다.
XML은 태그 중심 구조다
JSON이 key-value 구조라면,
XML은 <tag>value</tag> 형태의 태그 구조다.
예시:
<movie>
<movieCd>123</movieCd>
<movieNm>영화이름</movieNm>
</movie>
이 구조에서는 "movieCd" 같은 key 접근이 아니라,
👉 movieCd 태그를 찾아야 한다
BeautifulSoup로 XML 파싱하기
XML 응답을 그대로 쓰는 게 아니라, 먼저 파싱해야 한다.
import urllib.request
from bs4 import BeautifulSoup
url = "<http://www.kobis.or.kr/kobisopenapi/webservice/rest/movie/searchMovieList.xml?key=발급받은_개인키&itemPerPage=50>"
res = urllib.request.urlopen(url)
soup = BeautifulSoup(res, "xml")
👉 핵심
- "xml" 파서 사용
- 이후는 전부 태그 기반 탐색
find vs find_all 핵심 차이
이 부분이 가장 중요하다.
함수 결과
| find() | 첫 번째 태그 하나 |
| find_all() | 모든 태그 리스트 |
find 사용
soup.find("movie")
- 첫 번째 <movie>만 반환
- 단일 객체
find_all 사용
soup.find_all("movie")
- 모든 <movie> 반환
- 리스트 형태
왜 find_all이 더 많이 쓰일까
실전에서는 대부분 여러 데이터(row)를 반복 처리해야 한다.
movies = soup.find_all("movie")
이렇게 받은 뒤 반복문을 돌린다.
👉 즉, DataFrame 만들려면 거의 무조건 find_all
실제 데이터 추출 흐름
KOBIS XML 구조 기준으로 보면:
movie_list = []
for data in soup.find_all("movie"):
movie_cd = data.find("movieCd").text
movie_nm = data.find("movieNm").text
movie_nm_en = data.find("movieNmEn").text
open_dt = data.find("openDt").text
movie_list.append([movie_cd, movie_nm, movie_nm_en, open_dt])
👉 핵심 패턴
find_all → 반복문 → find → .text
감독 정보 추출 (중요 포인트)
XML에서도 중첩 구조가 있다.
<directors>
<director>
<peopleNm>감독이름</peopleNm>
</director>
</directors>
이 경우 이렇게 접근한다.
if data.find_all("peopleNm") != []:
director = data.find("peopleNm").text
else:
director = ""
👉 JSON이랑 똑같이 빈 값 예외 처리 필요
find의 단점 (실전에서 중요)
find()는 태그가 없을 때 문제가 생긴다.
- None 반환
- .text 접근 시 에러 가능
반면 find_all()은:
[]
👉 빈 리스트 반환
그래서 조건 처리하기 쉽다.
find vs find_all 사용 기준
find
- 단일 값이 확실할 때
- 구조가 고정일 때
find_all
- 반복 처리할 때
- 데이터 개수가 여러 개일 때
- 예외 처리까지 고려할 때
👉 실전에서는 대부분 find_all + 반복문
XML → DataFrame 변환
import pandas as pd
df = pd.DataFrame(movie_list, columns=[
"movieCd", "movieNm", "movieNmEn", "openDt"
])
print(df.head())
구현 관점 핵심 포인트
1. XML은 dict처럼 접근 안 된다
→ 무조건 태그 기반 접근
2. find_all → 반복문 구조가 기본
for data in soup.find_all("movie")
3. .text로 값 추출
data.find("movieCd").text
4. 빈 태그 예외 처리 필요
if data.find_all("peopleNm") != []
5. JSON보다 DataFrame 변환이 번거롭다
→ 직접 구조를 풀어줘야 함
XML 파싱은 dict 접근이 아니라, find_all → find → text 흐름으로 태그를 찾아가며 데이터를 추출하는 방식이다.
'Data Analytics > 수집·크롤링' 카테고리의 다른 글
| API 데이터 수집할 때 샘플 단위로 처리해야 하는 이유 | 열 단위 수집이 위험한 이유 (0) | 2026.05.08 |
|---|---|
| BeautifulSoup HTML 파싱 정리 | 일반 웹사이트에서 태그와 속성으로 데이터 추출하는 방법 (1) | 2026.05.08 |
| JSON과 XML 차이 정리 | API 응답 포맷에 따라 파이썬 처리 방식이 달라지는 이유 (0) | 2026.05.07 |
| requests.get 정리 | params로 API URL 깔끔하게 보내는 방법 (0) | 2026.05.07 |
| JSON 데이터를 Pandas DataFrame으로 바꾸는 방법 | 리스트와 딕셔너리 구조 정리 (0) | 2026.05.06 |
