개발공작소
article thumbnail
728x90

요즘 계속 API만 하고 있는데, 여러번 써봐야 몸에 밸 것 같아서.. 계속 한번 해보자.

저번에는 그냥 데이터를 보내 카카오 API호출을 해서 데이터를 받아 오는 것만 했는데, 이번에는

카카오에서 지원하는 주소검색을 한번 해보자.

 

우선 자세한 가이드는 아래 링크에서 확인 가능하다.

https://postcode.map.daum.net/guide

 

Daum 우편번호 서비스

우편번호 검색과 도로명 주소 입력 기능을 너무 간단하게 적용할 수 있는 방법. Daum 우편번호 서비스를 이용해보세요. 어느 사이트에서나 무료로 제약없이 사용 가능하답니다.

postcode.map.daum.net

이런 느낌의 주소창을 이용하여 주소검색을 하고 데이터를 가져올 수 있다. 깔끔한 주소창... 실제 프로젝트에서

활용하면 더 좋을 것 같다. 그럼 바로 주소검색 API를 활용하여 구현해보자.

 

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>카카오 주소검색</title>
<script src="//t1.daumcdn.net/mapjsapi/bundle/postcode/prod/postcode.v2.js"></script>
<script type="text/javascript">
	new daum.Postcode({
	    oncomplete: function(data) {
	        // 팝업에서 검색결과 항목을 클릭했을때 실행할 코드를 작성하는 부분입니다.
	        // 예제를 참고하여 다양한 활용법을 확인해 보세요.
	        console.log(data);
	    }
	}).open();
</script>
</head>
<body>
</body>
</html>

우선 위와 같이 <script>만 넣어주고 실행하면 바로 팝업창이 뜨고 주소 검색도 가능하다.

 

그리고 저번에 배웠던 검색 API를 활용하면 X좌표, Y좌표도 가져 올수 있다. 아래와 같이 oncomplete함수 안에

axios를 통해 API를 호출하면 된다.

 

<script type="text/javascript">
	new daum.Postcode({
	    oncomplete: function(data) {
	        // 팝업에서 검색결과 항목을 클릭했을때 실행할 코드를 작성하는 부분입니다.
	        // 예제를 참고하여 다양한 활용법을 확인해 보세요.
	        console.log(data);
	        var config = { headers: {Authorization : 'KakaoAK 4fb67---------------d360ad8fe'}};
	        var url = 'https://dapi.kakao.com/v2/local/search/address.json?query='+data.jibunAddress;
	        axios.get(url,config).then(function(response) {
				console.log(JSON.stringify(response.data));
			})
	    }
	}).open();
</script>

이렇게 하고 검색을 해주면..

 

결과값

이렇게 X좌표, Y좌표도 가져 올 수 있다. 이렇게 주소값, 좌표값이 있으니, 

지오코딩 및 리버스 지오코딩에도 활용 할 수 있다. 물론 검색한 주소에 맞게 지도 중심으로 이동 하는 등 다양하게

활용이 가능하다.

 

근데 나는 저 주소검색창을 팝업으로 안띄우고 그냥 일반 검색창처럼 활용하고 싶었다.. 팝업창 불편....

그래서 Vue.js와 axios를 통해서 일반 검색창처럼 만들어보자~ ( 요즘 Vue.js랑 axios를 너무 많이 쓰는 것 같음.. )

 

============================================================================

 

우선 가이드 문서를 보자 팝업창 말고 아이프레임 형식도 지원을 하는데, 이 코드를 참고해서 만들어 보았다.

 

참조 코드

그렇게 수정해서 만든 코드가 아래 코드

 

kakaoAddress.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>카카오 주소검색</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<script src="http://ajax.aspnetcdn.com/ajax/jQuery/jquery-1.12.4.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js"></script>
<script src="//t1.daumcdn.net/mapjsapi/bundle/postcode/prod/postcode.v2.js"></script>
<script type="text/javascript" src="<c:url value='/js/kakaoAddress.js' />"></script>
</head>
<body>
	<div id="address">
		<div class="search">
			<input type="search" @keyup.enter='searchAddress()' v-model="keyword" placeholder="주소를 입력해주세요.."/>
			<input type="button" @click='searchAddress()' class="search_btn" value="검색">
		</div>
		<div>
			<div style="width: 400px;height: 100%;border: 1px solid black;">
				<div v-if="searchResult.length > 0">
					<div class="list_wrap" v-for='result in searchResult[0]' @:click='move(result.x,result.y)' style="width: 400px;height: 100%;border: 1px solid black;">
						<p class="txt01">{{result.address_name}}</p>
						<div class="in_w">
							<div class="txt02">도로명</div>
							<p class="txt03">{{result.road_address}}</p>
						</div>
					</div>
				</div>
			</div>	
		</div>
	</div>
</body>
</html>

kakaoAddress.js

$(document).ready(function(){   
	
	var address = new Vue({
		el : '#address',
		data : {
			keyword : '',
			searchResult : []
		},
		methods : {
			searchAddress : function(){
				var self = this;
				this.searchResult = []; // 검색시 기존 목록을 비움
				var searchTxt = this.keyword; // 키워드를 변수에 담음
				if(searchTxt === '' || searchTxt === null) { //키워드 입력 안헀을 시 return해줌
					alert("검색어를 입력하세요");
					return;
				}
				var config = { headers: {Authorization : 'KakaoAK 4fb672dd8d7bfc3a4bd9eb4d360ad8fe'}}; //인증키 정보
				var url = 'https://dapi.kakao.com/v2/local/search/address.json?query='+searchTxt; // url 및 키워드 담아 보냄
				axios.get(url, config).then(function(result) { // API호출
					if(result.data != undefined || result.data != null){
						self.searchResult.push(result.data.documents); //결과를 목록에 담음
					}
				})
			},
			move : function(x,y){
				// 아직 작성하지 않음. 에러 안뜨게 함수만 생성
			}
		}
	});
	
});

이렇게 작성하였다. 간단히 설명을 하면 주소를 입력하고 검색을 누르면 해당 키워드로 API를 호출하여

주소를 가져오는 화면이다. 결과는 아래와 같다.

신림동 및 신림으로 검색하였더니 위와 같이 나왔다. 근데 조금 허전하다. 주소만 가져왔기 때문.. 보통 신림동으로

검색하면 신림동 94-144와 같이 더 자세한 주소가 나와야 실제로 사용할 수 있을 것이다.

그렇기 때문에 해당 주소로 한번 더 API호출을 해보자.

 

kakaoAddress.jsp

 

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>카카오 주소검색</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<script src="http://ajax.aspnetcdn.com/ajax/jQuery/jquery-1.12.4.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js"></script>
<script src="//t1.daumcdn.net/mapjsapi/bundle/postcode/prod/postcode.v2.js"></script>
<script type="text/javascript" src="<c:url value='/js/kakaoAddress.js' />"></script>
</head>
<body>
	<div id="address">
		<div class="search">
			<input type="search" @keyup.enter='searchAddress()' v-model="keyword" placeholder="주소를 입력해주세요.."/>
			<input type="button" @click='searchAddress()' class="search_btn" value="검색">
			<div>검색결과 : {{resultList.length}}</div>
		</div>
		<div>
			<div style="width: 400px;height: 100%;border: 1px solid black;">
				<div v-if="resultList.length > 0">
					<div class="list_wrap" v-for='result in resultList' @:click='move(result.x,result.y)' style="width: 400px;height: 100%;border: 1px solid black;">
						<p class="txt01">{{result.address_name}}</p>
						<p class="txt01">{{result.place_name}}</p>
						<div class="in_w">
							<div class="txt02">도로명</div>
							<p class="txt03">{{result.road_address_name}}</p>
						</div>
					</div>
				</div>
			</div>	
		</div>
	</div>
</body>
</html>

 

우선 화면 단. 텍스트 입력후 검색버튼을 누르면 searchAddress라는 메서드를 호출하고 결과값을

v-for문을 이용하여 화면에 뿌려준다.

 

kakaoAddress.js

$(document).ready(function(){   
	
	var address = new Vue({
		el : '#address',
		data : {
			keyword : '', //검색어
			searchResult : [], // 검색어로 가져온 주소
			resultList : [] // 결과값을 담을 배열
		},
		methods : {
			searchAddress : function(){
				var self = this;
				this.resultList = []; // 검색시 기존 목록을 비움
				var searchTxt = this.keyword; // 키워드를 변수에 담음
				if(searchTxt === '' || searchTxt === null) { //키워드 입력 안헀을 시 return해줌
					alert("검색어를 입력하세요");
					return;
				}
                //인증키 정보
				var config = { headers: {Authorization : 'KakaoAK 4fb672d------------4d360ad8fe'}};
                // url 및 키워드 담아 보냄 - 주소를 가져옴
				var url = 'https://dapi.kakao.com/v2/local/search/address.json?query='+searchTxt;
                 // API호출
				axios.get(url, config).then(function(result) {
					/*
					 * 만약 API호출을 통해 가져온 주소가 있을 경우 주소의 길이만큼 키워드 검색 API호출
					 * */
					if(result.data.documents.length != 0 && result.data != undefined && result.data != null){
						//결과를 목록에 담음
                        self.searchResult.push(result.data.documents); 
						for(var i=0; i<self.searchResult[0].length;i++){
                        	// 키워드 검색 API호출
							self.getAddress(result.data.documents[i].address_name); 
						}
					}else{
                   		// API호출을 통해 가져온 주소가 없을 경우 입력한 값으로 바로 키워드 호출
						self.getAddress(self.keyword);
					}
				})
			},
			getAddress : function(name){
				var self = this;
                // 인증키
				var config = { headers: {Authorization : 'KakaoAK 4fb672dd---------------ad8fe'}};
                // 키워드 검색 API URL
				var url = 'https://dapi.kakao.com/v2/local/search/keyword.json?query=' + name;
				axios.get(url, config).then(function(result) {
					/*
					 * // 결과를 concat을 통하여 배열에 적재, flat함수는 배열의 깊이를 없애준다. 
					 * */
					self.resultList = self.resultList.concat(result.data.documents.flat()); 
				})
			},
			move : function(x,y){
				// 아직 작성하지 않음. 에러 안뜨게 함수만 생성
			}
		}
	});
	
});

자 됬다. 이렇게 하면 정상적으로 작동할 것이다. 키워드 검색 API를 추가하였는데, 로직을 조금 설명하자면,

1. 검색어를 통해 주소 API를 호출한다.

2. 값이 있을 경우 가져온 주소정보를 키워드 검색 API 파라메터로 사용한다.

3. 값이 없을 경우 검색어를 키워드 검색 API 파라메터로 사용한다.

 

왜 이렇게 했냐하면, 신림동으로 검색했을 시 주소를 가져오지만, 홈플러스, 감자탕 특 특정 키워드로 검색 했을 시

주소 검색 API에서 주소정보를 가져오지 못한다. 그렇기 때문에

검색어 자체를 키워드 파라메터로 사용하여 키워드 검색 API를 호출 하는 것이다. 아래는 결과이다.

좌측은 주소정보를 통해 키워드 검색을, 우측은 검색어를 통해 키워드 검색을 하였다.

물론 해당 데이터에는 x좌표, y좌표가 있으니 지도 이동 및 여러 기능에도 활용할 수 있다.

 

x좌표, y좌표를 포함함

 

이렇게 주소검색을 직접 만들어 보았다. 제일 좋은 방법은 카카오에서 제공하는 팝업 API를 활용하는 방법이겠지만,

팝업이 아니라, 일반 검색창을 통해 카카오 API를 활용해야 한다면 이런 방식으로 해야 될 것 같다.

물론 고쳐야 할게 많겠지만... 이런 API를 프론트엔드단이 아닌 백엔드단에서 properties를 이용해서 url이나 인증키 등을

보관하고, 처리하는 방법도 있다. 오히려 그게 좋을 것 같기도 .....

728x90
profile

개발공작소

@모찌바라기

포스팅이 좋았다면 "좋아요❤️" 또는 "구독👍🏻" 해주세요!