나른한 코딩 생활

[33일차] ABC 부트캠프 프로젝트 - 3 본문

ABC 부트캠프

[33일차] ABC 부트캠프 프로젝트 - 3

GerHerMo 2024. 8. 11. 13:36

오전

작업 분담 세분화

4조의 프로젝트 체크리스트

 

어제의 피드백을 바탕으로 우리들의 역할에 대해 더욱 세분화 및 상태를 파악할 수 있도록 조장님께서 힘써 주셨다.

 

자료 수집 및 파악

한국 관광 데이터랩
차량별 탄소배출량


오후

자료 조사는 다른 팀원들이 더 힘써주었다. 그 동안 나는 직접적인 설계부분을 맡았다

 

먼저 카카오맵 API 를 발급 받은 다음 어디까지 가능한가를 알아봤다

javascript 및 html은 이번 학습 과정에 없기도 했고 지식이 없기에 거의 사용하지 않는 방향으로 잡았다

 

먼저 맵을 열고 마커로 찍어 보았다

import requests
import pandas as pd
import numpy as np
import folium
from folium.plugins import MiniMap

# 카카오 API
def elec_location(region, page_num):
    url = 'https://dapi.kakao.com/v2/local/search/keyword.json'
    params = {'query': region, 'page': page_num}
    headers = {"Authorization": "KakaoAK mykakaoAPI"} # 내 API 입력
    
    response = requests.get(url, params=params, headers=headers)
    response_json = response.json()
    places = response_json['documents']
    total = response_json['meta']['total_count']
    if total > 45:
        print(total, '개 중 45개 데이터밖에 가져오지 못했습니다!')
    else:
        print('모든 데이터를 가져왔습니다!')
    return places

def elec_info(places):
    X = []
    Y = []
    stores = []
    road_address = []
    place_url = []
    ID = []
    for place in places:
        X.append(float(place['x']))
        Y.append(float(place['y']))
        stores.append(place['place_name'])
        road_address.append(place['road_address_name'])
        place_url.append(place['place_url'])
        ID.append(place['id'])

    ar = np.array([ID, stores, X, Y, road_address, place_url]).T
    df = pd.DataFrame(ar, columns=['ID', 'stores', 'X', 'Y', 'road_address', 'place_url'])
    return df

def keywords(location_name):
    df = None
    for loca in location_name:
        for page in range(1, 4):
            local_name = elec_location(loca, page)
            local_elec_info = elec_info(local_name)

            if df is None:
                df = local_elec_info
            elif local_elec_info is None:
                continue
            else:
                df = pd.concat([df, local_elec_info], join='outer', ignore_index=True)
    return df

def make_map(dfs):
    # 지도 생성하기
    m = folium.Map(location=[36.3504119, 127.3845475],   # 기준좌표
                   zoom_start=10)

    # 미니맵 추가하기
    minimap = MiniMap()
    m.add_child(minimap)

    # 마커 추가하기
    for i in range(len(dfs)):
        folium.Marker([float(dfs['Y'][i]), float(dfs['X'][i])],
                      tooltip=dfs['stores'][i],
                      popup=dfs['place_url'][i],
                      ).add_to(m)
    return m

location = ['대동역 7번출구', '한밭대학교']
df = keywords(location)
df = df.drop_duplicates(['ID'])
df = df.reset_index(drop=True)

map_object = make_map(df)
map_object.save('map.html')

map_html 파일 / 각각 한밭대학교, 대동역 7번출구를 검색하여 마커로 표시

 

이번에는 각각의 목적지를 이어주는 코드를 작성했다

import requests
import pandas as pd
import numpy as np
import folium
from folium.plugins import MiniMap

# 카카오 API
def elec_location(region, page_num):
    url = 'https://dapi.kakao.com/v2/local/search/keyword.json'
    params = {'query': region, 'page': page_num}
    headers = {"Authorization": "KakaoAK maykakaoAPI"}

    response = requests.get(url, params=params, headers=headers)
    response_json = response.json()
    places = response_json['documents']
    total = response_json['meta']['total_count']
    if total > 45:
        print(total, '개 중 45개 데이터밖에 가져오지 못했습니다!')
    else:
        print('모든 데이터를 가져왔습니다!')
    return places

def elec_info(places):
    X = []
    Y = []
    stores = []
    road_address = []
    place_url = []
    ID = []
    for place in places:
        X.append(float(place['x']))
        Y.append(float(place['y']))
        stores.append(place['place_name'])
        road_address.append(place['road_address_name'])
        place_url.append(place['place_url'])
        ID.append(place['id'])

    ar = np.array([ID, stores, X, Y, road_address, place_url]).T
    df = pd.DataFrame(ar, columns=['ID', 'stores', 'X', 'Y', 'road_address', 'place_url'])
    return df

def keywords(location_name):
    df = None
    for loca in location_name:
        for page in range(1, 4):
            local_name = elec_location(loca, page)
            local_elec_info = elec_info(local_name)

            if df is None:
                df = local_elec_info
            elif local_elec_info is None:
                continue
            else:
                df = pd.concat([df, local_elec_info], join='outer', ignore_index=True)
    return df

def make_map(dfs, start, end):
    # 지도 생성하기
    m = folium.Map(location=[33.4935, 126.6266],   # 기준좌표: 제주어딘가로 내가 대충 설정
                   zoom_start=12)

    # 미니맵 추가하기
    minimap = MiniMap()
    m.add_child(minimap)

    # 마커 추가하기
    for i in range(len(dfs)):
        folium.Marker([float(dfs['Y'][i]), float(dfs['X'][i])],
                      tooltip=dfs['stores'][i],
                      popup=dfs['place_url'][i],
                      icon=folium.Icon(color='blue')
                      ).add_to(m)

    # 출발지와 목적지 추가하기
    folium.Marker(start, tooltip='출발지', icon=folium.Icon(color='green')).add_to(m)
    folium.Marker(end, tooltip='목적지', icon=folium.Icon(color='red')).add_to(m)

    # 출발지와 목적지 연결하기
    folium.PolyLine(locations=[start, end], color='red', weight=2.5, opacity=1).add_to(m)

    return m

location = ['대동역 7번 출구', '목포시 갓바위']
df = keywords(location)
df = df.drop_duplicates(['ID'])
df = df.reset_index(drop=True)

# 출발지와 목적지 설정
start = [33.4607, 126.9364]  # 예시 좌표 (출발지)
end = [33.5097, 126.4913]    # 예시 좌표 (목적지)

map_object = make_map(df, start, end)
map_object.save('map_start_arrive.html')

출발지, 목적지의 좌표는 제주도의 임의의 장소 2개를 설정, 나머지는 마커로 표시됨

 

하지만 이러한 동적 지도로는 현재의 앱에 사용할 지도와는 방향성이 많이 다르기 때문에 웹 크롤링을 통한 맵 사용으로 계획을 변경하였다.

import time
from selenium import webdriver
from selenium.webdriver.chrome.service import Service
from webdriver_manager.chrome import ChromeDriverManager

def create_map_url(latitude, longitude, name=None):
    base_url = "https://map.kakao.com/link/map/"
    if name:
        url = f"{base_url}{name},{latitude},{longitude}"
    else:
        url = f"{base_url}{latitude},{longitude}"
    return url

def create_directions_url(latitude, longitude, name=None):
    base_url = "https://map.kakao.com/link/to/"
    if name:
        url = f"{base_url}{name},{latitude},{longitude}"
    else:
        url = f"{base_url}{latitude},{longitude}"
    return url

# 예시 사용 < - 해당 부분을 여행지로 변경
# https://deveapp.com/map.php <- 위도 경도 변환 사이트
latitude = 34.7921469527007
longitude = 126.425695326
name = "목포갓바위"

map_url = create_map_url(latitude, longitude, name)
directions_url = create_directions_url(latitude, longitude, name)

# Selenium을 사용하여 Chrome으로 URL 열기
driver = webdriver.Chrome(service=Service(ChromeDriverManager().install()))

# 첫 번째 URL 열기
# driver.get(map_url)
# time.sleep(5)

# 두 번째 URL ( 목적지 ) 열기
driver.get(directions_url)
driver.implicitly_wait(10)
time.sleep(5)


input("Press Enter to close the browser...")
driver.quit()

 

해당 코드를 실행하면 목적지로 찍힌 '목포 갓바위' 카카오맵 페이지가 실행된다