빅데이터 Java 개발자 교육 - 11일차 [REST API]

Jun_Gyu·2023년 2월 26일
0
post-thumbnail

11일차의 힘찬 아침!

오늘은 REST api를 이용하여 데이터베이스로 자료를 주고받는 실습을 해볼것이다.

REST, REST API란?

출처

- REST

“Representational State Transfer” 의 약자로써,

자원을 이름(자원의 표현)으로 구분하여 해당 자원의 상태(정보)를 주고 받는 모든 것을 의미한다.

- REST API

REST API에서 API(Application Programming Interface)란 데이터와 기능의 집합을 제공하여 컴퓨터 프로그램간 상호작용을 촉진하며, 서로 정보를 교환가능 하도록 하는 것이며,

REST 기반으로 서비스 API를 구현한 것이다.



최근 OpenAPI(누구나 사용할 수 있도록 공개된 API: 구글 맵, 공공 데이터 등), 마이크로 서비스(하나의 큰 애플리케이션을 여러 개의 작은 애플리케이션으로 쪼개어 변경과 조합이 가능하도록 만든 아키텍처) 등을 제공하는 업체 대부분은 REST API를 제공한다.


이처럼 REST API를 이용해 서버에 접속하여 필요로 하는 정보를 데이터베이스에 저장하여 프로그래밍을 통해 연동을 시켜 내가 사용하고자 하는 정보를 사용할 수 있겠다.

REST API의 사용에 대해서 이해를 돕고자 예시로 아래의 소스코드를 작성하였다.

package day11;

import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;

// rest api 서버 
// 정보를 제공해주는 문서의 종류, xml, json ... (문서에 대한 이해 필요)
// 영화진흥원 현재 상영하고 있는 영화정보를 제공해줌.
// 카카오 결제를 위한 정보를 제공해줌.
// 모든 정보 가능

// http://------------/json/exam1.json

// rest api 서버에 접속해서 정보를 받아오는 기능을 하는 라이브러리 okhttp3
public class RestClient1 {

	// 접속해서서 정보를 받아올 rest 서버 주소.
	final String URL = "http://---------------/json/exam1.json";

	public RestClient1() {
		try {
			// 라이브러리를 제공한 곳의 문서 참고
			// 1. 클라이언트 객체 생성
			OkHttpClient client = new OkHttpClient();
			// 2. 요청 정보 객체 만들기
			Request request = new Request.Builder().url(URL).get().build();
			// 3. 1과 2를 이용한 요청 후에 결과받기
			Response response = client.newCall(request).execute();

			// 결과를 잘 받았는지 확인
			if (response.isSuccessful()/* == true */) { // isSuccessful은 boolean타입
				// 실제로 받은 정보를 문자변수 strData에 저장.
				String strData = response.body().string().toString(); // 질문) .string()이후 .toString()하는 이유는??
				// 콘솔에 확인하기
				System.out.println(strData); // {"ret":"y","data":"123"}
			}

		} // 위의 방법으로 어떠한 rest서버에 접속해서 정보를 받아올 수 있다!
		catch (Exception e) {
			e.printStackTrace();
		}

	}

}

강사님이 지정해주신 주소에 있는 값을 직접 불러오는코드이다.

주소에 IP값이 포함되어있기에 따로 공개할 수는 없지만,

이를 출력하게 되면

라고 출력이 되게 된다. 이는 곧

위와 같은 클래스 하나라고 볼 수 있다.

이번에는 위의 자료를 형식별로 분류해보도록하자.

	// 필요한 데이터만 꺼냄 변수명X
	// JSONObject == Map (키를 통해 데이터 꺼내기!)
	JSONObject jobj = new JSONObject(strData);
	String ret = jobj.getString("ret");
	int data = jobj.getInt("data");

	// 콘솔에 확인하기
	System.out.println(strData);
	System.out.println(ret);
	System.out.println(data);

위의 코드를 실행할 시

사진처럼 정보들을 하나하나 분류하여 꺼낼 수 있게된다.

이러한 정보를 바탕으로 DB에 저장하여 필요할때마다 사용할 수 있겠다.



현재 위의 url로 접속하면

{"ret" : "y", "data":"123"}

과 같이 나오게 되는데, 이를 좀 더 보기 쉽게 하기 위하여 Chrome 확장자를 설치하였다.

위의 확장자를 설치하면

사진과같이 보기 좀 더 쉽게 나타내준다.

이번에는 다른 자료를 행렬로 나타내보겠다. 위와 같이 코드를 짜준 뒤 메인에서실행을 시키게 되면

package day11;

import org.json.JSONArray;
import org.json.JSONObject;

import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;

public class RestClient2 {

	final String URL = "http://--------------/json/exam2.json";
	private String data = null;

	// 데이터를 받아와서 문자열 변수에 보관
	public RestClient2() {
		try {
			/*------------------------------------------------------------*/
			OkHttpClient client = new OkHttpClient();
			Request request = new Request.Builder().url(URL).get().build();
			Response response = client.newCall(request).execute();
			/*------------------------------------------------------------*/

			if (response.isSuccessful()) {
				// 실제로 받은 정보를 문자변수 data에 저장.
				this.data = response.body().string().toString();
				System.out.println(this.data);
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
	}
	
	// [{"ret":"y1","data":"123"},{"ret":"y2","data":"234"}]
	public void parseData() {
		// JSONArray == ArrayList
		JSONArray jary = new JSONArray (this.data);
		for(int i=0; i<jary.length(); i++) { // 2번 반복함
			JSONObject jobj =  jary.getJSONObject(i);
			String tmp1 = jobj.getString("ret");
			int tmp2 = jobj.getInt("data");
					
			System.out.println(tmp1);
			System.out.println(tmp2);
			System.out.println("------------------");
			
		}
	}
}

와 같이 나오게 된다. 여기서 중요한것은
JSONObject == Map (키를 통해 데이터 꺼내기!)

으로, Map과 같은 방식을 취한다는것이다. '<key, value>'

따라서 필요한 정보를 꺼내고자 할 때 해당 정보의 key값을 불러와야 한다.


이번에는 좀 더 복잡한 내용으로 실습을해보겠다.

위를 바탕으로 코드를 구생해보자.

package day11;

import org.json.JSONArray;
import org.json.JSONObject;

import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;

public class RestClient7 {

	final String URL = "http://------------/json/exam7.json";
	private String data = null;

	public RestClient7() {
		try {
			OkHttpClient client = new OkHttpClient();
			Request request = new Request.Builder().url(URL).get().build();
			Response response = client.newCall(request).execute();

			if (response.isSuccessful()) {
				this.data = response.body().string().toString();
			}
		} catch (Exception e) {
			e.printStackTrace();
		}

	}// string, string

	public void parseData() {
		JSONObject jobj = new JSONObject(this.data); // JSONObject인 이유 -> data 안에 여러가지 타입이 있기 때문.

		String ret = jobj.getString("ret"); // 데이터의 성공유무를 알려주는 변수
		String ret1 = new String("y"); // 실제 데이터

		JSONArray jary = jobj.getJSONArray("data");
		if (ret.equals(ret1)) {
			for (int i = 0; i < jary.length(); i++) { // 5번반복 (정보5개)

				JSONObject jobj1 = jary.getJSONObject(i); // 첫번째~5번째

				System.out.println(jobj1.getString("id"));
				System.out.println(jobj1.getString("name"));
				System.out.println(jobj1.getInt("age"));
				System.out.println(jobj1.getFloat("height"));
				System.out.println(jobj1.getFloat("weight"));
				System.out.println("------------------");

			}

		}

	}

}

위를 실행시키면

와 같이 나오게 된다. 이번에는 DB로 자료를 옮겨주기 위해서 한번 작업을 해보자.

package day11;

import lombok.Data;

// 주로 사용하는 getter setter toString, 생성자.. 등을 한번에.
@Data
public class Member1 {

	private String id = null;
	private String name = null;
	private int age = 0;
	private float height = 0.0f;
	private float weight = 0.0f;
}

먼저 위의 정보들을 넣어 줄 클래스를 만든 뒤,

전송받은 데이터들을 DB로 반환시켜 저장시킬 메소드를 만든다.

public List<Member1> parseData1() {
		// 1. 리턴할 빈 객체를 생성
		List<Member1> list = new ArrayList<>();

		JSONObject jobj = new JSONObject(this.data);
		String ret = jobj.getString("ret"); //
		JSONArray jary = jobj.getJSONArray("data"); // [{0},{1},{2},{3},{4}]

		if (ret.equals("y")) {
			for (int i = 0; i < jary.length(); i++) {
				// JSONObject => Member1로 복사하기
				// jobj1 => m1로 복사

				JSONObject jobj1 = jary.getJSONObject(i);

				// 2. 리턴할 빈공간 생성 후 정보 담기
				Member1 m1 = new Member1();
				m1.setId(jobj1.getString("id"));
				m1.setName(jobj1.getString("name"));
				m1.setAge(jobj1.getInt("age"));
				m1.setHeight(jobj1.getFloat("height"));
				m1.setWeight(jobj1.getFloat("weight"));

				// 3. 빈 객체에 담은 정보 넣기
				list.add(m1);
			}

		}
		return list;
	}

위를 메인클래스에 실행시켜보자.

import java.util.List;

public class Main {

	public static void main(String[] args) {
		RestClient7 obj3 = new RestClient7();
		 obj3.parseData1(); // parseData1은 List<Member1>의 형태이기때문에 아래와 같이 객체를 지정해줘야 함.
	  //----------------------------------------
		 List<Member1> list = obj3.parseData1();
		 for(Member1 m : list) { // for (한개 꺼냈을때 타입 m: 리스트변수){
			 System.out.println(m.getId());
			 System.out.println(m.getName());
			 System.out.println(m.getAge());
			 System.out.println(m.getHeight());
			 System.out.println(m.getWeight());
			 System.out.println("------------------"); 
		 }
}

해당 코드의 경우에는

parseData1자체를 List<Member1>의 형태로 만들었기 때문에 메인클래스에서도 똑같은 타입으로 List객체를 생성해준 뒤 값을 출력시켰다.

이번에는 조금 더 심화과정으로 들어가보도록 haza.



이번에는 Object 안에 score라는 항목이 들어가있는 형태이다. 큰 흐름은 위와 같지만 수학 영어 국어의 각 점수를 도출하기 위해서는 score라는 Object를 따로 지정한 뒤 값을 불러와야 한다.

먼저 정보의 형태를 저장하고자 틀이 될 클래스를 만들어 준 뒤,

// 코드가 너무 길어 해당 메소드만 올림. (생성자, import 등등 기존에 들어가야 하는 부분들은 위와 동일함.)

public void parseData() {
		try {
			JSONObject jobj = new JSONObject(this.data);
			String ret = jobj.getString("ret");
			JSONArray jary = jobj.getJSONArray("data"); // data에 여러 정보가 있기때문에 Array로 받음.
			// [{0},{1},{2},{3},{4}]
			System.out.println("ㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡ");
			if (ret.equals("y")) {
				for (int i = 0; i < jary.length(); i++) { // 5번 왕복

					JSONObject jobj1 = jary.getJSONObject(i); // 한개 꺼내기
					// {"id": "id1", "name": "가나다1", "age"; 31, "score": {"math: 50, "eng": 90,
					// "kor": 69}}
					String id = jobj1.getString("id");
					String name = jobj1.getString("name");
					int age = jobj1.getInt("age");

					// {"math: 50, "eng": 90, "kor": 69}
					JSONObject score = jobj1.getJSONObject("score"); 
					int math = score.getInt("math");
					int eng = score.getInt("eng");
					int kor = score.getInt("kor");

					System.out.println(id + "," + name + "," + age + "," + math + "," + eng + "," + kor);
					System.out.println("ㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡ");
				}
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

각 과목의 점수를 세부적으로 나타내기 위해서

위와같이 코드를 구성하였다. 이를 메인에서 실행시키면..


와 같이 출력된다.

하지만 위의 코드는 void타입으로, 반환하지 않는 메소드이다.

DB에 저장하기위해서는 메소드의 코드를 List타입으로 아래와 같이 구성해주어야 한다.

public List<Score1> parseData1() {
		// 1. 반환 객체 만들기
		List<Score1> list = new ArrayList<>();
		JSONObject jobj = new JSONObject(this.data);
		JSONArray jary = jobj.getJSONArray("data");

		// 실제 저장된 객체에서 Score1객체로 1개씩 복사
		for (int i = 0; i < jary.length(); i++) {
			JSONObject jobj1 = jary.getJSONObject(i);
			Score1 s1 = new Score1();

			s1.setId(jobj1.getString("id"));
			s1.setName(jobj1.getString("name"));
			s1.setAge(jobj1.getInt("age"));

			JSONObject score = jobj1.getJSONObject("score");

			s1.setMath(score.getInt("math"));
			s1.setEng(score.getInt("eng"));
			s1.setKor(score.getInt("kor"));

			// 반환할 객체에 Score1객체 추가
			list.add(s1);
		}
		return list;

	}

그리고 메인에서 List를 불러와 실행시켜보자.

import java.util.List;

public class Main {

	public static void main(String[] args) {
        RestClient10 obj4 = new RestClient10();
		List<Score1> list = obj4.parseData1();
		System.out.println("------------------------");
		for (Score1 s : list) {
			System.out.println("id : " + s.getId());
			System.out.println("이름 : " + s.getName());
			System.out.println("나이 : " + s.getAge());
			System.out.println("수학점수 : " + s.getMath());
			System.out.println("영어점수  : " + s.getEng());
			System.out.println("국어점수 : " + s.getKor());
			System.out.println("------------------------");
		 }
	}
}

와 같이 구성하면 결과는 아래와 같이 도출된다.

(JSon과 OKHttp는 앞으로도 웹에서 계속 쓸것이니 매우 중요함!!)

profile
시작은 미약하지만, 그 끝은 창대하리라

0개의 댓글