Chapter 4 노선 버스의 실시간 위치 확인

data.go.kr의 Open API 활용 방법을 학습하기 위해, 두 번째로 서울시에서 운행중인 버스의 실시간 위치 정보 조회 방법을 알아보기로 한다.

(버스위치정보조회 서비스 Open API 활용가이드 P. 8 참고)

패키지 불러오기

library(XML)
library(ggmap)
library(tidyverse)

4.1 특정 노선의 실시간 위치

먼저 Open API를 사용하기 위해 data.go.kr에서 발급받은 API Key를 인증받는다.

4.1.1 API Key 인증받기

API_key <- "XNamCEPA1y........w2oz2Hqld26g%3D%3D"               
# data.go.kr에서 발급받은 API_key 입력

4.1.2 실시간 버스 위치 정보 조회

(버스위치정보조회 서비스 Open API 활용가이드 P. 8 참고)

4.1.2.1 조회할 노선 ID

노선번호(busRtNm)를 공란으로 한다. 즉, 서울시에 운행중인 모든 노선정보를 조회한다.

busRtNm <- busID                      # 검색할 노선버스 번호를 빈문자로 정한다. 

4.1.2.2 노선정보 조회 서비스 URL

노선정보조회 서비스 url을 입력한다.

url <- "http://ws.bus.go.kr/api/rest/buspos/getBusPosByRtid?ServiceKey="
srch_url <- paste(url, API_key, "&busRouteId=", busRtNm, sep= "")

4.1.2.3 실시간 위치 정보 조회

xmlParse() 함수를 이용하여 실시간 위치 정보 데이터를 다운로드하여, xmlfile에 대입한다.

xmlfile <- xmlParse(srch_url)      # 해당 url에 데이터를 요구(request)하고, 
                                   # 그 결과(response)를 xmlfile 변수에 저장한다.
# xmlRoot(xmlfile)                 # xmlfile 변수의 내용을 출력한다. 

4.1.2.4 조회한 정보를 데이터 프레임 형태로 변환

xmlToDataFrmae() 함수를 이용하여, xmlfile을 데이터 프레임 형태로 변환하여 df 변수에 대입한다.

이제 df 변수는 노선 ID가 100100063인 노선의 운행 중인 버스들의 실시간 위치 정보를 담고 있다.

df <- xmlToDataFrame(getNodeSet(xmlfile, "//itemList"))
str(df)
## 'data.frame':    16 obs. of  23 variables:
##  $ busType     : chr  "1" "1" "1" "1" ...
##  $ congetion   : chr  "0" "0" "3" "3" ...
##  $ dataTm      : chr  "20201206210916" "20201206210912" "20201206210856" "20201206210900" ...
##  $ fullSectDist: chr  "0.576" "0.972" "2.97" "0.424" ...
##  $ gpsX        : chr  "127.131748" "127.104033" "127.077381" "127.059167" ...
##  $ gpsY        : chr  "37.481563" "37.485382" "37.482695" "37.492735" ...
##  $ isFullFlag  : chr  "0" "0" "0" "0" ...
##  $ islastyn    : chr  "0" "0" "0" "0" ...
##  $ isrunyn     : chr  "1" "1" "1" "1" ...
##  $ lastStTm    : chr  "10477" "9701" "9309" "8246" ...
##  $ lastStnId   : chr  "123000372" "122000718" "122000278" "122000124" ...
##  $ nextStId    : chr  "122000297" "122000297" "122000250" "122000214" ...
##  $ nextStTm    : chr  "920" "143" "352" "402" ...
##  $ plainNo     : chr  "서울70사9585" "서울70사9583" "서울70사9565" "서울70사9582" ...
##  $ posX        : chr  "211651.24601290378" "209199.77741288094" "206843.1500228184" "205231.70362587066" ...
##  $ posY        : chr  "442472.1744005908" "442892.91876124544" "442592.4585516141" "443705.47902125027" ...
##  $ rtDist      : chr  "56.21" "56.21" "56.21" "56.21" ...
##  $ sectDist    : chr  "0.04" "0.18" "0.409" "0.026" ...
##  $ sectOrd     : chr  "3" "12" "18" "27" ...
##  $ sectionId   : chr  "123605062" "122606586" "122606508" "122605652" ...
##  $ stopFlag    : chr  "1" "0" "0" "1" ...
##  $ trnstnid    : chr  "101900006" "101900006" "101900006" "101900006" ...
##  $ vehId       : chr  "123053266" "123053347" "123053485" "123053346" ...
  • 100100063 노선 버스들의 실시간 위치 정보를 보여 준다. 현재 26대의 버스가 운행 중이다.
  • 컬럼의 갯수는 26개 : 이들에 대한 자세한 내용은 “버스 노선정보조회 서비스 Open API 활용가이드 P. 13 참고”

4.1.2.5 분석용 데이터 세트 생성

다운 받은 정보 중 gpsX, gpsY, 그리고 plainNo 컬럼 만을 선택하여 data에 대입한다.

  • plainNo : 차량 번호판 => 문자형 데이터
  • gpsX : 경도 => 문자형 데이터를 숫자형으로 변환 => 컬럼명을 lon으로 변경
  • gpsY : 위도 => 문자형 데이터를 숫자형으로 변환 => 컬럼명을 lat으로 변경
gpsX <- as.numeric(df$gpsX)
gpsY <- as.numeric(df$gpsY)

df_location <- data.frame(plainNo = df$plainNo, lon = gpsX, lat = gpsY)
head(df_location)
##        plainNo      lon      lat
## 1 서울70사9585 127.1317 37.48156
## 2 서울70사9583 127.1040 37.48538
## 3 서울70사9565 127.0774 37.48269
## 4 서울70사9582 127.0592 37.49274
## 5 서울70사9580 127.0295 37.49433
## 6 서울70사9563 127.0035 37.54158

4.1.2.6 데이터 세트의 저장

write_rds(df_location, "data/df-location.rds")