본문 바로가기
네이버클라우드/JAVA 웹 프로그래밍

JAVA 29일차 (2023-07-03) 자바 기초 DAY27_자바 프로그래밍_JSON(Gson 라이브러리와 Jackson 라이브러리)

by prometedor 2023. 7. 3.
- 자바 프로그래밍(com.eomcs.openapi.json)
  - Gson 라이브러리 사용법
  - Jackson 라이브러리 사용법

 

JSON

Gson 과 Jackson

Gson 라이브러리 추가

com.eomcs.openapi.json.gson

Exam0100.java

ㄴ 해당 코드 복사

 

ㄴ 빌드 스크립트 파일에 추가

 

ㄴ Gradle 재설정해주기

 

ㄴ 라이브러리 추가됨을 확인

 

com.eomcs.openapi.json.gson

Exam0110.java

// 객체 --> JSON 문자열 : 객체의 필드 값을 json 형식의 문자열로 만들기
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import com.google.gson.Gson;

public class Exam0110 {
  public static void main(String[] args) {

    // 1) 객체 준비
    Member m = new Member();
    m.setNo(100);
    m.setName("홍길동");
    m.setEmail("hong@test.com");
    m.setPassword("1111");
    m.setPhoto("hong.gif");
    m.setTel("010-2222-1111");
    m.setRegisteredDate(new Date(System.currentTimeMillis()));

    // 2) JSON 처리 객체 준비
    Gson gson = new Gson();

    // 3) 객체의 값을 JSON 문자열로 얻기
    String jsonStr = gson.toJson(m);

    System.out.println(jsonStr);
  }
}

// JSON 객체 형식 - { 객체 정보 }
// => { "프로퍼티명" : 값, "프로퍼티명": 값, ...}
// 
// 값:
// - 문자열 => "값"
// - 숫자   => 값
// - 논리   => true, false
//
// 프로퍼티명은 반드시 문자열로 표현해야 한다.

 

Member.java

ㄴ 필드명을 "nm" 으로 변경

프로퍼티명과 필드명이 다른 경우 필드 이름으로 출력됨

 

 

jackson 라이브러리 추가

ㄴ 해당 코드 복사

ㄴ 빌드 스크립트 파일에 복사한 코드 붙여넣기

ㄴ 라이브러리 추가됨을 확인

 

com.eomcs.openapi.json.jackson

Member.java

ㄴ 필드 이름을 nm 으로 변경

 

프로퍼티명과 필드명이 다른 경우 프라퍼티(getter, setter)명에서 set/get 제거 후 나머지 메서드명에서 첫 번째 알파벳을 속문자로 한 이름으로 출력됨

 

결론 => 필드명과 프러퍼티 명을 다르게 하지말자

 

 

com.eomcs.openapi.json.gson

Exam0120.java

// JSON 문자열 --> 객체 : JSON 문자열을 해석하여 객체를 생성하기
package com.eomcs.openapi.json.gson;

import com.google.gson.Gson;

public class Exam0120 {
  public static void main(String[] args) {

    // 1) JSON 문자열 준비
    String jsonStr = "{\"no\":100,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"password\":\"1111\",\"photo\":\"hong.gif\",\"tel\":\"010-2222-1111\",\"registeredDate\":\"7월 3, 2023\"}";

    // 2) JSON 처리 객체 준비
    Gson gson = new Gson();

    // 3) JSON 문자열을 가지고 객체 만들기
    Member m = gson.fromJson(jsonStr, Member.class);

    System.out.println(m);
  }
}

ㄴ JSON 문자열에서 날짜 데이터 형식은 "7월 3, 2023" 이 기본

 

날짜 형식을 yyyy-MM-dd 로 변경하여 저장하려고 할 경우

=>

ㄴ 예외 발생

 

gson 날짜 데이터 형식

=>

com.eomcs.openapi.json.gson

Exam0130.java

// JSON 문자열 --> 객체 : JSON 문자열에는 클래스 정보가 없다.
package com.eomcs.openapi.json.gson;

import com.google.gson.Gson;

public class Exam0130 {
  public static void main(String[] args) {

    // 1) JSON 문자열 준비
    String jsonStr = "{\"no\":100,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"password\":\"1111\",\"photo\":\"hong.gif\",\"tel\":\"010-2222-1111\",\"registeredDate\":\"7월 3, 2023\"}";

    // 2) JSON 처리 객체 준비
    Gson gson = new Gson();

    // 3) JSON 문자열을 가지고 객체 만들기
    // - JSON 문자열에서 프로퍼티 이름과 일치하는 필드가 객체에 있다면 값을 설정해 준다. 
    // - 예)
    //   JSON 문자열     ------>   Board 객체
    //     no                         no
    //     name                       X
    //     email                      X
    //     password                   X
    //     photo                      X
    //     tel                        X
    //     registeredDate             registeredDate
    // 
    Board b = gson.fromJson(jsonStr, Board.class);

    System.out.println(b);
  }
}

Board.java

Member.java

ㄴ jsonStr 에 적은 필드명이 생성하려는 Board 객체의 클래스의 프로퍼티명과 다르면 null 출력됨 (해당 클래스에 존재하는 no, registeredDate 만 출력됨)

=> JSON 문자열에서 프로퍼티 이름과 일치하는 필드가 객체에 있다면 값을 설정해 줌

 

 

Gson 에서 날짜 다루기

com.eomcs.openapi.json.gson

gson 패키지의 Exam0111.java 

// 객체 --> JSON 문자열 : 객체의 필드 값을 json 형식의 문자열로 만들기
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;

public class Exam0110 {
  public static void main(String[] args) {

    // 1) 객체 준비
    Member m = new Member();
    m.setNo(100);
    m.setName("홍길동");
    m.setEmail("hong@test.com");
    m.setPassword("1111");
    m.setPhoto("hong.gif");
    m.setTel("010-2222-1111");
    m.setRegisteredDate(new Date(System.currentTimeMillis()));

    // // 2) JSON 처리 객체 준비
    // Gson gson = new Gson();

    // GsonBuilder builder = new GsonBuilder();
    // builder.setDateFormat("yyyy-MM-dd");
    // Gson gson = builder.create();
	
    Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd").create();

    // 3) 객체의 값을 JSON 문자열로 얻기
    String jsonStr = gson.toJson(m);

    System.out.println(jsonStr);
  }
}

// JSON 객체 형식 - { 객체 정보 }
// => { "프로퍼티명" : 값, "프로퍼티명": 값, ...}
//
// 값:
// - 문자열 => "값"
// - 숫자 => 값
// - 논리 => true, false
//
// 프로퍼티명은 반드시 문자열로 표현해야 한다.

ㄴ com.eomcs.openapi.json.gson 패키지의 Exam0110.java 활용하여 Exam0111.java 생성

ㄴ GsonBuilder 이용하여 Gson 객체 생성

ㄴ setDateFormat 메서드를 사용하여 날짜 형식을 지정

ㄴ create 메서드를 호출하여 Gson 객체 생성

 

com.eomcs.openapi.json.gson

Exam0121.java

ㄴ 타입 오류

=>

com.eomcs.openapi.json.gson

Exam0121.java

ㄴ Gson 객체를 생성해줄 도우미 객체 GsonBuilder 클래스 이용

 

com.eomcs.openapi.json.gson

Exam0112.java

// 객체 --> JSON 문자열 : 객체의 필드 값을 json 형식의 문자열로 만들기
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.sql.Date;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonElement;
import com.google.gson.JsonPrimitive;
import com.google.gson.JsonSerializationContext;
import com.google.gson.JsonSerializer;

public class Exam0112 {
  public static void main(String[] args) {

    // 1) 객체 준비
    Member m = new Member();
    m.setNo(100);
    m.setName("홍길동");
    m.setEmail("hong@test.com");
    m.setPassword("1111");
    m.setPhoto("hong.gif");
    m.setTel("010-2222-1111");
    m.setRegisteredDate(new Date(System.currentTimeMillis()));

    // // 2) JSON 처리 객체 준비
    // Date 타입의 값을 내보내고 가져올 때 사용할 변환 도구를 준비
    class GsonDateFormatAdapter implements JsonSerializer<Date> {

      private DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");

      @Override
      public JsonElement serialize(Date src, Type typeOfSrc, JsonSerializationContext context) {
        // 객체를 JSON 문자열로 변환할 때 호출된다.
        // 그 중 Date 타입의 프로퍼티 값을 JSON 문자열로 바꿀 때 호출된다.
        // String str = dateFormat.format(src);
        // // System.out.println(str);  => 확인용
        // return new JsonPrimitive(str);
        
        System.out.println(src.getTime());
        return new JsonPrimitive(dateFormat.format(src));
      }
    }

    // Gson 객체를 만들어 줄 도우미 객체
    GsonBuilder builder = new GsonBuilder();

    // Date 타입의 프로퍼티 값을 JSON 형식의 문자열로 바꿔줄 변환기를 등록한다.
    builder.registerTypeAdapter(
        Date.class, // 원래 데이터의 타입
        new GsonDateFormatAdapter() // Date 형식의 데이터를 JSON 문자열로 바꿔줄 변환
    );
    
    Gson gson = builder.create();

    // 3) 객체의 값을 JSON 문자열로 얻기
    String jsonStr = gson.toJson(m);

    System.out.println(jsonStr);
  }
}

// JSON 객체 형식 - { 객체 정보 }
// => { "프로퍼티명" : 값, "프로퍼티명": 값, ...}
//
// 값:
// - 문자열 => "값"
// - 숫자 => 값
// - 논리 => true, false
//
// 프로퍼티명은 반드시 문자열로 표현해야 한다.

ㄴ GsonDateFormatAdapter 클래스 이용 (JsonSerializer<Date> 인터페이스를 구현)

ㄴ Gson 객체를 만들어줄 도우미 객체 GsonBuilder 이용

ㄴ registerTypeAdapter 메서드를 사용하여 Date 타입의 값을 JSON 문자열로 변환하는 GsonDateFormatAdapter를 등록

=> Gson은 Date 타입의 프로퍼티 값을 JSON 문자열로 변환할 때 GsonDateFormatAdapter의 serialize 메서드를 호출하여 변환을 수행

ㄴ GsonBuilder를 사용하여 설정한 날짜 형식이 포함된 Gson 객체가 생성됨
ㄴ Member 객체를 toJson 메서드를 사용하여 JSON 문자열로 변환하여 JSON 문자열을 출력


=>  GsonDateFormatAdapter를 사용하여 Date 타입의 값을 지정된 날짜 형식으로 JSON 문자열로 변환

 

 

익명 클래스 사용

com.eomcs.openapi.json.gson

Exam0113.java

// 객체 --> JSON 문자열 : 객체의 필드 값을 json 형식의 문자열로 만들기
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.sql.Date;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonElement;
import com.google.gson.JsonPrimitive;
import com.google.gson.JsonSerializationContext;
import com.google.gson.JsonSerializer;

public class Exam0113 {
  public static void main(String[] args) {

    // 1) 객체 준비
    Member m = new Member();
    m.setNo(100);
    m.setName("홍길동");
    m.setEmail("hong@test.com");
    m.setPassword("1111");
    m.setPhoto("hong.gif");
    m.setTel("010-2222-1111");
    m.setRegisteredDate(new Date(System.currentTimeMillis()));

    // // 2) JSON 처리 객체 준비
    DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
    GsonBuilder builder = new GsonBuilder();
    builder.registerTypeAdapter(Date.class, new JsonSerializer<Date>() {
      @Override
      public JsonElement serialize(Date src, Type typeOfSrc, JsonSerializationContext context) {
        return new JsonPrimitive(dateFormat.format(src));
      }
    });

    Gson gson = builder.create();

    // 3) 객체의 값을 JSON 문자열로 얻기
    String jsonStr = gson.toJson(m);

    System.out.println(jsonStr);
  }
}

// JSON 객체 형식 - { 객체 정보 }
// => { "프로퍼티명" : 값, "프로퍼티명": 값, ...}
//
// 값:
// - 문자열 => "값"
// - 숫자 => 값
// - 논리 => true, false
//
// 프로퍼티명은 반드시 문자열로 표현해야 한다.

ㄴ Exam0112.java -> Exam0113.java 익명 클래스로 바꾸기 

ㄴ Member 객체를 생성하고, JSON 처리를 위한 Gson 객체를 생성

ㄴ DateFormat 클래스를 사용하여 날짜 형식을 지정하고, GsonBuilder를 통해 Date 타입의 필드 값을 JSON 문자열로 변환하는 JsonSerializer를 등록
ㄴ JsonSerializer는 serialize 메서드를 오버라이딩하여 원하는 형식으로 Date 값을 JSON 문자열로 변환

     => dateFormat.format(src)를 사용하여 Date 값을 원하는 형식의 문자열로 변환한 후, JsonPrimitive로 감싸서 반환
ㄴ gson.toJson(m)을 호출하여 Member 객체의 필드 값을 JSON 형식의 문자열로 얻어와 출력

 

 

com.eomcs.openapi.json.gson

Exam0122.java

// JSON 문자열 --> 객체 : JSON 문자열을 해석하여 객체를 생성하기
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.sql.Date;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonParseException;

public class Exam0122 {
  public static void main(String[] args) {

    // 1) JSON 문자열 준비
    String jsonStr =
        "{\"no\":100,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"password\":\"1111\",\"photo\":\"hong.gif\",\"tel\":\"010-2222-1111\",\"registeredDate\":\"2023-07-03\"}";

    // 2) JSON 처리 객체 준비
    class GsonDateFormat implements JsonDeserializer<Date> {
      @Override
      public Date deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context)
          throws JsonParseException {
        // JSON 문자열을 자바 타입의 값으로 바꿀 때 호출된다.
        // 특히 Date 타입의 값으로 바꿀 때 호출된다.
        String strValue = json.getAsString();
        return Date.valueOf(strValue); // yyyy-MM-dd ==> Date
      }
    }

    GsonBuilder builder = new GsonBuilder();
    builder.registerTypeAdapter(Date.class, new GsonDateFormat());
    Gson gson = builder.create();

    // 3) JSON 문자열을 가지고 객체 만들기
    Member m = gson.fromJson(jsonStr, Member.class);

    System.out.println(m);
  }
}

ㄴ Exam0121.java 복사하여 Exam0122.java 생성 후 수정

ㄴ JSON 문자열을 해석하여 Member 객체를 생성

ㄴ GsonDateFormat 클래스를 정의하여 JsonDeserializer<Date> 인터페이스를 구현

     => 이 인터페이스는 JSON 문자열을 자바 타입의 값으로 변환할 때 호출되는 메서드인 deserialize을 오버라이딩하여 구현

ㄴ Date 타입의 값을 해석하기 위해 문자열을 Date 객체로 변환

ㄴ GsonBuilder를 생성하고 registerTypeAdapter 메서드를 사용하여 Date.class와 GsonDateFormat 객체를 등록

     ㄴ Date.class를 사용하면 Date 클래스의 타입 정보를 얻을 수 있음

          => 이를 통해 Gson 라이브러리에서 Date 타입의 필드 값을 직렬화(serialization)하거나 역직렬화(deserialization)할 때 특별한 처리를 할 수 있음

=> Gson 객체가 JSON 문자열에서 Date 타입의 필드 값을 해석할 때 GsonDateFormat 객체의 deserialize 메서드가 호출되도록 설정

ㄴ gson.fromJson(jsonStr, Member.class)을 호출하여 JSON 문자열을 해석하여 Member 객체를 생성

ㄴ 생성된 객체는 변수 m에 할당되고 출력됨

 

 

com.eomcs.openapi.json.gson

Exam0123.java

// JSON 문자열 --> 객체 : JSON 문자열을 해석하여 객체를 생성하기
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.sql.Date;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonParseException;

public class Exam0123 {
  public static void main(String[] args) {

    // 1) JSON 문자열 준비
    String jsonStr =
        "{\"no\":100,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"password\":\"1111\",\"photo\":\"hong.gif\",\"tel\":\"010-2222-1111\",\"registeredDate\":\"2023-07-03\"}";

    // 2) JSON 처리 객체 준비
    GsonBuilder builder = new GsonBuilder();
    builder.registerTypeAdapter(Date.class, new JsonDeserializer<Date>() {
      @Override
      public Date deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context)
          throws JsonParseException {
        return Date.valueOf(json.getAsString()); // yyyy-MM-dd ==> Date
      }
    });
    Gson gson = builder.create();

    // 3) JSON 문자열을 가지고 객체 만들기
    Member m = gson.fromJson(jsonStr, Member.class);

    System.out.println(m);
  }
}

ㄴ Exam0122.java 를 복사하여 Exam0123.java 를 생성 후 수정

ㄴ 익명 클래스로 구현하기 

ㄴ JSON 문자열 준비
    ㄴ jsonStr 변수에 JSON 형식의 문자열을 준비

    ㄴ 이 문자열은 Member 객체를 나타내며 필드에 대한 정보를 포함함
ㄴ JSON 처리 객체 준비
    ㄴ Gson 객체를 생성하기 전에 GsonBuilder를 사용하여 JSON 처리에 필요한 설정을 구성함

    ㄴ registerTypeAdapter 메서드를 사용하여 Date.class와 JsonDeserializer<Date>를 등록함
ㄴ Date.class 는 java.util.Date 클래스의 타입 정보

    => Gson은 이 타입 정보를 활용하여 Date 타입의 필드 값을 역직렬화할 때 특별한 변환기를 사용
ㄴ JsonDeserializer<Date> 는 Gson에서 JSON 문자열의 Date 타입 필드 값을 역직렬화할 때 호출되는 변환기

ㄴ deserialize 메서드를 오버라이딩하여 JSON 문자열을 Date 객체로 변환하는 작업을 수행

    ㄴ Date.valueOf() 메서드를 사용하여 문자열을 Date 객체로 변환
ㄴ JSON 문자열을 가지고 객체 만들기
    ㄴ Gson 객체를 생성하고, fromJson 메서드를 사용하여 JSON 문자열을 Member 객체로 역직렬화 함

    ㄴ Gson은 등록된 변환기를 활용하여 JSON 문자열을 객체의 필드 값으로 변환함

ㄴ 변환된 Member 객체는 m 변수에 저장됨
ㄴ 결과 출력:
    ㄴ Member 객체인 m을 출력하여 확인


=> deserialize 메서드를 직접 오버라이딩하여 JSON 문자열의 registeredDate 필드 값을 Date 객체로 변환함

=> 변환된 Member 객체는 System.out.println(m)을 통해 출력됨

 

 

com.eomcs.openapi.json.gson

Exam0210.java

// 객체 --> JSON 문자열 : 배열 다루기
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import com.google.gson.Gson;

public class Exam0210 {
  public static void main(String[] args) {

    // 1) 배열 준비
    Member m1 = new Member();
    m1.setNo(101);
    m1.setName("홍길동");
    m1.setEmail("hong@test.com");
    m1.setRegisteredDate(new Date(System.currentTimeMillis()));

    Member m2 = new Member();
    m2.setNo(102);
    m2.setName("임꺽정");
    m2.setEmail("leem@test.com");
    m2.setRegisteredDate(new Date(System.currentTimeMillis()));

    Member m3 = new Member();
    m3.setNo(103);
    m3.setName("안창호");
    m3.setEmail("ahn@test.com");
    m3.setRegisteredDate(new Date(System.currentTimeMillis()));

    Member[] members = {m1, m2, m3};

    String jsonStr = new Gson().toJson(members);

    System.out.println(jsonStr);
  }
}

// JSON 배열 형식 - [{ 객체 정보 },{ 객체 정보}, ...]
// => [
//      {"프로퍼티명":값,"프로퍼티명":값, ...}, 
//      {"프로퍼티명":값,"프로퍼티명":값, ...},
//      {"프로퍼티명":값,"프로퍼티명":값, ...},
//      ...
//    ]
//

ㄴ json 문자열에 [] 가 등장하면 무조건 배열임

 

com.eomcs.openapi.json.gson

Exam0220.java

// JSON 문자열 --> 객체 : 배열 다루기
package com.eomcs.openapi.json.gson;

import com.google.gson.Gson;

public class Exam0220 {
  public static void main(String[] args) {

    String jsonStr = "[{\"no\":101,\"name\":\"홍길동\"},{\"no\":102,\"name\":\"임꺽정\"},{\"no\":103,\"name\":\"안창호\"}]";

    Member[] members = new Gson().fromJson(jsonStr, Member[].class);

    for (Member m : members) {
      System.out.println(m);
    }
  }
}

ㄴ JSON 배열 형식의 문자열인 jsonStr을 Member 배열로 변환하여 출력

 

 

com.eomcs.openapi.json.gson

Exam0310.java

// 객체 --> JSON 문자열 : 컬렉션 다루기
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import java.util.ArrayList;
import com.google.gson.Gson;

public class Exam0310 {
  public static void main(String[] args) {

    // 1) ArrayList 준비
    Member m1 = new Member();
    m1.setNo(101);
    m1.setName("홍길동");
    m1.setEmail("hong@test.com");
    m1.setRegisteredDate(new Date(System.currentTimeMillis()));

    Member m2 = new Member();
    m2.setNo(102);
    m2.setName("임꺽정");
    m2.setEmail("leem@test.com");
    m2.setRegisteredDate(new Date(System.currentTimeMillis()));

    Member m3 = new Member();
    m3.setNo(103);
    m3.setName("안창호");
    m3.setEmail("ahn@test.com");
    m3.setRegisteredDate(new Date(System.currentTimeMillis()));

    ArrayList<Member> list = new ArrayList<>();
    list.add(m1);
    list.add(m2);
    list.add(m3);

    String jsonStr = new Gson().toJson(list);

    System.out.println(jsonStr);
  }
}

// JSON 컬렉션 형식 - [{ 객체 정보 },{ 객체 정보 }, ...]
// => 배열을 출력한 것과 같다.
//    JSON은 배열과 컬렉션을 구분하지 않는다.
// => [
//      {"프로퍼티명":값,"프로퍼티명":값, ...},
//      {"프로퍼티명":값,"프로퍼티명":값, ...},
//      {"프로퍼티명":값,"프로퍼티명":값, ...},
//      ...
//    ]
//

ㄴ 배열을 출력한 것과 같음
=> JSON은 배열과 컬렉션을 구분하지 않음

 

com.eomcs.openapi.json.gson

Exam0320.java

// JSON 문자열 --> 객체 : 컬렉션 다루기
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.util.Collection;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;

public class Exam0320 {
  public static void main(String[] args) {

    String jsonStr = "[{\"no\":101,\"name\":\"홍길동\"},{\"no\":102,\"name\":\"임꺽정\"},{\"no\":103,\"name\":\"안창호\"}]";

    // 1) TypeToken 클래스의 서브 클래스를 만든다.
    class MyTypeToken extends TypeToken<Collection<Member>> {
      // 수퍼 클래스를 지정할 때 제네릭의 타입을 설정한다.
      // TypeToken 클래스에는 Type 인터페이스의 구현체를 만드는 메서드가 있기 때문에 
      // 이 클래스의 서브 클래스를 만드는 것이다.
      // 타입 파라미터에 컬렉션 타입을 전달하는 목적 이외에는 다른 이유가 없다.
      // 그래서 서브 클래스에 뭔가를 추가할 필요가 없다.
    }

    // 2) TypeToken 객체 준비 
    MyTypeToken typeToken = new MyTypeToken();

    // 3) TypeToken 객체를 통해 Type 구현체를 얻는다.
    Type collectionType = typeToken.getType();

    // 4) Type 객체에 저장된 정보를 바탕으로 JSON 문자열로부터 컬렉션 객체를 만든다.
    Collection<Member> list = new Gson().fromJson(jsonStr, collectionType);

    for (Member m : list) {
      System.out.println(m);
    }
  }
}

=>

=>

=>

=>

=>

com.eomcs.openapi.json.gson

Exam0321.java

// JSON 문자열 --> 객체 : 컬렉션 다루기
package com.eomcs.openapi.json.gson;

import java.util.Collection;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;

public class Exam0321 {
  public static void main(String[] args) {

    String jsonStr =
        "[{\"no\":101,\"name\":\"홍길동\"},{\"no\":102,\"name\":\"임꺽정\"},{\"no\":103,\"name\":\"안창호\"}]";

    // // Exam0320의 코드를 익명 클래스를 이용하여 간결하게 정리한 것이다.
    // Type collectionType = new TypeToken<Collection<Member>>(){}.getType();
    // Collection<Member> list = new Gson().fromJson(jsonStr, collectionType);

    Collection<Member> list =
        new Gson().fromJson(jsonStr, new TypeToken<Collection<Member>>() {}.getType());

    for (Member m : list) {
      System.out.println(m);
    }
  }
}

ㄴ 제네릭 타입을 사용하는 경우 TypeToken을 사용하여 Gson에 제네릭 타입 정보를 전달해야함
ㄴ TypeToken<Collection<Member>>은 Gson에게 컬렉션의 요소 타입은 Member이며, 컬렉션 타입은 Collection인 것을 알려준다는 의미

=> new TypeToken<Collection<Member>>() {}.getType()는 컬렉션 타입에 대한 제네릭 타입 정보를 얻기 위해 사용되며, Gson에게 컬렉션의 요소 타입과 컬렉션 타입 정보를 제공함

ㄴ Gson은 이 정보를 토대로 JSON 문자열을 해당 컬렉션 객체로 변환할 때, 올바른 타입 정보를 사용하여 객체를 생성함

 

=>

com.eomcs.openapi.json.gson

Exam0322.java

// JSON 문자열 --> 객체 : 컬렉션 다루기
package com.eomcs.openapi.json.gson;

import java.util.Collection;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;

public class Exam0322 {
  public static void main(String[] args) {

    String jsonStr =
        "[{\"no\":101,\"name\":\"홍길동\"},{\"no\":102,\"name\":\"임꺽정\"},{\"no\":103,\"name\":\"안창호\"}]";

    // Exam0321과 다른 방법으로 Type 객체를 얻기
    // Type collectionType = TypeToken.getParameterized(Collection.class, Member.class).getType();
    // Collection<Member> list = new Gson().fromJson(jsonStr, collectionType);

    Collection<Member> list = new Gson().fromJson(jsonStr,
        TypeToken.getParameterized(Collection.class, Member.class).getType());

    for (Member m : list) {
      System.out.println(m);
    }
  }
}

ㄴ TypeToken.getParameterized(Collection.class, Member.class).getType()은 컬렉션의 요소 타입이 Member인 컬렉션 타입의 Type 객체를 반환함

    => 이 Type 객체를 Gson에 전달하여 JSON 문자열을  Collection<Member> 타입의 컬렉션 객체로 변환할 때 올바른 타입 정보를 사용

 

com.eomcs.openapi.json.gson

Exam0410.java

// 객체 --> JSON 문자열 : 다른 객체를 포함하는 경우
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import com.google.gson.Gson;

public class Exam0410 {
  public static void main(String[] args) {

    // 1) 객체 준비
    Member m = new Member();
    m.setNo(100);
    m.setName("홍길동");
    m.setEmail("hong@test.com");
    m.setPassword("1111");
    m.setPhoto("hong.gif");
    m.setTel("010-2222-1111");
    m.setRegisteredDate(new Date(System.currentTimeMillis()));

    Board b = new Board();
    b.setNo(1);
    b.setTitle("제목");
    b.setContent("내용");
    b.setWriter(m);
    b.setViewCount(98);
    b.setLike(5);
    b.setRegisteredDate(new Date(System.currentTimeMillis()));

    String jsonStr = new Gson().toJson(b);

    System.out.println(jsonStr);
  }
}

// 다른 객체를 포함했을 때 JSON 형식
// {
//    프로퍼티명 : 값,
//    프로퍼티명 : {프로퍼티명:값,프로퍼티명:값,...},
//    ...
// }
//

 

 

com.eomcs.openapi.json.gson

Exam0420.java

// JSON 문자열 --> 객체 : 다른 객체를 포함하는 경우
package com.eomcs.openapi.json.gson;

import com.google.gson.Gson;

public class Exam0420 {
  public static void main(String[] args) {

    String jsonStr = "{\"no\":1,\"title\":\"제목\",\"content\":\"내용\",\"writer\":{\"no\":100,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"password\":\"1111\",\"photo\":\"hong.gif\",\"tel\":\"010-2222-1111\",\"registeredDate\":\"9월 16, 2021\"},\"registeredDate\":\"9월 16, 2021\",\"viewCount\":98,\"like\":5}";

    Board b = new Gson().fromJson(jsonStr, Board.class);

    System.out.println(b);
  }
}

 

com.eomcs.openapi.json.gson

Exam0510.java

// 객체 --> JSON 문자열 : 다른 객체를 목록으로 포함하는 경우
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import java.util.ArrayList;
import com.google.gson.Gson;

public class Exam0510 {
  public static void main(String[] args) {

    // 1) 객체 준비
    Member m1 = new Member();
    m1.setNo(101);
    m1.setName("홍길동");
    m1.setEmail("hong@test.com");
    m1.setRegisteredDate(new Date(System.currentTimeMillis()));

    Member m2 = new Member();
    m2.setNo(102);
    m2.setName("임꺽정");
    m2.setEmail("leem@test.com");
    m2.setRegisteredDate(new Date(System.currentTimeMillis()));

    Member m3 = new Member();
    m3.setNo(103);
    m3.setName("안창호");
    m3.setEmail("ahn@test.com");
    m3.setRegisteredDate(new Date(System.currentTimeMillis()));

    ArrayList<Member> members = new ArrayList<>();
    members.add(m1);
    members.add(m2);
    members.add(m3);

    Project p = new Project();
    p.setNo(11);
    p.setTitle("제목");
    p.setContent("내용");
    p.setStartDate(Date.valueOf("2021-1-1"));
    p.setEndDate(Date.valueOf("2021-2-2"));
    p.setOwner(m2);
    p.setMembers(members);

    String jsonStr = new Gson().toJson(p);

    System.out.println(jsonStr);
  }
}

// 다른 객체를 목록으로 포함했을 때 JSON 형식
// {
//    프로퍼티명 : 값,
//    프로퍼티명 : {프로퍼티명:값,프로퍼티명:값,...},
//    프로퍼티명 : [{...},{...},{...},...],
//    ...
// }
//

 

com.eomcs.openapi.json.gson

Exam0520.java

// JSON 문자열 --> 객체 : 다른 객체를 여러 개 포함하는 경우
package com.eomcs.openapi.json.gson;

import com.google.gson.Gson;

public class Exam0520 {
  public static void main(String[] args) {

    String jsonStr = "{\"no\":11,\"title\":\"제목\",\"content\":\"내용\",\"startDate\":\"1월 1, 2021\",\"endDate\":\"2월 2, 2021\",\"owner\":{\"no\":102,\"name\":\"임꺽정\",\"email\":\"leem@test.com\",\"registeredDate\":\"9월 16, 2021\"},\"members\":[{\"no\":101,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"registeredDate\":\"9월 16, 2021\"},{\"no\":102,\"name\":\"임꺽정\",\"email\":\"leem@test.com\",\"registeredDate\":\"9월 16, 2021\"},{\"no\":103,\"name\":\"안창호\",\"email\":\"ahn@test.com\",\"registeredDate\":\"9월 16, 2021\"}],\"tasks\":[]}";

    Project p = new Gson().fromJson(jsonStr, Project.class);

    System.out.println(p);
  }
}

 

com.eomcs.openapi.json.gson

Exam0610.java

// 객체 --> JSON 문자열 : 다양한 타입의 객체를 목록에 포함하는 경우
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import java.util.ArrayList;
import com.google.gson.Gson;

public class Exam0610 {
  public static void main(String[] args) {

    // 1) 객체 준비
    Manager mgr = new Manager();
    mgr.setNo(101);
    mgr.setName("홍길동");
    mgr.setEmail("hong@test.com");
    mgr.setRegisteredDate(new Date(System.currentTimeMillis()));
    mgr.setPosition("대리");
    mgr.setFax("02-1111-2222");

    Teacher teacher = new Teacher();
    teacher.setNo(103);
    teacher.setName("안창호");
    teacher.setEmail("ahn@test.com");
    teacher.setRegisteredDate(new Date(System.currentTimeMillis()));
    teacher.setMajor("컴퓨터공학");
    teacher.setHourPay(10000);

    ArrayList<Member> members = new ArrayList<>();
    members.add(mgr);
    members.add(teacher);

    String jsonStr = new Gson().toJson(members);

    System.out.println(jsonStr);
  }
}

ㄴ 어떤 객체가 출력되어야 하는지 알려준 경우

 

com.eomcs.openapi.json.gson

Exam0620.java

// JSON 문자열 --> 객체 : 다른 객체를 여러 개 포함하는 경우
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.util.Collection;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;

public class Exam0620 {
  public static void main(String[] args) {

    String jsonStr = "[{\"position\":\"대리\",\"fax\":\"02-1111-2222\",\"no\":101,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"registeredDate\":\"9월 16, 2021\"},{\"major\":\"컴퓨터공학\",\"hourPay\":10000,\"no\":103,\"name\":\"안창호\",\"email\":\"ahn@test.com\",\"registeredDate\":\"9월 16, 2021\"}]";

    Type collectionType = TypeToken.getParameterized(Collection.class, Member.class).getType();
    Collection<Member> list = new Gson().fromJson(jsonStr, collectionType);

    for (Member m : list) {
      System.out.println(m);
    }
  }
}

ㄴ 어떤 객체가 출력되어야 하는지 정확히 알려주지 않아 Member 타입의 객체로 출력되고, 프로퍼티명과 다른 필드는 null 로 출력됨

ㄴ 컬렉션의 요소 타입으로 Member를 사용하고 있어서 JSON 문자열을 Collection<Member> 타입의 컬렉션 객체로 변환하게 됨
ㄴ 하지만 JSON 문자열에는 Member 객체 외에도 다른 객체들이 포함되어 있으므로, 가장 상위 타입으로 모든 객체들을 포함할 수 있는 타입을 사용해야 함

 

com.eomcs.openapi.json.gson

Exam0621.java

// JSON 문자열 --> 객체 : 다른 객체를 여러 개 포함하는 경우
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.util.Collection;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParseException;
import com.google.gson.reflect.TypeToken;

public class Exam0621 {
  public static void main(String[] args) {

    String jsonStr = "[{\"position\":\"대리\",\"fax\":\"02-1111-2222\",\"no\":101,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"registeredDate\":\"9월 16, 2021\"},{\"major\":\"컴퓨터공학\",\"hourPay\":10000,\"no\":103,\"name\":\"안창호\",\"email\":\"ahn@test.com\",\"registeredDate\":\"9월 16, 2021\"}]";

    // JSON 데이터를 가지고 객체를 생성할 때 특정 타입의 객체로 만들어주는 어댑터
    // => 프로퍼티의 존재 유무에 따라 Manager를 생성하든가 Teacher를 생성하는 일을 한다.
    class MyJsonDeserializer implements JsonDeserializer<Member> {
      @Override
      public Member deserialize(JsonElement json, Type typeOfT,
          JsonDeserializationContext context) throws JsonParseException {

        JsonObject jsonObject = json.getAsJsonObject();

        if (jsonObject.get("position") != null) {
          return context.deserialize(jsonObject, Manager.class);
        } else {
          return context.deserialize(jsonObject, Teacher.class);
        }
      }
    }

    // Gson 객체를 만들어주는 공장
    GsonBuilder gsonBuilder = new GsonBuilder();

    // 공장에 객체 생성기(JsonDeserializer)를 꼽는다.
    gsonBuilder.registerTypeAdapter(Member.class, new MyJsonDeserializer());

    // 공장을 통해 Gson 객체를 준비한다.
    Gson gson = gsonBuilder.create();

    // Gson 객체가 JSON 데이터를 가지고 객체를 생성할 때 알아야 하는 객체 타입 정보 준비
    Type collectionType = TypeToken.getParameterized(Collection.class, Member.class).getType();

    // JSON 데이터를 읽어서 주어진 타입의 객체를 생성한다.
    // => 단 내부에 설정된 객체 어댑터(JsonDeserializer)를 이용하여 객체를 생성한다.
    Collection<Member> list = gson.fromJson(jsonStr, collectionType);

    for (Member m : list) {
      System.out.println(m);
    }
  }
}

ㄴ MyJsonDeserializer 클래스는 JsonDeserializer<Member> 인터페이스를 구현하여 JSON 데이터를 해석하고 특정 타입의 객체로 생성하는 클래스

ㄴ deserialize 메서드에서는 JSON 데이터의 프로퍼티를 확인하여 해당하는 타입의 객체로 변환함

=> position 프로퍼티의 존재 여부에 따라 Member 중에서 Manager 객체 또는 Teacher 객체를 생성하도록 구현되어 있음

 

=> JSON 데이터를 파싱하여 Member, Manager, Teacher 객체로 변환하고, 생성된 객체들을 컬렉션에 담아 출력함

 

 

=>

익명클래스 사용

com.eomcs.openapi.json.gson

Exam0622.java

// JSON 문자열 --> 객체 : 다른 객체를 여러 개 포함하는 경우
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.util.Collection;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParseException;
import com.google.gson.reflect.TypeToken;

public class Exam0622 {
  public static void main(String[] args) {

    String jsonStr = "[{\"position\":\"대리\",\"fax\":\"02-1111-2222\",\"no\":101,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"registeredDate\":\"9월 16, 2021\"},{\"major\":\"컴퓨터공학\",\"hourPay\":10000,\"no\":103,\"name\":\"안창호\",\"email\":\"ahn@test.com\",\"registeredDate\":\"9월 16, 2021\"}]";

    Gson gson = new GsonBuilder()
        .registerTypeAdapter(Member.class, new JsonDeserializer<Member>() {
          @Override
          public Member deserialize(JsonElement json, Type typeOfT,
              JsonDeserializationContext context) throws JsonParseException {

            JsonObject jsonObject = json.getAsJsonObject();

            if (jsonObject.get("position") != null) {
              return context.deserialize(jsonObject, Manager.class);
            } else {
              return context.deserialize(jsonObject, Teacher.class);
            }
          }
        })
        .create();

    Type collectionType = TypeToken.getParameterized(Collection.class, Member.class).getType();
    Collection<Member> list = gson.fromJson(jsonStr, collectionType);

    for (Member m : list) {
      System.out.println(m);
    }
  }
}

 

Exam0114.java

=>

 

com.eomcs.openapi.json.gson

Exam0115.java

// 메서드 chaining call - before
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.sql.Date;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonElement;
import com.google.gson.JsonPrimitive;
import com.google.gson.JsonSerializationContext;
import com.google.gson.JsonSerializer;

public class Exam0115 {
  public static void main(String[] args) {
    
    class Member {
      int no;
      String name;
      String email;
      String password;
      boolean working;
      public int getNo() {return no;}
      public void setNo(int no) {this.no = no;}
      public String getName() {return name;}
      public void setName(String name) {this.name = name;}
      public String getEmail() {return email;}
      public void setEmail(String email) {this.email = email;}
      public String getPassword() {return password;}
      public void setPassword(String password) {this.password = password;}
      public boolean isWorking() {return working;}
      public void setWorking(boolean working) {this.working = working;}
      
    }
    
    Member m = new Member();
    m.setNo(100);
    m.setName("홍길동");
    m.setEmail("hong@test.com");
    m.setPassword("1111");
    m.setWorking(true);
  }
}

// JSON 객체 형식 - { 객체 정보 }
// => { "프로퍼티명" : 값, "프로퍼티명": 값, ...}
//
// 값:
// - 문자열 => "값"
// - 숫자 => 값
// - 논리 => true, false
//
// 프로퍼티명은 반드시 문자열로 표현해야 한다.

=>

com.eomcs.openapi.json.gson

Exam0116.java

// 메서드 chaining call - after
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.sql.Date;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonElement;
import com.google.gson.JsonPrimitive;
import com.google.gson.JsonSerializationContext;
import com.google.gson.JsonSerializer;

public class Exam0116 {
  public static void main(String[] args) {
    
    class Member {
      int no;
      String name;
      String email;
      String password;
      boolean working;
      public int getNo() {return no;}
      public Member setNo(int no) {this.no = no; return this;}
      public String getName() {return name;}
      public Member setName(String name) {this.name = name; return this;}
      public String getEmail() {return email;}
      public Member setEmail(String email) {this.email = email; return this;}
      public String getPassword() {return password;}
      public Member setPassword(String password) {this.password = password; return this;}
      public boolean isWorking() {return working;}
      public Member setWorking(boolean working) {this.working = working; return this;}
      
    }
    
    Member m = new Member()
        .setNo(100)
        .setName("홍길동")
        .setEmail("hong@test.com")
        .setPassword("1111")
        .setWorking(true);
  }
}

// JSON 객체 형식 - { 객체 정보 }
// => { "프로퍼티명" : 값, "프로퍼티명": 값, ...}
//
// 값:
// - 문자열 => "값"
// - 숫자 => 값
// - 논리 => true, false
//
// 프로퍼티명은 반드시 문자열로 표현해야 한다.

ㄴ setter 에 리턴값을 줌

ㄴ chaining 기법 원래의 setter 를 수정해서 사용할 경우 setter 메서드 인식 못 하는 경우가 있음

=>

com.eomcs.openapi.json.gson

Exam0117.java

// 메서드 chaining call - after
package com.eomcs.openapi.json.gson;

import java.lang.reflect.Type;
import java.sql.Date;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.JsonElement;
import com.google.gson.JsonPrimitive;
import com.google.gson.JsonSerializationContext;
import com.google.gson.JsonSerializer;

public class Exam0117 {
  public static void main(String[] args) {
    
    class Member {
      int no;
      String name;
      String email;
      String password;
      boolean working;
      public int getNo() {return no;}
      public void setNo(int no) {this.no = no;}
      public String getName() {return name;}
      public void setName(String name) {this.name = name;}
      public String getEmail() {return email;}
      public void setEmail(String email) {this.email = email;}
      public String getPassword() {return password;}
      public void setPassword(String password) {this.password = password;}
      public boolean isWorking() {return working;}
      public void setWorking(boolean working) {this.working = working;}
      
      
      public Member no(int no) {this.no = no; return this;}
      public Member name(String name) {this.name = name; return this;}
      public Member email(String email) {this.email = email; return this;}
      public Member password(String password) {this.password = password; return this;}
      public Member working(boolean working) {this.working = working; return this;}  
    }
    
    Member m = new Member()
        .no(100)
        .name("홍길동")
        .email("hong@test.com")
        .password("1111")
        .working(true);
  }
}

// JSON 객체 형식 - { 객체 정보 }
// => { "프로퍼티명" : 값, "프로퍼티명": 값, ...}
//
// 값:
// - 문자열 => "값"
// - 숫자 => 값
// - 논리 => true, false
//
// 프로퍼티명은 반드시 문자열로 표현해야 한다.

ㄴ chaining 기법 원래의 setter 를 수정해서 사용할 경우 setter 메서드 인식 못 하는 경우가 있으므로 이렇게 새로 구현해주어야 함

 

com.eomcs.openapi.json.gson

Exam0710.java

// 맵객체 --> JSON 문자열 
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import java.util.HashMap;
import com.google.gson.Gson;

public class Exam0710 {
  public static void main(String[] args) {

    // 자바 기본 타입과 객체를 묶어서 JSON으로 내보내기
    Manager mgr = new Manager();
    mgr.setNo(101);
    mgr.setName("홍길동");
    mgr.setEmail("hong@test.com");
    mgr.setRegisteredDate(new Date(System.currentTimeMillis()));
    mgr.setPosition("대리");
    mgr.setFax("02-1111-2222");

    HashMap<String,Object> params = new HashMap<>();
    params.put("no", String.valueOf(100));
    params.put("title", "Hello");
    params.put("manager", mgr);

    String jsonStr = new Gson().toJson(params);

    System.out.println(jsonStr);
  }
}

ㄴ Manager 객체와 다른 자바 기본 타입 및 객체들을 HashMap에 담아서 JSON으로 변환
ㄴ Manager 객체를 생성하고 필드에 값을 설정

ㄴ HashMap 객체인 params를 생성하고 필드 이름과 값을 쌍으로 저장

ㄴ "no", "title", "manager"라는 키로 값을 저장함

ㄴ "manager" 키에는 Manager 객체 자체가 저장됨
ㄴ new Gson().toJson(params)를 호출하여 params 맵 객체를 JSON 문자열로 변환

    => 이 때 Gson 객체를 사용하고 toJson() 메서드에 변환할 객체를 전달함

 

=> params 맵 객체가 JSON 문자열로 변환되어 출력됨

     ㄴ 출력된 JSON 문자열은 params 맵 객체의 구조와 내용을 반영하고 있음

 

com.eomcs.openapi.json.gson

Exam0711.java

// 맵객체 --> JSON 문자열 
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import java.util.HashMap;
import com.google.gson.Gson;

public class Exam0711 {
  public static void main(String[] args) {

    // 자바 기본 타입과 객체를 묶어서 JSON으로 내보내기
    Manager mgr = new Manager();
    mgr.setNo(101);
    mgr.setName("홍길동");
    mgr.setEmail("hong@test.com");
    mgr.setRegisteredDate(new Date(System.currentTimeMillis()));
    mgr.setPosition("대리");
    mgr.setFax("02-1111-2222");

    HashMap<String,String> params = new HashMap<>();
    params.put("no", String.valueOf(100));
    params.put("title", "Hello");
    params.put("manager", new Gson().toJson(mgr));

    String jsonStr = new Gson().toJson(params);

    System.out.println(jsonStr);
  }
}

ㄴ Manager 객체를 먼저 생성하고 필드에 값을 설정함

ㄴ HashMap 객체인 params를 생성하고 필드 이름과 값을 쌍으로 저장

ㄴ "no", "title", "manager"라는 키로 값을 저장

ㄴ "manager" 키에는 Gson().toJson(mgr)를 호출하여 Manager 객체를 JSON 문자열로 변환한 결과가 저장됨
ㄴ new Gson().toJson(params)를 호출하여 params 맵 객체를 JSON 문자열로 변환

    => Gson 객체를 사용하고 toJson() 메서드에 변환할 객체를 전달함

 

=> params 맵 객체가 JSON 문자열로 변환되어 출력됨

     ㄴ 출력된 JSON 문자열은 params 맵 객체의 구조와 내용을 반영하고 있음

     ㄴ manager" 키에는 Manager 객체가 JSON 형태로 포함되어 있음

 

com.eomcs.openapi.json.gson

Exam0712.java

// 맵객체 --> JSON 문자열 
package com.eomcs.openapi.json.gson;

import java.sql.Date;
import com.google.gson.Gson;

public class Exam0712 {
  public static void main(String[] args) {

    // 자바 기본 타입과 객체를 묶어서 JSON으로 내보내기
    Manager mgr = new Manager();
    mgr.setNo(101);
    mgr.setName("홍길동");
    mgr.setEmail("hong@test.com");
    mgr.setRegisteredDate(new Date(System.currentTimeMillis()));
    mgr.setPosition("대리");
    mgr.setFax("02-1111-2222");

    ManagerParam param = new ManagerParam();
    param.no = 100;
    param.title = "Hello";
    param.manager = mgr;

    String jsonStr = new Gson().toJson(param);

    System.out.println(jsonStr);
  }
}

ㄴ Manager 객체와 ManagerParam 객체를 생성하고 필드에 값을 설정함

ㄴ Manager 객체의 필드 값을 설정한 후, ManagerParam 객체의 필드 값을 설정함

ㄴ Gson().toJson(param)을 호출하여 param 객체를 JSON 문자열로 변환함
ㄴ 변환된 JSON 문자열을 출력

=> param 객체가 JSON 문자열로 변환되어 출력됨

     ㄴ 출력된 JSON 문자열은 param 객체의 구조와 내용을 반영하고 있음

     ㄴ manager 필드에는 Manager 객체가 JSON 형태로 포함되어 있음

 

com.eomcs.openapi.json.gson

Exam0720.java

// JSON 문자열 --> 객체 : 다른 객체를 여러 개 포함하는 경우
package com.eomcs.openapi.json.gson;

import java.util.Map;
import com.google.gson.Gson;

public class Exam0720 {
  public static void main(String[] args) {

    String jsonStr = "{\"no\":100,\"manager\":{\"position\":\"대리\",\"fax\":\"02-1111-2222\",\"no\":101,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"registeredDate\":\"10월 5, 2021\"},\"title\":\"Hello\"}";

    Map<String,Object> map = new Gson().fromJson(jsonStr, Map.class);

    Object v1 = map.get("no");
    Object v2 = map.get("title");
    Object v3 = map.get("manager");

    System.out.println(v1.getClass().getName());
    System.out.println(v2.getClass().getName());
    System.out.println(v3.getClass().getName());

    System.out.println(map.get("no"));
    System.out.println(map.get("title"));
    System.out.println(map.get("manager"));
  }
}

ㄴ 값을 꺼낼 때 각각 타입이 다르게 꺼내짐

 

com.eomcs.openapi.json.gson

Exam0721.java

// JSON 문자열 --> 객체 : 다른 객체를 여러 개 포함하는 경우
package com.eomcs.openapi.json.gson;

import java.util.Map;
import com.google.gson.Gson;

public class Exam0721 {
  public static void main(String[] args) {

    String jsonStr = "{\"no\":\"100\",\"manager\":\"{\\\"position\\\":\\\"대리\\\",\\\"fax\\\":\\\"02-1111-2222\\\",\\\"no\\\":101,\\\"name\\\":\\\"홍길동\\\",\\\"email\\\":\\\"hong@test.com\\\",\\\"registeredDate\\\":\\\"10월 5, 2021\\\"}\",\"title\":\"Hello\"}";

    Map<String,String> map = new Gson().fromJson(jsonStr, Map.class);

    String v1 = map.get("no");
    String v2 = map.get("title");
    String v3 = map.get("manager");

    System.out.println(v1);
    System.out.println(v2);
    System.out.println(v3);

    Manager mgr = new Gson().fromJson(v3, Manager.class);
    System.out.println(mgr);
  }
}

ㄴ JSON 문자열을 객체로 변환

ㄴ jsonStr 변수에 JSON 문자열을 저장하고, fromJson 메서드를 사용하여 JSON 문자열을 Map 객체로 변환함
ㄴ map.get 메서드를 사용하여 변환된 Map 객체에서 필요한 값을 가져옴

ㄴ 변수 v1, v2, v3에는 map.get 메서드를 호출한 결과가 저장됨
ㄴ 변수 v3에 저장된 JSON 문자열을 다시 Gson을 사용하여 Manager 객체로 변환

=> 변환된 Manager 객체를 출력

=> JSON 문자열이 Map 객체로 변환되고, 해당 필드의 값을 가져와서 출력됨

     ㄴ v3에 저장된 JSON 문자열을 다시 Manager 객체로 변환하여 출력하면 Manager 객체의 정보가 출력됨

 

com.eomcs.openapi.json.gson

Exam0722.java

// JSON 문자열 --> 객체 : 다른 객체를 여러 개 포함하는 경우
package com.eomcs.openapi.json.gson;

import com.google.gson.Gson;

public class Exam0722 {
  public static void main(String[] args) {

    String jsonStr = "{\"no\":100,\"title\":\"Hello\",\"manager\":{\"position\":\"대리\",\"fax\":\"02-1111-2222\",\"no\":101,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"registeredDate\":\"10월 5, 2021\"}}";

    ManagerParam param = new Gson().fromJson(jsonStr, ManagerParam.class);

    System.out.println(param.no);
    System.out.println(param.title);
    System.out.println(param.manager);
  }
}

ㄴ 값을 원래 자바 객체로 꺼낼 때 ManagerParam 에 담아 달라고 하면 타입 변하지 않고 원래 타입대로 출력됨

=> 별도의 클래스에 담아서 저장하고, 가져오도록 하는 것이 좋음!

 

 

com.eomcs.openapi.json.jackson

Exam0110.java

// 객체 --> JSON 문자열 : 객체의 필드 값을 json 형식의 문자열로 만들기
package com.eomcs.openapi.json.jackson;

import java.sql.Date;
import com.fasterxml.jackson.databind.ObjectMapper;

public class Exam0110 {
  public static void main(String[] args) throws Exception {

    // 1) 객체 준비
    Member m = new Member();
    m.setNo(100);
    m.setName("홍길동");
    m.setEmail("hong@test.com");
    m.setPassword("1111");
    m.setPhoto("hong.gif");
    m.setTel("010-2222-1111");
    m.setRegisteredDate(new Date(System.currentTimeMillis()));

    // 2) JSON 처리 객체 준비
    ObjectMapper mapper = new ObjectMapper();

    // 3) 객체의 값을 JSON 문자열로 얻기
    String jsonStr = mapper.writeValueAsString(m);

    System.out.println(jsonStr);
  }
}

// JSON 객체 형식 - { 객체 정보 }
// => { "프로퍼티명" : 값, "프로퍼티명": 값, ...}
// 
// 값:
// - 문자열 => "값"
// - 숫자   => 값
// - 논리   => true, false
//
// 프로퍼티명은 반드시 문자열로 표현해야 한다.

 

com.eomcs.openapi.json.jackson

Exam0120.java

// JSON 문자열 --> 객체 : JSON 문자열을 해석하여 객체를 생성하기
package com.eomcs.openapi.json.jackson;

import com.fasterxml.jackson.databind.ObjectMapper;

public class Exam0120 {
  public static void main(String[] args) throws Exception {

    // 1) JSON 문자열 준비
    String jsonStr = "{\"no\":100,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"password\":\"1111\",\"photo\":\"hong.gif\",\"tel\":\"010-2222-1111\",\"registeredDate\":1642991105179}";

    // 2) JSON 처리 객체 준비
    ObjectMapper mapper = new ObjectMapper();

    // 3) JSON 문자열을 가지고 객체 만들기
    Member m = mapper.readValue(jsonStr, Member.class);

    System.out.println(m);
  }
}

ㄴ ObjectMapper 객체를 사용하여 JSON 문자열을 객체로 변환하는 과정은 readValue 메서드를 사용함

ㄴ 첫 번째 인자로는 변환할 JSON 문자열을 전달하고, 두 번째 인자로는 변환될 객체의 타입(Member.class)을 전달함

ㄴ readValue 메서드는 JSON 문자열을 분석하여 해당 타입의 객체를 생성하고 반환함
=> 주어진 JSON 문자열이 Member 객체로 변환되어 출력됨

 

 

com.eomcs.openapi.json.jackson

Board.java

package com.eomcs.openapi.json.jackson;

import java.sql.Date;

// JSON 문자열로 넘어 온 값을 객체로 만들 때
// JSON 프로퍼티의 이름과 일치하는 객체 프로퍼티가 없다면 예외가 발생한다.
// 그럴 경우 다음과 같이
// JSON으로 넘어온 값 중에서 객체에 저장할 대상이 아닌 프로퍼티에 대해 표시를 해야 한다.
// 그 방법은 다음과 같이 애노테이션을 이용하여 무시할 JSON 프로퍼티의 이름을 명시한다.
//
// @JsonIgnoreProperties(value= {"name", "email", "password", "photo", "tel"})
public class Board {
  private int no;
  private String title;
  private String content;
  private Member writer;
  private Date registeredDate;
  private int viewCount;
  private int like;

  @Override
  public String toString() {
    return "Board [no=" + no + ", title=" + title + ", content=" + content + ", writer=" + writer
        + ", registeredDate=" + registeredDate + ", viewCount=" + viewCount + ", like=" + like
        + "]";
  }

  public int getNo() {
    return no;
  }

  public void setNo(int no) {
    this.no = no;
  }

  public String getTitle() {
    return title;
  }

  public void setTitle(String title) {
    this.title = title;
  }

  public String getContent() {
    return content;
  }

  public void setContent(String content) {
    this.content = content;
  }

  public Date getRegisteredDate() {
    return registeredDate;
  }

  public void setRegisteredDate(Date registeredDate) {
    this.registeredDate = registeredDate;
  }

  public int getViewCount() {
    return viewCount;
  }

  public void setViewCount(int viewCount) {
    this.viewCount = viewCount;
  }

  public int getLike() {
    return like;
  }

  public void setLike(int like) {
    this.like = like;
  }

  public Member getWriter() {
    return writer;
  }

  public void setWriter(Member writer) {
    this.writer = writer;
  }

}

ㄴ @JsonIgnoreProperties(value= {"name", "email", "password", "photo", "tel"}) 주석처리 할 경우 예외 발생

=> 주석처리 없애주기

 

com.eomcs.openapi.json.jackson

Exam0210.java

// 객체 --> JSON 문자열 : Date 값을 yyyy-MM-dd 형식으로 출력하기
package com.eomcs.openapi.json.jackson;

import java.sql.Date;
import java.text.SimpleDateFormat;
import com.fasterxml.jackson.databind.ObjectMapper;

public class Exam0210 {
  public static void main(String[] args) throws Exception {

    // 1) 객체 준비
    Member m1 = new Member();
    m1.setNo(101);
    m1.setName("홍길동");
    m1.setEmail("hong@test.com");
    m1.setRegisteredDate(new Date(System.currentTimeMillis()));

    // 2) JSON 처리 객체 준비
    ObjectMapper mapper = new ObjectMapper();

    mapper.setDateFormat(new SimpleDateFormat("yyyy-MM-dd"));

    // 3) 객체의 값을 JSON 문자열로 얻기
    String jsonStr = mapper.writeValueAsString(m1);

    System.out.println(jsonStr);
  }
}

ㄴ SimpleDateFormat 클래스를 사용하여 날짜 포맷을 지정

ㄴ mapper.setDateFormat 메서드를 호출하여 ObjectMapper 객체에 날짜 포맷을 설정

ㄴ SimpleDateFormat 생성자에 전달되는 "yyyy-MM-dd"는 날짜를 원하는 형식으로 출력하기 위한 패턴임

=>  Member 객체의 필드 값 중 Date 필드인 registeredDate가 "yyyy-MM-dd" 형식으로 JSON 문자열에 출력됨

 

com.eomcs.openapi.json.jackson

Exam0220.java

package com.eomcs.openapi.json.jackson;

import com.fasterxml.jackson.databind.ObjectMapper;

public class Exam0220 {

  public static void main(String[] args) throws Exception {
    String jsonStr =
        "{\"no\":100,\"name\":\"홍길동\",\"email\":\"hong@test.com\",\"password\":\"1111\",\"photo\":\"hong.gif\",\"tel\":\"010-2222-1111\",\"registeredDate\":\"2023-07-03\"}";
    ObjectMapper mapper = new ObjectMapper();
    Member member = mapper.readValue(jsonStr, Member.class);

    System.out.println(member);
  }

}

ㄴ 미리 준비된 JSON 문자열을 ObjectMapper를 사용하여 Member 객체로 변환함

ㄴ mapper.readValue 메서드를 호출하여 JSON 문자열을 Member 객체로 변환함

    => Member 클래스는 JSON 문자열의 필드와 일치하는 필드를 가져야 함

=> JSON 문자열의 내용이 Member 객체로 변환되고, Member 객체의 내용이 출력됨