[OpenAPI] 공공데이터의 개요와 가공 및 활용

2022. 11. 30. 10:32·📗 self-study/📗 KH정보교육원 당산지원

 

 

 

공공 데이터(Open Data)

👉🏻 데이터베이스, 전자화된 파일 등으로 공공기관에서 사용할 목적으로 처리된 자료 또는 정보

👉🏻 공공기관에서의 일상적 업무 수행의 결과물로 생성 또는 수집/취득한 다양한 형태(텍스트, 이미지, 동영상 등)의 모드 자료

 

 

 

공공 데이터 포털

https://www.data.go.kr  

 

공공데이터 포털

국가에서 보유하고 있는 다양한 데이터를『공공데이터의 제공 및 이용 활성화에 관한 법률(제11956호)』에 따라 개방하여 국민들이 보다 쉽고 용이하게 공유•활용할 수 있도록 공공데이터(Datase

www.data.go.kr

 

 

 

Open API

👉🏻 공공 데이터 제공 형식 중 하나

👉🏻  HttpRequest 요청을 보내면 서버가 데이터를 응답해주는 방식
👉🏻  요청 해야하는 주소, 파라미터 (요청 시 전달값), 반환 데이터 등이 정해져 있으며, 인증키를 발급받아야 함
👉🏻  웹 애플리케이션 개발 시에는 해당 OpenAPI 방식을 권장

 

 

 

요청 변수와 출력 결과

👉🏻 요청 변수 (Request Parameter)

✔️ OpenAPI 서버에 요청 시 필요한 속성들을 나열한 것으로 항목 구분이 필수인 속성들은 반드시 key=value 형식으로 전달

 

👉🏻 출력 결과 (Response Element)

✔️ OpenAPI 서버에 요청 결과 응답메세지에 포함된 데이터의 형식을 의미

✔️ 기본적으로 결과 코드, 결과 메시지 등을 포함하고 있으며 실제 필요로 하는 값들이 담겨 있는 형식이므로 API 문서를 잘 파악해서 구현하고자 하는 application 과 연동해야 한다

 

 

 

 

데이터 포맷 종류

👉🏻 xml 파일

✔️ HTML 과 같은 마크업언어 (Markup Language)
✔️ 웹에서 구조화된 문서를 전송 가능하도록 설계

✔️  각 요소들의 독립성을 보장함으로써 문서의 호환성, 내용의 독립성, 요소 변경의 용이성 등의 특성을 제공하는 사용자 정의 태그 문서

 

👉🏻 json 파일

✔️ 자바스크립트의 구문 형식으로 프로그래밍 언어나 플랫폼에 독립적이기 때문에 C, C++, C#, Java, JavaScript 등의 많은 언어에서 이용 가능

 

 

 

공공 데이터 사용하는법

1. 공공데이터 포털 접속 후 회원 가입

 

 

 

2. 원하는 키워드 검색

 

 

 

3. 검색 결과 중 파일 형식 참고하여 필요한 양식 찾기 (JSON+SML 파일인 OpenAPI 권장)

👉🏻 hwp, xlsx 같은 파일은 이미 고정된 데이터임

👉🏻 이런 자료를 끌어와서 뿌려 줘도 상관은 없지만 JSON + XML 파일 사용 시 실시간 반영이 가능해짐 (OpenAPI 방식)

 

 

 

3-1. OpenAPI 중 필요한 데이터 선택 후 활용 신청

 

3-2. 활용 목적 선택 후 내용 기재, 상세 기능 정보 선택 후 활용 신청

👉🏻 상세 기능 정보 선택에 따라 제공하는 정보 양이 달라질 수 있으므로 모두 선택하는 게 좋음

 

 

 

4. 마이페이지 개발계정/인증키 발급현황에서 승인 내역 및 인증키 확인

👉🏻 마이페이지-개발계정: 승인 현황을 확인할 수 있음 (활용 신청 버튼 클릭 시 자동으로 이동함)

👉🏻 마이페이지-인증키 발급현황: 클릭 시 확인할 수 있음 (개별 발급이므로 타인에게 노출되지 않도록 주의할 것)

 

 

 

5. 마이페이지-개발계정-승인된 공공데이터 클릭

👉🏻 참고문서: 사용 방법과 문서 관련 내용 등을 알고 싶을 때 참고하는 개발자 문서

👉🏻 인코딩된 일반 인증키: 우리가 사용할 인증키이며 개별 발급이므로 타인에게 노출되지 않도록 주의할 것

👉🏻 활용신청 상세기능 정보: 사용하고 싶은 정보의 상세 내용 및 요청 정보를 확인할 수 있음

 

 

 

6. 내가 제공받길 원하는 정보의 확인 버튼 클릭

 

 

 

6-1. 내가 제공받길 원하는 정보의 확인 버튼 클릭

👉🏻 요청 변수가 나옴

내 요청을 다른 사람의 DB로 보내기 때문에 요청 변수에서 원하는 형식대로 보내 줘야 함!

 

 

 

6-2. 미리보기 클릭 시 정보와 함께 url이 뜸

👉🏻  url 뜯어 보기

 

👉🏻 기본 정보(아이템별로 하나의 측청값인 듯하다)

 

 

 

url 내용 변경해 보기

👉🏻 url의 returnType=xml에서 json으로 바꿨을 때

 

👉🏻 url의 returnType=xml에서 json으로, sidoName=부산으로 바꿨을 때

 

 

 

공공데이터를 프로젝트에서 활용하기

 

1. Spring Legacy Project 생성 및 설정

 

1-1. 프로젝트 생성

👉🏻  Project name: OpenData_Project

👉🏻 Spring MVC Project 선택 후 Next

 

👉🏻 도메인 역순 2번째까지, 3번째는 contextroot 기재

 

1-2. HomeController, home.jsp 삭제

 

 

 

1-3. pom.xml 설정

👉🏻 java-version을 1.6에서 1.8로 바꾸기

 

1️⃣ properties의 java-version을 하드코딩으로 1.8로 변경

	<properties>
		<java-version>1.8</java-version>
		<org.springframework-version>3.1.1.RELEASE</org.springframework-version>
		<org.aspectj-version>1.6.10</org.aspectj-version>
		<org.slf4j-version>1.6.6</org.slf4j-version>
	</properties>

기존 코드

 

2️⃣ <plugin> groupId org.apache.maver.plugins 부분의 source와 target을 동적 코딩으로 자바 버전 변경

            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>2.5.1</version>
                <configuration>
                    <source>${java-version}</source>
                    <target>${java-version}</target>
                    <compilerArgument>-Xlint:all</compilerArgument>
                    <showWarnings>true</showWarnings>
                    <showDeprecation>true</showDeprecation>
                </configuration>
            </plugin>

기존 코드

 

 

 

1-4. 프로젝트의 Maven-Update Project

 

 

 

1-5.  Package Explorer에서 java-version 변경 확인 후 진행하기

 

 

 

2. AirPollutionTest 클래스 생성

👉🏻 test에 생성하기

👉🏻 run 패키지를 경로에 추가 후 생성하기

 

 

 

3. AirVO 클래스 생성

👉🏻 응답 데이터 중 내가 필요한 정보를 가공할 용도의 클래스

👉🏻 model.vo 패키지를 경로에 추가 후 생성하기

package com.kh.opendata.model.vo;

public class AirVO {
	
	// 필드부
	private String stationName; // 측정소명
	private String dataTime; // 측정일시
	private String khaiValue; // 통합대기환경수치
	
	private String pm10Value; // 미세먼지농도
	private String so2Value; // 아황산가스농도
	private String co2Value; // 일산화탄소 농도
	private String no2Value; // 이산화질소농도
	private String o3Value; // 오존 농도
	
	// 생성자부
	public AirVO() {}

	public AirVO(String stationName, String dataTime, String khaiValue, String pm10Value, String so2Value,
			String co2Value, String no2Value, String o3Value) {
		super();
		this.stationName = stationName;
		this.dataTime = dataTime;
		this.khaiValue = khaiValue;
		this.pm10Value = pm10Value;
		this.so2Value = so2Value;
		this.co2Value = co2Value;
		this.no2Value = no2Value;
		this.o3Value = o3Value;
	}
	
	// 메소드부
	public String getStationName() {
		return stationName;
	}

	public void setStationName(String stationName) {
		this.stationName = stationName;
	}

	public String getDataTime() {
		return dataTime;
	}

	public void setDataTime(String dataTime) {
		this.dataTime = dataTime;
	}

	public String getKhaiValue() {
		return khaiValue;
	}

	public void setKhaiValue(String khaiValue) {
		this.khaiValue = khaiValue;
	}

	public String getPm10Value() {
		return pm10Value;
	}

	public void setPm10Value(String pm10Value) {
		this.pm10Value = pm10Value;
	}

	public String getSo2Value() {
		return so2Value;
	}

	public void setSo2Value(String co2Value) {
		this.so2Value = so2Value;
	}
	
	public String getCo2Value() {
		return co2Value;
	}

	public void setCo2Value(String co2Value) {
		this.co2Value = co2Value;
	}

	public String getNo2Value() {
		return no2Value;
	}

	public void setNo2Value(String no2Value) {
		this.no2Value = no2Value;
	}

	public String getO3Value() {
		return o3Value;
	}

	public void setO3Value(String o3Value) {
		this.o3Value = o3Value;
	}

	@Override
	public String toString() {
		return "AirVO [stationName=" + stationName + ", dataTime=" + dataTime + ", khaiValue=" + khaiValue
				+ ", pm10Value=" + pm10Value + ", so2Value=" + so2Value + ", co2Value=" + co2Value + ", no2Value=" + no2Value + ", o3Value="
				+ o3Value + "]";
	};

}

 

 

 

🙋🏻‍♀️ 필드명은 무슨 기준으로 한 건가요?

🙆🏻‍♀️ 아까 확인했던 xml파일에서 가지고 왔습니다 개발자문서에서도 확인 가능합니다!

 

 

 

 

4. OpenAPI 서버로 요청하고자 하는 url 만들기

⌨️ AirPollutionTest 1

package com.kh.opendata.run;

import java.io.IOException;
import java.net.URLEncoder;

import org.junit.Test;

public class AirPollutionTest {
	
	// 공공 데이터를 테스트하기 위한 간단한 테스트 환경 구성 => JUnit
	@Test
	public void testRun() throws IOException { // UnsupportedEncodingException의 부모인 IOException으로 예외처리

		String url = "http://apis.data.go.kr/B552584/ArpltnInforInqireSvc/getCtprvnRltmMesureDnsty";
			   url += "?serviceKey=서비스키";
			   url += "&sidoName=" + URLEncoder.encode("서울", "UTF-8");
			   // 요청 시 전달값에 한글이 있을 경우 encoding 해야 함!
			   url += "&returnType=xml";
			   
		System.out.println(url);
		
	}

}

쿼리스트링 전에 들어가는 url 주소

 

 

 

📌 현재 콘솔에 뜨는 url을 브라우저로 접속해 봤을 때의 상황

👉🏻 서비스키가 제대로 부여되지 않았을 경우 SERVICE_KEY_IS_NOT_REGISTERED_ERROR 발생함

 

 

 

⌨️ AirPollutionTest 2

👉🏻 서비스키는 한 번 부여받으면 약 2년여 간 고정된 값으로 지속되기 때문에 상수 필드로 지정해 놓을 것!

package com.kh.opendata.run;

import java.io.IOException;
import java.net.URLEncoder;

import org.junit.Test;

public class AirPollutionTest {
	
	// 발급받은 인증키 정보를 상수 필드에 담아두기(변할 일이 없기 때문)
	public static final String SERVICEKEY = "알려줄수없는나의인증키입니다";
	
	// 공공 데이터를 테스트하기 위한 간단한 테스트 환경 구성 => JUnit
	@Test
	public void testRun() throws IOException { // UnsupportedEncodingException의 부모인 IOException으로 예외처리
		
		// 1. OpenAPI 서버로 요청하고자 하는 url 만들기
		String url = "http://apis.data.go.kr/B552584/ArpltnInforInqireSvc/getCtprvnRltmMesureDnsty";
			   url += "?serviceKey=" + SERVICEKEY;
			   url += "&sidoName=" + URLEncoder.encode("서울", "UTF-8");
			   // 요청 시 전달값에 한글이 있을 경우 encoding 해야 함!
			   url += "&returnType=xml";
			   
		System.out.println(url);
		// 서비스키가 제대로 부여되지 않았을 경우
		// SERVICE_KEY_IS_NOT_REGISTERED_ERROR 발생함
		
	}

}

 

 

 

📌 현재 콘솔에 뜨는 url을 브라우저로 접속해 봤을 때의 상황

👉🏻 처음 공공데이터 포털에서 조회했던 것처럼 제대로 뜸!

 

 


내용 쪼개기


 

⌨️💻 AirPollutionTest 2

public class AirPollutionTest {
	
	// 발급받은 인증키 정보를 상수 필드에 담아두기(변할 일이 없기 때문)
	public static final String SERVICEKEY = "Tx1KtZT26sjtr%2F1tn0i0ea5161fXk0m8t0J7eWdWJsk1GBVTcGj%2B8zDIsbwQ8pibb461SlMf6mZ4LTTSqkUNyw%3D%3D";
	
	// 공공 데이터를 테스트하기 위한 간단한 테스트 환경 구성 => JUnit
	@Test
	public void testRun() throws IOException { // UnsupportedEncodingException의 부모인 IOException으로 예외처리
		
		// 1. OpenAPI 서버로 요청하고자 하는 url 만들기
		String url = "http://apis.data.go.kr/B552584/ArpltnInforInqireSvc/getCtprvnRltmMesureDnsty";
			   url += "?serviceKey=" + SERVICEKEY;
			   url += "&sidoName=" + URLEncoder.encode("서울", "UTF-8");
			   // 요청 시 전달값에 한글이 있을 경우 encoding 해야 함!
			   url += "&returnType=xml";
			   
		// System.out.println(url);
		// 서비스키가 제대로 부여되지 않았을 경우
		// SERVICE_KEY_IS_NOT_REGISTERED_ERROR 발생함
			   
		// 2. HttpURLConnection 객체를 이용해서 OpenAPI 요청 절차
	    // 2_1. 요청하고자 하는 url 주소를 전달하면서 java.net.URL 객체 생성
	    URL requestUrl = new URL(url);
	    
	    // 2_2. 생성된 URL 객체를 가지고 HttpURLConnection 객체 생성
	    HttpURLConnection urlConnection = (HttpURLConnection)requestUrl.openConnection();
		
	    // 2_3. 요청에 필요한 Header 설정하기(get/post 방식 설정)
	    urlConnection.setRequestMethod("GET");
	    
	    // 2_4. 해당 OpenAPI 서버로 요청을 보낸 후 스트림을 통해 응답데이터 읽어들이기
	    BufferedReader br = new BufferedReader( new InputStreamReader (urlConnection.getInputStream()));
	    // 보조스트림은 단독 존재 불가!
	    // 보조스트림인 BufferedReader는 2바이트 사이즈의 문자스트림
	    // 기반스트림인 InputStream은 1바이트 사이즈의 바이트스트림
	    // 항상 보조스트림과 기반스트림 통로의 사이즈가 일치해야 함 => InputStramReader 객체를 통해 호환시켜 줌
	    
	    // 2_5. 반복적으로 매번 응답데이터를 한줄씩 읽어들이기
	    String line; // 기본적으로 null이 담겨 있음
	    
	    while((line = br.readLine()) != null) { // 더 이상 읽어들일 게 없을 때까지 반복
	    	
	    	System.out.println(line);
	    	
	    }
	    
	    // 2_6. 다 사용한 스트림 반납 및 연결 끊기
	    br.close();
	    urlConnection.disconnect();
	}

}

 

 

 

⌨️💻 AirPollutionTest 2

package com.kh.opendata.run;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;

import org.junit.Test;

public class AirPollutionTest {
	
	// 발급받은 인증키 정보를 상수 필드에 담아두기(변할 일이 없기 때문)
	public static final String SERVICEKEY = "Tx1KtZT26sjtr%2F1tn0i0ea5161fXk0m8t0J7eWdWJsk1GBVTcGj%2B8zDIsbwQ8pibb461SlMf6mZ4LTTSqkUNyw%3D%3D";
	
	// 공공 데이터를 테스트하기 위한 간단한 테스트 환경 구성 => JUnit
	@Test
	public void testRun() throws IOException { // UnsupportedEncodingException의 부모인 IOException으로 예외처리
		
		// 1. OpenAPI 서버로 요청하고자 하는 url 만들기
		String url = "http://apis.data.go.kr/B552584/ArpltnInforInqireSvc/getCtprvnRltmMesureDnsty";
			   url += "?serviceKey=" + SERVICEKEY;
			   url += "&sidoName=" + URLEncoder.encode("서울", "UTF-8");
			   // 요청 시 전달값에 한글이 있을 경우 encoding 해야 함!
			   url += "&returnType=xml";
			   
		// System.out.println(url);
		// 서비스키가 제대로 부여되지 않았을 경우
		// SERVICE_KEY_IS_NOT_REGISTERED_ERROR 발생함
			   
		// 2. HttpURLConnection 객체를 이용해서 OpenAPI 요청 절차
	    // 2_1. 요청하고자 하는 url 주소를 전달하면서 java.net.URL 객체 생성
	    URL requestUrl = new URL(url);
	    
	    // 2_2. 생성된 URL 객체를 가지고 HttpURLConnection 객체 생성
	    HttpURLConnection urlConnection = (HttpURLConnection)requestUrl.openConnection();
		
	    // 2_3. 요청에 필요한 Header 설정하기(get/post 방식 설정)
	    urlConnection.setRequestMethod("GET");
	    
	    // 2_4. 해당 OpenAPI 서버로 요청을 보낸 후 스트림을 통해 응답데이터 읽어들이기
	    BufferedReader br = new BufferedReader( new InputStreamReader (urlConnection.getInputStream()));
	    // 보조스트림은 단독 존재 불가!
	    // 보조스트림인 BufferedReader는 2바이트 사이즈의 문자스트림
	    // 기반스트림인 InputStream은 1바이트 사이즈의 바이트스트림
	    // 항상 보조스트림과 기반스트림 통로의 사이즈가 일치해야 함 => InputStramReader 객체를 통해 호환시켜 줌
	    
	    // 2_5. 반복적으로 매번 응답데이터를 한줄씩 읽어들이기
	    String line; // 기본적으로 null이 담겨 있음
	    
	    // 응답 데이터를 받아둘 변수 선언
	    String responseText = "";
	    
	    while((line = br.readLine()) != null) { // 더 이상 읽어들일 게 없을 때까지 반복
	    	
	    	// System.out.println(line);
	    	responseText += line; // 누적으로 문자열 연이어 붙이기
	    	
	    }
	    
	    System.out.println(responseText);
	    
	    // 2_6. 다 사용한 스트림 반납 및 연결 끊기
	    br.close();
	    urlConnection.disconnect();
	}

}

문자열 연이어서 나옴
returnType=json으로 바꿔 봤을 때 출력되는 내용

 

 

 

생긴 것은 json 형식이나 엄밀히 말하면 String 타입의 데이터임
JsonObject, JsonArray, JsonElement를 이용해서 "파싱 작업" 할 수 있음
기존의 흐름: VO에 담긴 내용물들을 JSON으로 가공
이번의 흐름: JSON에 담긴 내용물을 VO로 가공
    
기존의 JSONObject, JSONArray랑은 엄밀히 다른 타입 (헷갈리지 말 것) => json.jar 파일에서 제공
JsonObject, JsonArray, JsonElement => gson.jar 파일에서 제공
    

💻 pom.xml

JSON을 VO로 파싱하기 위한 gson 라이브러리 넣어 주기

		<!-- JSON을 VO로 파싱하기 위한 gson 라이브러리 넣어 주기 -->
		<dependency>
		    <groupId>com.google.code.gson</groupId>
		    <artifactId>gson</artifactId>
		    <version>2.10</version>
		</dependency>

 

 

 

JSON 테이터를 VO로 파싱하기

	    // *JSON 테이터를 VO로 파싱하기
	    // 1) 각각의 item 정보를 얻어내기 위해 문자열 타입인 responseText 변수를 JsonObject타입으로 변환
	    JsonObject totalObj = JsonParser.parseString(responseText).getAsJsonObject();
	    
	    // 2) totalObj로부터 response라는 키값에 딸린 객체만 추출하기
	    JsonObject responseObj = totalObj.getAsJsonObject("response");
	    
	    // 3) responseObj로부터 body라는 키값에 딸린 객체만 추출하기
	    JsonObject bodyObj = responseObj.getAsJsonObject("body");
	    
	    // 4) bodyObj로부터 totalCount라는 키값에 딸린 데이터만 추출
	    int totalCount = bodyObj.get("totalCount").getAsInt();
	    // System.out.println(totalCount);
	    
	    // 5) bodyObj로부터 items라는 키값에 딸린 배열만 추출하기
	    JsonArray itemArr = bodyObj.getAsJsonArray("items");
	    // System.out.println(itemArr);
        
            // 6) itemArr로부터 반복을 돌려 가져 AirVO로 가공 후 ArrayList에 담기
	    ArrayList<AirVO> list = new ArrayList<>();
	    
	    for(int i = 0; i < itemArr.size(); i++) {
	    	
	    	// itemArr의 각 인덱스에 들은 자바 스크립트 객체를 또 추출
	    	JsonObject item = itemArr.get(i).getAsJsonObject();
	    	// System.out.println(item);
	    	
	    	AirVO air = new AirVO();
	    	// 시간상 3개의 필드만 list에 담아 볼 것
	    	air.setStationName(item.get("stationName").getAsString());
	    	air.setDataTime(item.get("dataTime").getAsString());
	    	air.setKhaiValue(item.get("khaiValue").getAsString());
	    	
	    	list.add(air);
	    }

 

 

💻 AirPollutionTest

package com.kh.opendata.run;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.util.ArrayList;

import org.junit.Test;

import com.google.gson.JsonArray;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import com.kh.opendata.model.vo.AirVO;

public class AirPollutionTest {
	
	// 발급받은 인증키 정보를 상수 필드에 담아두기(변할 일이 없기 때문)
	public static final String SERVICEKEY = "Tx1KtZT26sjtr%2F1tn0i0ea5161fXk0m8t0J7eWdWJsk1GBVTcGj%2B8zDIsbwQ8pibb461SlMf6mZ4LTTSqkUNyw%3D%3D";
	
	// 공공 데이터를 테스트하기 위한 간단한 테스트 환경 구성 => JUnit
	@Test
	public void testRun() throws IOException { // UnsupportedEncodingException의 부모인 IOException으로 예외처리
		
		// 1. OpenAPI 서버로 요청하고자 하는 url 만들기
		String url = "http://apis.data.go.kr/B552584/ArpltnInforInqireSvc/getCtprvnRltmMesureDnsty";
			   url += "?serviceKey=" + SERVICEKEY;
			   url += "&sidoName=" + URLEncoder.encode("서울", "UTF-8");
			   // 요청 시 전달값에 한글이 있을 경우 encoding 해야 함!
			   url += "&returnType=json";
			   
		// System.out.println(url);
		// 서비스키가 제대로 부여되지 않았을 경우
		// SERVICE_KEY_IS_NOT_REGISTERED_ERROR 발생함
			   
		// 2. HttpURLConnection 객체를 이용해서 OpenAPI 요청 절차
	    // 2_1. 요청하고자 하는 url 주소를 전달하면서 java.net.URL 객체 생성
	    URL requestUrl = new URL(url);
	    
	    // 2_2. 생성된 URL 객체를 가지고 HttpURLConnection 객체 생성
	    HttpURLConnection urlConnection = (HttpURLConnection)requestUrl.openConnection();
		
	    // 2_3. 요청에 필요한 Header 설정하기(get/post 방식 설정)
	    urlConnection.setRequestMethod("GET");
	    
	    // 2_4. 해당 OpenAPI 서버로 요청을 보낸 후 스트림을 통해 응답데이터 읽어들이기
	    BufferedReader br = new BufferedReader( new InputStreamReader (urlConnection.getInputStream()));
	    // 보조스트림은 단독 존재 불가!
	    // 보조스트림인 BufferedReader는 2바이트 사이즈의 문자스트림
	    // 기반스트림인 InputStream은 1바이트 사이즈의 바이트스트림
	    // 항상 보조스트림과 기반스트림 통로의 사이즈가 일치해야 함 => InputStramReader 객체를 통해 호환시켜 줌
	    
	    // 2_5. 반복적으로 매번 응답데이터를 한줄씩 읽어들이기
	    String line; // 기본적으로 null이 담겨 있음
	    
	    // 응답 데이터를 받아둘 변수 선언
	    String responseText = "";
	    
	    while((line = br.readLine()) != null) { // 더 이상 읽어들일 게 없을 때까지 반복
	    	
	    	// System.out.println(line);
	    	responseText += line; // 누적으로 문자열 연이어 붙이기
	    	
	    }
	    
	    // System.out.println(responseText);
	    
	    /*
	     * 개행이 안 들어가서 그렇지 이런 느낌입니다!
         * {
         *      "response":
         *          {
         *              "body":
         *                  {
         *                      "totalCount":40,
         *                      "items":
         *                          [
         *                              {
         *                                  "so2Grade":"1",
         *                                  "coFlag":null,
         *                                  "khaiValue":"92",
         *                                  "so2Value":"0.003",
         *                                  "coValue":"0.4",
         *                                  "pm10Flag":null,
         *                                  "o3Grade":"2",
         *                                  "pm10Value":"25",
         *                                  "khaiGrade":"2",
         *                                  "sidoName":"서울",
         *                                  "no2Flag":null,
         *                                  "no2Grade":"1",
         *                                  "o3Flag":null,
         *                                  "so2Flag":null,
         *                                  "dataTime":"2022-05-29 14:00",
         *                                  "coGrade":"1",
         *                                  "no2Value":"0.011",
         *                                  "stationName":"중구",
         *                                  "pm10Grade":"1",
         *                                  "o3Value":"0.080"
         *                              },
         *                              {
         *                                  "so2Grade":"1",
         *                                  "coFlag":null,
         *                                  "khaiValue":"67",
         *                                  "so2Value":"0.003",
         *                                  "coValue":"0.4",
         *                                  "pm10Flag":null,
         *                              ...
         *                              }
         *                          ],
         *                      "pageNo":1,
         *                      "numOfRows":10
         *                  },
         *              "header":
         *                  {
         *                      "resultMsg":"NORMAL_CODE",
         *                      "resultCode":"00"
         *                  }
         *          }
         *  }
         */
	    
	    // 생긴 것은 json 형식이나 엄밀히 말하면 String 타입의 데이터임
	    // JsonObject, JsonArray, JsonElement를 이용해서 "파싱 작업" 할 수 있음
	    // 기존의 흐름: VO에 담긴 내용물들을 JSON으로 가공
	    // 이번의 흐름: JSON에 담긴 내용물을 VO로 가공
	    
	    // 기존의 JSONObject, JSONArray랑은 엄밀히 다른 타입 (헷갈리지 말 것) => json.jar 파일에서 제공
	    // JsonObject, JsonArray, JsonElement => gson.jar 파일에서 제공
	    
	    // *JSON 테이터를 VO로 파싱하기
	    // 1) 각각의 item 정보를 얻어내기 위해 문자열 타입인 responseText 변수를 JsonObject타입으로 변환
	    JsonObject totalObj = JsonParser.parseString(responseText).getAsJsonObject();
	    
	    // 2) totalObj로부터 response라는 키값에 딸린 객체만 추출하기
	    JsonObject responseObj = totalObj.getAsJsonObject("response");
	    
	    // 3) responseObj로부터 body라는 키값에 딸린 객체만 추출하기
	    JsonObject bodyObj = responseObj.getAsJsonObject("body");
	    
	    // 4) bodyObj로부터 totalCount라는 키값에 딸린 데이터만 추출
	    int totalCount = bodyObj.get("totalCount").getAsInt();
	    // System.out.println(totalCount);
	    
	    // 5) bodyObj로부터 items라는 키값에 딸린 배열만 추출하기
	    JsonArray itemArr = bodyObj.getAsJsonArray("items");
	    // System.out.println(itemArr);
	    
	    // 6) itemArr로부터 반복을 돌려 가져 AirVO로 가공 후 ArrayList에 담기
	    ArrayList<AirVO> list = new ArrayList<>();
	    
	    for(int i = 0; i < itemArr.size(); i++) {
	    	
	    	// itemArr의 각 인덱스에 들은 자바 스크립트 객체를 또 추출
	    	JsonObject item = itemArr.get(i).getAsJsonObject();
	    	// System.out.println(item);
	    	
	    	AirVO air = new AirVO();
	    	// 시간상 3개의 필드만 list에 담아 볼 것
	    	air.setStationName(item.get("stationName").getAsString());
	    	air.setDataTime(item.get("dataTime").getAsString());
	    	air.setKhaiValue(item.get("khaiValue").getAsString());
	    	
	    	// 현재 khaiValue까지만 값이 나오고 다른 값들은 null!
	    	// 내가 넣어 주지 않았기 때문이므로 나머지 필드에 대해서도 가공한다면 모든 정보 파싱 가능!
	    	
	    	list.add(air);
	    }
	    
	    // ArrayList에 담긴 내용물 확인
	    for(AirVO a : list) { 
	    	System.out.println(a);
	    }

	    // 2_6. 다 사용한 스트림 반납 및 연결 끊기
	    br.close();
	    urlConnection.disconnect();
	}

}

저작자표시 비영리 변경금지 (새창열림)
'📗 self-study/📗 KH정보교육원 당산지원' 카테고리의 다른 글
  • [JavaScript] 화살표 함수(Lamda)
  • [OpenAPI] 가지고 온 공공 데이터를 화면에 뿌려 주기
  • [11/29 백업] 서버에 별점 올리니까 안 됨...
  • [11/29] 별점/신고
천재강쥐
천재강쥐
  • 천재강쥐
    디버거도 버거다
    천재강쥐
  • 전체
    오늘
    어제
    • Category (467)
      • 진짜 너무 궁금한데 이걸 나만 몰라...? (0)
      • 💾 Portfolio (2)
      • 🐤 CodingTest (28)
        • Java (20)
        • ᕕ(ꐦ°᷄д°᷅)ᕗ❌ (5)
      • 🚀 from error to study (142)
        • AI (1)
        • Cloud (2)
        • DB (12)
        • Front-End (16)
        • Github (14)
        • Java (39)
        • Mac (7)
        • Normal (29)
        • Server (22)
      • 📘 certificate (44)
        • 📘 리눅스마스터1급 (1)
        • 📘⭕️ 정보처리기사 (40)
        • 📘⭕️ SQLD (3)
      • 📗 self-study (234)
        • 📗 inflearn (35)
        • 📗 생활코딩 (8)
        • 📗 KH정보교육원 당산지원 (190)
      • 🎨 Scoop the others (0)
        • 📖 Peeking into other people.. (0)
        • 🇫🇷 (0)
        • 📘⭕️ 한국사능력검정시험 심화 (11)
        • 오블완 (4)
  • 인기 글

  • hELLO· Designed By정상우.v4.10.1
천재강쥐
[OpenAPI] 공공데이터의 개요와 가공 및 활용
상단으로

티스토리툴바