참조 홈페이지
카카오맵과 마찬가지로 코드를 작성하기 전에 먼저 위 사이트에 들어가서 만들어 줘야 될 것들이 있다.
먼저 위 공공데이터포털 사이트에 들어가서 회원가입 한 후
원하는 데이터를 입력해 준 후
아래쪽에 보이는 오픈 API에 들어간 후
본인이 원하는 데이터에 활용신청을 한 후
메인 페이지에서 마이페이지로 들어가면 아래와 같은 화면이 보이는데
API신청을 클릭하면
신청되어 있는 글에 들어가 보면 본인이 부여받은 키를 확인할 수 있는데
그 키를 이용해서 코드를 작성하면 된다.
++
활용 신청 상세기능정보에서 이용하려는 데이터의 요청변수가 어떤 식으로 나오는지 미리 볼 수 있는 기능도 있으니 이용하면 좋다.
이런 식으로 확인할 수 있다.
또 개발계정 상세보기에서 기본정보에서 상세설명을 클릭하면 출력결과도 확인할 수 있다.
관련 화면
사진과 같이 지역을 입력해서 검색하면 입력한 지역에 맞게 날씨와 관련 정보들을 보여준다.
관련 코드
1. JavaScript 작성
/* Javascript 샘플 코드 */
var xhr = new XMLHttpRequest();
var url = 'http://apis.data.go.kr/1360000/VilageFcstInfoService_2.0/getUltraSrtNcst'; /*URL*/
var queryParams = '?' + encodeURIComponent('serviceKey') + '='+'서비스키'; /*Service Key*/
queryParams += '&' + encodeURIComponent('pageNo') + '=' + encodeURIComponent('1'); /**/
queryParams += '&' + encodeURIComponent('numOfRows') + '=' + encodeURIComponent('1000'); /**/
queryParams += '&' + encodeURIComponent('dataType') + '=' + encodeURIComponent('JSON'); /**/
queryParams += '&' + encodeURIComponent('base_date') + '=' + encodeURIComponent('20210628'); /**/
queryParams += '&' + encodeURIComponent('base_time') + '=' + encodeURIComponent('0600'); /**/
queryParams += '&' + encodeURIComponent('nx') + '=' + encodeURIComponent('55'); /**/
queryParams += '&' + encodeURIComponent('ny') + '=' + encodeURIComponent('127'); /**/
xhr.open('GET', url + queryParams);
xhr.onreadystatechange = function () {
if (this.readyState == 4) {
alert('Status: '+this.status+'nHeaders: '+JSON.stringify(this.getAllResponseHeaders())+'nBody: '+this.responseText);
}
};
xhr.send('');
공공데이터 포털 홈페이지에서 제공하는 javascript 샘플 코드에서
'서비스키'에 일반 인증키(Encoding)를 붙여 넣는다.
let latPoint = ""; // 위도
let lonPoint = ""; // 경도
let xPoint = ""; // 격자 x 포인트
let yPoint = ""; // 격자 y 포인트
// 위도, 경도
let xValue = parseFloat(result[0].x);
let yValue = parseFloat(result[0].y);
latPoint = yValue; // 위도
lonPoint = xValue; // 경도
주소에 따른 위도, 경도 값을 통해 해당 위치의 현재 기상 정보를 조회하는데
일단 위도, 경도 값이 아닌 기상 정보 API에서 요구하는 격자 x, y 포인트 값으로 조회한다.
위도, 경도는 이전에 작성했던 카카오맵 geocoder에서 뽑았다.
// 현재 날짜 구하기
let currentDate = new Date();
let year = currentDate.getFullYear();
let month = ('0' + (currentDate.getMonth() + 1)).slice(-2);
let day = ('0' + currentDate.getDate()).slice(-2);
let formattedDate = year + month + day;
// 시간 구하기
let hours = ('0' + currentDate.getHours()).slice(-2);
let minutes = ('0' + (currentDate.getMinutes() - 30)).slice(-2);
// 만약 minutes가 30보다 작으면 hours에서 1을 빼주기
if (currentDate.getMinutes() < 30) {
hours = ('0' + (currentDate.getHours() - 1)).slice(-2);
minutes = ('0' + (currentDate.getMinutes() + 30)).slice(-2);
}
let formattedTime = hours + minutes;
// 좌표를 격자 x,y point로 바꾸기
let result = dfs_xy_conv("toXY", latPoint, lonPoint);
console.log("X:", result.x, "Y:", result.y);
xPoint = result.x;
yPoint = result.y;
샘플 코드에 요청 변수에 조회하고 싶은 값을 입력한다.
base_date는 20240117 형식으로
base_time은 1730 형식으로
nx와 ny에는 변환된 x, y 포인트 값을 입력한다.
주의할 점은 base_time 발표시각은 30분마다 갱신되는 거여서 현재 시간에서 30분 전 시간을 입력해야 된다.
/** 위도, 경도를 x,y 격자 포인트로 변경 */
var RE = 6371.00877; // 지구 반경(km)
var GRID = 5.0; // 격자 간격(km)
var SLAT1 = 30.0; // 투영 위도1(degree)
var SLAT2 = 60.0; // 투영 위도2(degree)
var OLON = 126.0; // 기준점 경도(degree)
var OLAT = 38.0; // 기준점 위도(degree)
var XO = 43; // 기준점 X좌표(GRID)
var YO = 136; // 기1준점 Y좌표(GRID)
// LCC DFS 좌표변환 ( code : "toXY"(위경도->좌표, v1:위도, v2:경도), "toLL"(좌표->위경도,v1:x, v2:y) )
function dfs_xy_conv(code, v1, v2) {
// LCC DFS 좌표변환을 위한 기초 자료
var DEGRAD = Math.PI / 180.0;
var RADDEG = 180.0 / Math.PI;
var re = RE / GRID;
var slat1 = SLAT1 * DEGRAD;
var slat2 = SLAT2 * DEGRAD;
var olon = OLON * DEGRAD;
var olat = OLAT * DEGRAD;
var sn = Math.tan(Math.PI * 0.25 + slat2 * 0.5) / Math.tan(Math.PI * 0.25 + slat1 * 0.5);
sn = Math.log(Math.cos(slat1) / Math.cos(slat2)) / Math.log(sn);
var sf = Math.tan(Math.PI * 0.25 + slat1 * 0.5);
sf = Math.pow(sf, sn) * Math.cos(slat1) / sn;
var ro = Math.tan(Math.PI * 0.25 + olat * 0.5);
ro = re * sf / Math.pow(ro, sn);
var rs = {};
if (code == "toXY") {
rs['lat'] = v1;
rs['lng'] = v2;
var ra = Math.tan(Math.PI * 0.25 + (v1) * DEGRAD * 0.5);
ra = re * sf / Math.pow(ra, sn);
var theta = v2 * DEGRAD - olon;
if (theta > Math.PI) theta -= 2.0 * Math.PI;
if (theta < -Math.PI) theta += 2.0 * Math.PI;
theta *= sn;
rs['x'] = Math.floor(ra * Math.sin(theta) + XO + 0.5);
rs['y'] = Math.floor(ro - ra * Math.cos(theta) + YO + 0.5);
}
else {
rs['x'] = v1;
rs['y'] = v2;
var xn = v1 - XO;
var yn = ro - v2 + YO;
ra = Math.sqrt(xn * xn + yn * yn);
if (sn < 0.0) - ra;
var alat = Math.pow((re * sf / ra), (1.0 / sn));
alat = 2.0 * Math.atan(alat) - Math.PI * 0.5;
if (Math.abs(xn) <= 0.0) {
theta = 0.0;
}
else {
if (Math.abs(yn) <= 0.0) {
theta = Math.PI * 0.5;
if (xn < 0.0) - theta;
}
else theta = Math.atan2(xn, yn);
}
var alon = theta / sn + olon;
rs['lat'] = alat * RADDEG;
rs['lng'] = alon * RADDEG;
}
return rs;
}
위 코드는 위도, 경도, x, y 격자 포인트 변경하는 코드 함수다.
var xhr = new XMLHttpRequest();
var url = 'http://apis.data.go.kr/1360000/VilageFcstInfoService_2.0/getUltraSrtFcst'; /*URL*/
var queryParams = '?' + encodeURIComponent('serviceKey') + '='+'5CZW8vE4f16CFpvpKdt5RwisoNCWGjCG%2FlZqcpESy8NaGCdcB8vPI6aDpHCKyQcqTImAERfoVVHuzLJsaDHitg%3D%3D'; /*Service Key*/
queryParams += '&' + encodeURIComponent('pageNo') + '=' + encodeURIComponent('1'); /* 페이지 번호 */
queryParams += '&' + encodeURIComponent('numOfRows') + '=' + encodeURIComponent('1000'); /* 한 페이지 결과 수 */
queryParams += '&' + encodeURIComponent('dataType') + '=' + encodeURIComponent('JSON'); /* 응답자료형식 */
queryParams += '&' + encodeURIComponent('base_date') + '=' + encodeURIComponent(formattedDate); /* 발표일자 */
queryParams += '&' + encodeURIComponent('base_time') + '=' + encodeURIComponent(formattedTime); /* 발표시각 */
queryParams += '&' + encodeURIComponent('nx') + '=' + encodeURIComponent(xPoint); /* 예보지점 X 좌표 */
queryParams += '&' + encodeURIComponent('ny') + '=' + encodeURIComponent(yPoint); /* 예보지점 Y 좌표 */
xhr.open('GET', url + queryParams);
xhr.onreadystatechange = function () {
if (this.readyState == 4) {
if (this.status == 200) {
console.log("Success!");
// JSON 파싱
var jsonResponse = JSON.parse(this.responseText);
// 필요한 정보 추출
var items = jsonResponse.response.body.items.item;
console.log("items length: " + items.length);
for (var i = 0; i < items.length; i++) {
var item = items[i];
console.log("item: " + JSON.stringify(item));
console.log("자료구분코드: " + item.category);
console.log("예보일자: " + item.fcstDate);
console.log("예보시각: " + item.fcstTime);
console.log("예보값: " + item.fcstValue);
}
} else {
console.log("Error: " + this.status);
}
}
};
xhr.send('');
준비된 요청 변수를 통해서 현재 위치에 따른 기상 정보를 조회한다.
완성된 화면
'project > personal project' 카테고리의 다른 글
[API] 카카오맵 API 기능 구현 (0) | 2024.01.17 |
---|---|
[API] 화면구현 (0) | 2024.01.16 |
[CRUD] 기능구현 - 단일 파일첨부 업로드 및 다운로드 (0) | 2024.01.10 |
[CRUD] 기능구현 - 게시글 작성 (네이버 스마트 에디터) (0) | 2024.01.10 |
[CRUD] 기능구현 - 로그인 기능 구현 (스프링 시큐리티) (0) | 2024.01.10 |