fetch

2025. 4. 18. 01:21프론트엔드/JavaScript

728x90
반응형

1. fetch

fetch는 자바스크립트에서 서버와 통신할 수 있도록 도와주는 비동기 함수로, 주로 HTTP 요청(GET, POST 등)을 보낼 때 사용됩니다. fetch() 함수는 URL을 인자로 받아 서버에 요청을 보내고, 그 결과를 Promise 객체로 반환합니다. 이 Promise는 응답이 도착하면 then()에서 응답(Response 객체)을 처리할 수 있으며, 네트워크 오류 등이 발생하면 catch()로 에러를 잡을 수 있습니다. fetch는 기본적으로 비동기 처리이기 때문에 응답이 도착하기 전에도 다음 코드가 실행되며, await 키워드와 함께 사용하면 보다 직관적인 코드 흐름으로 작성할 수 있습니다.

<script>
    fetch('https://jsonplaceholder.typicode.com/todos/1')
    .then((response) => {
        return response.json()
    })
    .then((data) => console.log(data.title))
</script>

 

<script>
  async function getDate() {
    try {
      const response = await fetch('https://jsonplaceholder.typicode.com/todos/1');
      const data = await response.json();
      console.log(data.title);
    } catch (error) {
      console.error('에러 발생:', error);
    }
  }

  getDate();
</script>

 

 

2. 기상청_관광코스별 관광지 상세 날씨 조회서비스

기상청_관광코스별 관광지 상세 날씨 조회서비스 API는 국내 주요 관광지의 기후와 날씨 정보를 제공하는 공공데이터 API로, 특정 관광코스나 지역의 체감기후지수(TCI: Tourism Climate Index)를 포함한 상세 기상 데이터를 조회할 수 있도록 설계되었습니다. 이 API는 관광객의 여행 만족도를 높이기 위해 날씨에 따른 관광 적합도를 수치화한 데이터를 제공하며, 사용자는 CITY_AREA_ID, CURRENT_DATE, DAY 등의 파라미터를 통해 특정 지역의 예보 시점별 기후지수와 날씨 예보 데이터를 JSON 또는 XML 형식으로 받을 수 있습니다. 이를 활용하면 실시간 날씨 기반 관광 안내 시스템이나 관광 정보 앱에 유용하게 활용할 수 있습니다.

 

 

3. 카카오 맵

https://developers.kakao.com/docs/latest/ko/kakaomap/common

 

Kakao Developers

카카오 API를 활용하여 다양한 어플리케이션을 개발해보세요. 카카오 로그인, 메시지 보내기, 친구 API, 인공지능 API 등을 제공합니다.

developers.kakao.com

 

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>관광지 체감기후지수</title>
    <style>
      body {
        font-family: sans-serif;
        padding: 2rem;
      }
      select,
      button {
        font-size: 1rem;
        padding: 0.5rem;
      }
      #weatherInfo {
        margin-top: 1rem;
        padding: 1rem;
        border-radius: 8px;
        background-color: #f7f7f7;
      }
      .grade {
        font-weight: bold;
        padding: 0.3rem 0.6rem;
        border-radius: 4px;
        display: inline-block;
      }
      .매우좋음 {
        background: #1abc9c;
        color: white;
      }
      .좋음 {
        background: #2ecc71;
        color: white;
      }
      .보통 {
        background: #f1c40f;
        color: black;
      }
      .나쁨 {
        background: #e67e22;
        color: white;
      }
      .매우나쁨 {
        background: #e74c3c;
        color: white;
      }
      #map {
        width: 100%;
        height: 400px;
        margin-top: 2rem;
        border: 1px solid #ccc;
      }
    </style>
    <!-- 
        <script>: 순서가 중요. html과 함께 순서대로 처리
        <script defer>: DOM 요소 접근 오류 방지. 로딩 최적화. HTML이 모두 실행된 후 처리
    -->
    <script
      defer
      type="text/javascript"
      src="//dapi.kakao.com/v2/maps/sdk.js?appkey=카카오API키&autoload=false&libraries=services"
    ></script>
  </head>
  <body>
    <h2>관광지 체감기후지수</h2>
    <label for="region">지역 선택: </label>
    <select name="region" id="region">
      <option value="서울 중구|1111000000">서울 중구</option>
      <option value="부산 중구|2611000000">부산 중구</option>
      <option value="대구 중구|2711000000">대구 중구</option>
      <option value="인천 중구|2811000000">인천 중구</option>
      <option value="광주 동구|2911000000">광주 동구</option>
      <option value="대전 중구|3011000000">대전 중구</option>
      <option value="울산 남구|3114000000">울산 남구</option>
      <option value="세종|3611000000">세종</option>
      <option value="강릉시|4215000000">강릉시</option>
      <option value="청주시|4311000000">청주시</option>
      <option value="전주시|4511000000">전주시</option>
      <option value="목포시|4611000000">목포시</option>
      <option value="창원시|4812000000">창원시</option>
      <option value="제주 제주시|5011000000">제주 제주시</option>
      <option value="제주 서귀포시|5013000000" selected>제주 서귀포시</option>
    </select>
    <button onclick="loadData()">조회하기</button>
    <div id="weatherInfo">데이터를 불러오는 중입니다....</div>
    <div id="map"></div>
    <script>
      let map;
      let marker;
      const serviceKey =
        "공공데이터 오픈API 키";

      function loadData() {
        // 서울 중구|1111000000"
        const selected = document.getElementById("region").value;
        // cityAreaId=1111000000
        const [, cityAreaId] = selected.split("|");
        const now = new Date();
        // 10, 02
        const CURRENT_DATE = `${now.getFullYear()}${String(
          now.getMonth() + 1
        ).padStart(2, "0")}${String(now.getDate()).padStart(2, "0")}00`;

        const DAY = 3;
        const url = `https://apis.data.go.kr/1360000/TourStnInfoService1/getCityTourClmIdx1?serviceKey=${encodeURIComponent(
          serviceKey
        )}&pageNo=1&numOfRows=10&dataType=JSON&CURRENT_DATE=${CURRENT_DATE}&DAY=${DAY}&CITY_AREA_ID=${cityAreaId}`;

        console.log(url);

        fetch(url)
          .then((res) => res.json())
          .then((data) => {
            // JSON.stringify(문자열로 바꿀 자바스크립트 객체, 필터링 함수, 공백수)
            console.log("전체 응답 구조 확인: ", JSON.stringify(data, null, 2));
            // 옵셔널 체이닝
            // data -> response -> header 안전하기 접근
            // undefined나 null이 아닐 경우 header에 접근
            const header = data.response?.header;
            const body = data.response?.body;

            if (header?.resultCode !== "00") {
              document.getElementById("weatherInfo").innerText =
                "해당 지역의 데이터가 없습니다.";
              return;
            }

            const items = body?.items?.item;
            if (!items || items.length === 0) {
              document.getElementById("weatherInfo").innerText =
                "해당 지역의 데이터가 없습니다.";
              return;
            }

            let html = "";
            items.forEach((item, index) => {
              html += `
        <strong>날짜:</strong> ${item.tm}<br>
        <strong>지역:</strong> ${item.totalCityName}<br>
        <strong>체감기후지수:</strong> ${item.kmaTci}<br>
        <strong>등급:</strong>
        <span class="grade ${item.TCI_GRADE}">${item.TCI_GRADE}</span>
        <hr>
      `;
              if (index === 0) {
                moveMapByCityName(item.totalCityName);
              }
            });

            document.getElementById("weatherInfo").innerHTML = html;
          })
          .catch((err) => {
            console.error("fetch 실패 또는 파싱 오류", err);
            document.getElementById("weatherInfo").innerText =
              "데이터 불러오기 실패";
          });
      }

      function moveMapByCityName(address) {
        const geocoder = new kakao.maps.services.Geocoder();
        geocoder.addressSearch(address, function (result, status) {
          if (status === kakao.maps.services.Status.OK) {
            const coords = new kakao.maps.LatLng(result[0].y, result[0].x);
            map.setCenter(coords);
            if (marker) marker.setMap(null);
            marker = new kakao.maps.Marker({
              map: map,
              position: coords,
            });
          } else {
            console.warn("주소를 찾을 수 없습니다:", address);
          }
        });
      }

      window.onload = function () {
        kakao.maps.load(function () {
          map = new kakao.maps.Map(document.getElementById("map"), {
            center: new kakao.maps.LatLng(33.2539, 126.5596), // 서귀포시 초기 중심
            level: 9,
          });
          loadData(); // 초기 로딩
        });
      };
    </script>
  </body>
</html>

 

 

728x90
반응형

'프론트엔드 > JavaScript' 카테고리의 다른 글

Promise 기반 API  (1) 2025.04.17
브라우저에 데이터 저장하기  (0) 2025.04.17
JSON  (0) 2025.04.16
정규식  (0) 2025.04.16
이벤트  (0) 2025.04.16