package com.eactive.ext.kjb.obp;

import com.google.gson.Gson;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import com.google.gson.annotations.SerializedName;
import lombok.Data;

/**
 * OBP Organization 조회 응답
 * - 필수 필드만 명시적으로 선언하고, 나머지는 rawJson으로 보관하여 유연성 확보
 */
@Data
public class ObpOrganization {
    private static final Gson gson = new Gson();

    // 핵심 필드
    @SerializedName("partnerCode")
    private String partnerCode;

    @SerializedName("id")
    private String id;

    @SerializedName("name")
    private String name;

    @SerializedName("state")
    private String state;

    @SerializedName("status")
    private String status;

    @SerializedName("businessManRegistrationNo")
    private String businessManRegistrationNo;

    @SerializedName("corporateRegistrationNo")
    private String corporateRegistrationNo;

    @SerializedName("representativeName")
    private String representativeName;

    // 원본 JSON (추가 필드 접근용
    private transient JsonObject rawJson;

    /**
     * JSON 문자열에서 파싱
     */
    public static ObpOrganization fromJson(String json) {
        if (json == null || json.trim().isEmpty()) {
            return null;
        }

        ObpOrganization org = gson.fromJson(json, ObpOrganization.class);
        org.rawJson = new JsonParser().parse(json).getAsJsonObject();
        return org;
    }

    /**
     * ObpResponse에서 파싱
     */
    public static ObpOrganization fromResponse(ObpResponse response) {
        if (response == null || response.getStatus() != 200) {
            return null;
        }
        return fromJson(response.getBody());
    }

    /**
     * 원본 JSON에서 추가 필드 조회
     * @param fieldName 필드명 (예: "englishName", "description")
     * @return 필드 값 (없으면 null)
     */
    public String getField(String fieldName) {
        if (rawJson == null || !rawJson.has(fieldName) || rawJson.get(fieldName).isJsonNull()) {
            return null;
        }
        return rawJson.get(fieldName).getAsString();
    }

    /**
     * 원본 JSON에서 중첩 필드 조회
     * @param path 경로 (예: "type.name", "type.parent.name")
     * @return 필드 값 (없으면 null)
     */
    public String getNestedField(String path) {
        if (rawJson == null || path == null) {
            return null;
        }

        String[] parts = path.split("\\.");
        JsonObject current = rawJson;

        for (int i = 0; i < parts.length - 1; i++) {
            if (!current.has(parts[i]) || current.get(parts[i]).isJsonNull()) {
                return null;
            }
            current = current.getAsJsonObject(parts[i]);
        }

        String lastField = parts[parts.length - 1];
        if (!current.has(lastField) || current.get(lastField).isJsonNull()) {
            return null;
        }

        return current.get(lastField).getAsString();
    }

    /**
     * 원본 JSON 객체 반환
     */
    public JsonObject getRawJson() {
        return rawJson;
    }

    /**
     * partnerCode 유효성 확인
     */
    public boolean hasPartnerCode() {
        return partnerCode != null && !partnerCode.trim().isEmpty();
    }
}
