공공데이터포털의 특징은 자료를 활용을 요약하자면
1. 회원 가입 후 '사용자 인증키'를 생성해야한다.
2. 이후 원하는 데이터를 '활용 신청'을 해서 승인이 떨어지고 활용 권한을 획득해야한다. (실제 활용 가능 시간까지 약 1일 정도 소요) (파일데이터는 활용 신청 없이 그냥 다운로드 하여 사용 가능)
3. 제공되는 데이터는 파일데이터, JSON, XML 등이 있다.
1. XML이란?
eXtensible Markup Language로 태그를 이용해 데이터 구조를 기술하는 마크업 언어의 한 종류다. (한 마디로 HTML의 사촌)
따라서 requests.get으로 response를 받아온 뒤, BeautifulSoup로 xml로 바꿔 예쁘게 담아준 다음, HTML 태그 뽑아낼 때 사용했던 방식을 그대로 적용하면 된다. (find, find_all)
이 때 필요한 변수의 정보는 공공데이터포털에서 확인할 수 있다.
우선 아래로 내려보자.
이런식으로 어떤 데이터에는 어떤 키를 사용해야하는지, 그 키는 필수인지, 옵션인지를 알려준다.
(항목의 크기와 그 데이터의 샘플이 어떤지까지 보여준다.)
그리고 다시 위로 가보자. 자세한 정보는 반드시 '참고문서'를 다운 받아서 열어보도록 한다.
법정도 코드는 '행정표준코드관리시스템'에서 확인할 수 있다.
www.code.go.kr/stdcode/regCodeL.do
2. 파이썬으로 데이터 불러오기
활용 신청한 데이터를 '상세 보기'를 눌러 들어가면 '서비스URL'이라고 있다. 이것이 해당 XML로 구성된 데이터 전체의 기본 URL이다.
'상세 보기' 하단에 보면 요청 변수에 대한 예시가 있다. 위 URL에 필수 옵션을 이용해 데이터를 불러와보자.
www.openapi.molit.go.kr/OpenAPI_ToolInstallPackage/service/rest/RTMSOBJSvc/getRTMSDataSvcAptTradeDev?ServiceKey=내API키&LAWD_CD=11110&DEAL_YWD=201512
URL에 이걸 그대로 넣어야하는데 너무 기니까 가독성을 위해서 기본 URL과 파라미터를 분리시키고, 파이썬으로 합쳐서 URL을 보내보자.
xmlUrl = 'www.openapi.molit.go.kr/OpenAPI_ToolInstallPackage/service/rest/RTMSOBJSvc/getRTMSDataSvcAptTradeDev'
My_API_Key = '내API키'
queryParams = + urlencode({quote_plus(ServiceKey) : MyAPI_Key, quote_plus(LAWD_CD) : '11110', quote_plus(DEAL_YWD) : '201512'})
와 같다.
import requests, bs4
import pandas as pd
from lxml import html
from urllib.request import Request, urlopen
from urllib.parse import urlencode, quote_plus, unquote
# 1. URL 파라미터 분리하기.
# Service URL
xmlUrl = 'http://openapi.molit.go.kr/OpenAPI_ToolInstallPackage/service/rest/RTMSOBJSvc/getRTMSDataSvcAptTradeDev'
My_API_Key = unquote('sjOpJdbWHR3lhq4f8w5Dg6lc6IDZPdXeue%2BzGqY47h4Jp4sKy8SE5wKtpoHT7yfpI1NMFLyMMYHSiY4MNP6dhQ%3D%3D') # 아래 내가 받은 인증키가 안 되서 수업용 인증키 사용.
# My_API_Key = unquote('Agq7hySmyMi1FFU9kYibP%2BEnxYepQ%2FB6Dn%2Bw9lsYKVSCDjTwIdvpjmuhJrtyQrhipg3F3a4jbSq%2FLxHi%2FdUIoQ%3D%3D') # 사용자 인증키
queryParams = '?' + urlencode( # get 방식으로 쿼리를 분리하기 위해 '?'를 넣은 것이다. 메타코드 아님.
{
quote_plus('ServiceKey') : My_API_Key, # 필수 항목 1 : 서비스키 (본인의 서비스키)
quote_plus('LAWD_CD') : '11110', # 필수 항목 2 : 지역코드 (법정코드목록조회에서 확인)
quote_plus('DEAL_YMD') : '201512' # 픽수 항목 3 : 계약월
}
)
response = requests.get(xmlUrl + queryParams).text.encode('utf-8')
xmlobj = bs4.BeautifulSoup(response, 'lxml-xml')
# xmlobj # 디버깅용.
결과 :
<?xml version="1.0" encoding="utf-8"?>
<response><header><resultCode>00</resultCode><resultMsg>NORMAL SERVICE.</resultMsg></header><body><items><item><거래금액> 82,500</거래금액><건축년도>2008</건축년도><년>2015</년><도로명>사직로8길</도로명><도로명건물본번호코드>00004</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>03</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100135</도로명코드><법정동> 사직동</법정동><법정동본번코드>0009</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11500</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>광화문풍림스페이스본(101동~105동)</아파트><월>12</월><일>10</일><일련번호>11110-2203</일련번호><전용면적>94.51</전용면적><지번>9</지번><지역코드>11110</지역코드><층>11</층></item><item><거래금액> 60,000</거래금액><건축년도>1981</건축년도><년>2015</년><도로명>세종대로23길</도로명><도로명건물본번호코드>00047</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>02</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100190</도로명코드><법정동> 당주동</법정동><법정동본번코드>0145</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11700</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>롯데미도파광화문빌딩</아파트><월>12</월><일>22</일><일련번호>11110-12</일련번호><전용면적>149.95</전용면적><지번>145</지번><지역코드>11110</지역코드><층>8</층></item><item><거래금액> 130,000</거래금액><건축년도>2004</건축년도><년>2015</년><도로명>경희궁2길</도로명><도로명건물본번호코드>00005</도로명건물본번호코드><도로명건물부번호코드>00005</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>01</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100005</도로명코드><법정동> 내수동</법정동><법정동본번코드>0110</법정동본번코드><법정동부번코드>0015</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11800</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>킹스매너</아파트><월>12</월><일>8</일><일련번호>11110-118</일련번호><전용면적>194.43</전용면적><지번>110-15</지번><지역코드>11110</지역코드><층>6</층></item><item><거래금액> 105,000</거래금액><건축년도>2004</건축년도><년>2015</년><도로명>사직로8길</도로명><도로명건물본번호코드>00024</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>05</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100135</도로명코드><법정동> 내수동</법정동><법정동본번코드>0071</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11800</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>경희궁의아침2단지</아파트><월>12</월><일>14</일><일련번호>11110-115</일련번호><전용면적>124.17</전용면적><지번>71</지번><지역코드>11110</지역코드><층>8</층></item><item><거래금액> 120,000</거래금액><건축년도>2003</건축년도><년>2015</년><도로명>사직로8길</도로명><도로명건물본번호코드>00020</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>05</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100135</도로명코드><법정동> 내수동</법정동><법정동본번코드>0095</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11800</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>경희궁 파크팰리스</아파트><월>12</월><일>24</일><일련번호>11110-107</일련번호><전용면적>146.33</전용면적><지번>95</지번><지역코드>11110</지역코드><층>4</층></item><item><거래금액> 17,000</거래금액><건축년도>2014</건축년도><년>2015</년><도로명>대학로</도로명><도로명건물본번호코드>00047</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>05</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>3100002</도로명코드><법정동> 연건동</법정동><법정동본번코드>0195</법정동본번코드><법정동부번코드>0010</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>16600</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>이화에수풀</아파트><월>12</월><일>17</일><일련번호>11110-2359</일련번호><전용면적>16.98</전용면적><지번>195-10</지번><지역코드>11110</지역코드><층>8</층></item><item><거래금액> 17,000</거래금액><건축년도>2014</건축년도><년>2015</년><도로명>대학로</도로명><도로명건물본번호코드>00047</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>05</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>3100002</도로명코드><법정동> 연건동</법정동><법정동본번코드>0195</법정동본번코드><법정동부번코드>0010</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>16600</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>이화에수풀</아파트><월>12</월><일>18</일><일련번호>11110-2359</일련번호><전용면적>16.98</전용면적><지번>195-10</지번><지역코드>11110</지역코드><층>4</층></item><item><거래금액> 57,000</거래금액><건축년도>2006</건축년도><년>2015</년><도로명>혜화로3가길</도로명><도로명건물본번호코드>00030</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>01</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100544</도로명코드><법정동> 명륜1가</법정동><법정동본번코드>0019</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>17000</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>렉스빌</아파트><월>12</월><일>29</일><일련번호>11110-973</일련번호><전용면적>106.98</전용면적><지번>19</지번><지역코드>11110</지역코드><층>3</층></item><item><거래금액> 44,000</거래금액><건축년도>1995</건축년도><년>2015</년><도로명>창경궁로</도로명><도로명건물본번호코드>00265</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>07</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>3005008</도로명코드><법정동> 명륜2가</법정동><법정동본번코드>0004</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>17100</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>아남1</아파트><월>12</월><일>1</일><일련번호>11110-25</일련번호><전용면적>84.8</전용면적><지번>4</지번><지역코드>11110</지역코드><층>18</층></item><item><거래금액> 52,000</거래금액><건축년도>1995</건축년도><년>2015</년><도로명>창경궁로</도로명><도로명건물본번호코드>00265</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>07</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>3005008</도로명코드><법정동> 명륜2가</법정동><법정동본번코드>0004</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>17100</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>아남1</아파트><월>12</월><일>10</일><일련번호>11110-25</일련번호><전용면적>84.9</전용면적><지번>4</지번><지역코드>11110</지역코드><층>12</층></item></items><numOfRows>10</numOfRows><pageNo>1</pageNo><totalCount>49</totalCount></body></response>
3. 데이터 분리하기
XML 태그는 HTML 태그와 유사하지만 좀 더 간단하다. body 안에는 items 태그가 있고 그 안에는 item태그로 구성되어진다.
따라서 item 태그로 분리해보자.
rows = xmlobj.findAll('item')
# rows # 디버깅용.
결과 :
[7]:
[<item><거래금액> 82,500</거래금액><건축년도>2008</건축년도><년>2015</년><도로명>사직로8길</도로명><도로명건물본번호코드>00004</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>03</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100135</도로명코드><법정동> 사직동</법정동><법정동본번코드>0009</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11500</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>광화문풍림스페이스본(101동~105동)</아파트><월>12</월><일>10</일><일련번호>11110-2203</일련번호><전용면적>94.51</전용면적><지번>9</지번><지역코드>11110</지역코드><층>11</층></item>,
<item><거래금액> 60,000</거래금액><건축년도>1981</건축년도><년>2015</년><도로명>세종대로23길</도로명><도로명건물본번호코드>00047</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>02</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100190</도로명코드><법정동> 당주동</법정동><법정동본번코드>0145</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11700</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>롯데미도파광화문빌딩</아파트><월>12</월><일>22</일><일련번호>11110-12</일련번호><전용면적>149.95</전용면적><지번>145</지번><지역코드>11110</지역코드><층>8</층></item>,
<item><거래금액> 130,000</거래금액><건축년도>2004</건축년도><년>2015</년><도로명>경희궁2길</도로명><도로명건물본번호코드>00005</도로명건물본번호코드><도로명건물부번호코드>00005</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>01</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100005</도로명코드><법정동> 내수동</법정동><법정동본번코드>0110</법정동본번코드><법정동부번코드>0015</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11800</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>킹스매너</아파트><월>12</월><일>8</일><일련번호>11110-118</일련번호><전용면적>194.43</전용면적><지번>110-15</지번><지역코드>11110</지역코드><층>6</층></item>,
<item><거래금액> 105,000</거래금액><건축년도>2004</건축년도><년>2015</년><도로명>사직로8길</도로명><도로명건물본번호코드>00024</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>05</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100135</도로명코드><법정동> 내수동</법정동><법정동본번코드>0071</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11800</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>경희궁의아침2단지</아파트><월>12</월><일>14</일><일련번호>11110-115</일련번호><전용면적>124.17</전용면적><지번>71</지번><지역코드>11110</지역코드><층>8</층></item>,
<item><거래금액> 120,000</거래금액><건축년도>2003</건축년도><년>2015</년><도로명>사직로8길</도로명><도로명건물본번호코드>00020</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>05</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100135</도로명코드><법정동> 내수동</법정동><법정동본번코드>0095</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11800</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>경희궁 파크팰리스</아파트><월>12</월><일>24</일><일련번호>11110-107</일련번호><전용면적>146.33</전용면적><지번>95</지번><지역코드>11110</지역코드><층>4</층></item>,
<item><거래금액> 17,000</거래금액><건축년도>2014</건축년도><년>2015</년><도로명>대학로</도로명><도로명건물본번호코드>00047</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>05</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>3100002</도로명코드><법정동> 연건동</법정동><법정동본번코드>0195</법정동본번코드><법정동부번코드>0010</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>16600</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>이화에수풀</아파트><월>12</월><일>17</일><일련번호>11110-2359</일련번호><전용면적>16.98</전용면적><지번>195-10</지번><지역코드>11110</지역코드><층>8</층></item>,
<item><거래금액> 17,000</거래금액><건축년도>2014</건축년도><년>2015</년><도로명>대학로</도로명><도로명건물본번호코드>00047</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>05</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>3100002</도로명코드><법정동> 연건동</법정동><법정동본번코드>0195</법정동본번코드><법정동부번코드>0010</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>16600</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>이화에수풀</아파트><월>12</월><일>18</일><일련번호>11110-2359</일련번호><전용면적>16.98</전용면적><지번>195-10</지번><지역코드>11110</지역코드><층>4</층></item>,
<item><거래금액> 57,000</거래금액><건축년도>2006</건축년도><년>2015</년><도로명>혜화로3가길</도로명><도로명건물본번호코드>00030</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>01</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100544</도로명코드><법정동> 명륜1가</법정동><법정동본번코드>0019</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>17000</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>렉스빌</아파트><월>12</월><일>29</일><일련번호>11110-973</일련번호><전용면적>106.98</전용면적><지번>19</지번><지역코드>11110</지역코드><층>3</층></item>,
<item><거래금액> 44,000</거래금액><건축년도>1995</건축년도><년>2015</년><도로명>창경궁로</도로명><도로명건물본번호코드>00265</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>07</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>3005008</도로명코드><법정동> 명륜2가</법정동><법정동본번코드>0004</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>17100</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>아남1</아파트><월>12</월><일>1</일><일련번호>11110-25</일련번호><전용면적>84.8</전용면적><지번>4</지번><지역코드>11110</지역코드><층>18</층></item>,
<item><거래금액> 52,000</거래금액><건축년도>1995</건축년도><년>2015</년><도로명>창경궁로</도로명><도로명건물본번호코드>00265</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>07</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>3005008</도로명코드><법정동> 명륜2가</법정동><법정동본번코드>0004</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>17100</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>아남1</아파트><월>12</월><일>10</일><일련번호>11110-25</일련번호><전용면적>84.9</전용면적><지번>4</지번><지역코드>11110</지역코드><층>12</층></item>]
rows[0]을 조회해보자.
rows[0]
결과 :
<item><거래금액> 82,500</거래금액><건축년도>2008</건축년도><년>2015</년><도로명>사직로8길</도로명><도로명건물본번호코드>00004</도로명건물본번호코드><도로명건물부번호코드>00000</도로명건물부번호코드><도로명시군구코드>11110</도로명시군구코드><도로명일련번호코드>03</도로명일련번호코드><도로명지상지하코드>0</도로명지상지하코드><도로명코드>4100135</도로명코드><법정동> 사직동</법정동><법정동본번코드>0009</법정동본번코드><법정동부번코드>0000</법정동부번코드><법정동시군구코드>11110</법정동시군구코드><법정동읍면동코드>11500</법정동읍면동코드><법정동지번코드>1</법정동지번코드><아파트>광화문풍림스페이스본(101동~105동)</아파트><월>12</월><일>10</일><일련번호>11110-2203</일련번호><전용면적>94.51</전용면적><지번>9</지번><지역코드>11110</지역코드><층>11</층></item>
0번 행(rows[0])의 모든 값을 하나의 column값으로 보고 리스트에 담아보자.
# 한 개 행의 모든 컬럼값을 리스트에 담아보자.
columns = rows[0].find_all()
columns
결과 :
[<거래금액> 82,500</거래금액>,
<건축년도>2008</건축년도>,
<년>2015</년>,
<도로명>사직로8길</도로명>,
<도로명건물본번호코드>00004</도로명건물본번호코드>,
<도로명건물부번호코드>00000</도로명건물부번호코드>,
<도로명시군구코드>11110</도로명시군구코드>,
<도로명일련번호코드>03</도로명일련번호코드>,
<도로명지상지하코드>0</도로명지상지하코드>,
<도로명코드>4100135</도로명코드>,
<법정동> 사직동</법정동>,
<법정동본번코드>0009</법정동본번코드>,
<법정동부번코드>0000</법정동부번코드>,
<법정동시군구코드>11110</법정동시군구코드>,
<법정동읍면동코드>11500</법정동읍면동코드>,
<법정동지번코드>1</법정동지번코드>,
<아파트>광화문풍림스페이스본(101동~105동)</아파트>,
<월>12</월>,
<일>10</일>,
<일련번호>11110-2203</일련번호>,
<전용면적>94.51</전용면적>,
<지번>9</지번>,
<지역코드>11110</지역코드>,
<층>11</층>]
# 리스트 조회해보기
columns[0].name
결과 : '거래금액'
columns[0].text
결과 : ' 82,500'
반복문으로 만들어보자.
rowList = []
nameList = []
columnList = []
columnsLen = len(columns)
for j in range(0, columnsLen):
eachColumn = columns[j].text
columnList.append(eachColumn)
rowList.append(columnList)
이번에는 전체 데이터 값에 대해 반복문을 만들어보자. (매트릭스 리스트를 만들어보자.)
# 모든 행과 열의 값을 모아 매트릭스로 만들어보자.
rowList = []
nameList = []
columnList = []
rowsLen = len(rows)
for i in range(0, rowsLen):
columns = rows[i].find_all()
columnsLen = len(columns)
for j in range(0, columnsLen):
# 첫 번째 행 데이터 값 수집 시에만 컬럼 값을 저장한다. (어차피 rows[0], rows[1], ... 모두 컬럼헤더는 동일한 값을 가지기 때문에 매번 반복할 필요가 없다.)
if i == 0:
nameList.append(columns[j].name)
# 컬럼값은 모든 행의 값을 저장해야한다.
eachColumn = columns[j].text
columnList.append(eachColumn)
rowList.append(columnList)
columnList = [] # 다음 row의 값을 넣기 위해 비워준다. (매우 중요!!)
result = pd.DataFrame(rowList, columns=nameList)
result.head()
완성본
import requests, bs4
import pandas as pd
from lxml import html
from urllib.request import Request, urlopen
from urllib.parse import urlencode, quote_plus, unquote
# 1. URL 파라미터 분리하기.
# Service URL
xmlUrl = 'http://openapi.molit.go.kr/OpenAPI_ToolInstallPackage/service/rest/RTMSOBJSvc/getRTMSDataSvcAptTradeDev'
My_API_Key = unquote('sjOpJdbWHR3lhq4f8w5Dg6lc6IDZPdXeue%2BzGqY47h4Jp4sKy8SE5wKtpoHT7yfpI1NMFLyMMYHSiY4MNP6dhQ%3D%3D')
# My_API_Key = unquote('Agq7hySmyMi1FFU9kYibP%2BEnxYepQ%2FB6Dn%2Bw9lsYKVSCDjTwIdvpjmuhJrtyQrhipg3F3a4jbSq%2FLxHi%2FdUIoQ%3D%3D') # 사용자 인증키
queryParams = '?' + urlencode( # get 방식으로 쿼리를 분리하기 위해 '?'를 넣은 것이다. 메타코드 아님.
{
quote_plus('ServiceKey') : My_API_Key, # 필수 항목 1 : 서비스키 (본인의 서비스키)
quote_plus('LAWD_CD') : '11110', # 필수 항목 2 : 지역코드 (법정코드목록조회에서 확인)
quote_plus('DEAL_YMD') : '201512' # 픽수 항목 3 : 계약월
}
)
response = requests.get(xmlUrl + queryParams).text.encode('utf-8')
xmlobj = bs4.BeautifulSoup(response, 'lxml-xml')
# xmlobj # 디버깅용.
rows = xmlobj.findAll('item')
# rows # 디버깅용.
columns = rows[0].find_all()
# columns # 디버깅용.
# columns[0].name # 디버깅용.
# columns[0].text # 디버깅용.
# 모든 행과 열의 값을 모아 매트릭스로 만들어보자.
rowList = []
nameList = []
columnList = []
rowsLen = len(rows)
for i in range(0, rowsLen):
columns = rows[i].find_all()
columnsLen = len(columns)
for j in range(0, columnsLen):
# 첫 번째 행 데이터 값 수집 시에만 컬럼 값을 저장한다. (어차피 rows[0], rows[1], ... 모두 컬럼헤더는 동일한 값을 가지기 때문에 매번 반복할 필요가 없다.)
if i == 0:
nameList.append(columns[j].name)
# 컬럼값은 모든 행의 값을 저장해야한다.
eachColumn = columns[j].text
columnList.append(eachColumn)
rowList.append(columnList)
columnList = [] # 다음 row의 값을 넣기 위해 비워준다. (매우 중요!!)
result = pd.DataFrame(rowList, columns=nameList)
result.head()
'개발자 > Python' 카테고리의 다른 글
Python (파이썬) Matplotlib, Seaborn 시각화 (0) | 2020.05.10 |
---|---|
Python (파이썬) Seaborn DLL 에러 발생시 (0) | 2020.05.06 |
Python (파이썬) 공공데이터 수집 (Open API - JSON) (0) | 2020.05.06 |
Python (파이썬) 공공데이터 수집 (CSV 파일데이터) (0) | 2020.05.05 |
Python (파이썬) .bat 실행파일 만들기 / Crontab 크론탭 (0) | 2020.05.05 |