본문 바로가기
코딩/기타

Go언어(golang)로 공공데이터포털(data.go.kr) 오픈 API(국세청 사업자등록 상태 조회) 활용하기/REST API, HTTP request

by 나홀로코더 2022. 4. 16.
반응형

목차

1. 주제 소개

2. Go언어로 API 활용하기


 

1. 주제 소개

 

이 글은 기존에 소개한 파이썬을 이용한 오픈 API 활용법과 같은 내용으로, 아래 게시글의 내용 중 3번 부분을 Go언어 버전으로 바꾼 것이다.

 

파이썬으로 공공데이터포털(data.go.kr) 오픈 API 활용하기 예제/국세청 사업자등록 상태 조회

 

파이썬으로 공공데이터포털(data.go.kr) 오픈 API 활용하기 예제/국세청 사업자등록 상태 조회

목차 1. 주제 소개 2. API 활용신청하고 포털에서 API 사용해 보기 3. 파이썬으로 API 활용하기 1. 주제 소개 정부에서는 공공데이터의 제공 및 이용 활성화에 관한 법률 제21조에 따라 공공데이터포

codealone.tistory.com

 

API가 무엇인지, 공공데이터포털에서 오픈 API 활용 신청을 어떻게 하는지는 앞선 게시글(1~2번)에서 확인하고, Go언어로 API를 콜하는 방법을 바로 설명한다.

 

반응형

 

2. Go 언어로 API 활용하기

 

앞선 게시글에서 1~2번까지 잘 따라왔다면 공공데이터포털 API를 호출하는 curl 명령어를 얻었을 것이다.

 

아래 페이지에서는 curl 명령어를 go 코드로 간단히 변환할 수 있다.

 

 

https://mholt.github.io/curl-to-go/

 

curl-to-Go: Convert curl commands to Go code

curl-to-Go Instantly convert curl commands to Go code This tool turns a curl command into Go code. (To do the reverse, check out moul/http2curl.) Currently, it knows the following options: -d/--data, -H/--header, -I/--head, -u/--user, --url, and -X/--reque

mholt.github.io

 

공공데이터포털에서 복사해 둔 curl 명령어를 위 페이지에 붙여넣으면 아래와 같이 변환이 된다. 곧바로 실행할 수 있는 정도는 아니지만, 조금만 보완을 하면 바로 API 콜을 할수 있다.

 

// Generated by curl-to-Go: https://mholt.github.io/curl-to-go

// curl -X POST "https://api.odcloud.kr/api/nts-businessman/v1/status?serviceKey={serviceKey}" -H "accept: application/json" -H "Authorization: {serviceKey}" -H "Content-Type: application/json" -d "{ \"b_no\": [ \"0000000000\" ]}"
//

type Payload struct {
	BNo []string `json:"b_no"`
}

data := Payload{
// fill struct
}
payloadBytes, err := json.Marshal(data)
if err != nil {
	// handle err
}
body := bytes.NewReader(payloadBytes)

req, err := http.NewRequest("POST", "https://api.odcloud.kr/api/nts-businessman/v1/status?serviceKey={serviceKey}", body)
if err != nil {
	// handle err
}
req.Header.Set("Accept", "application/json")
req.Header.Set("Authorization", "{serviceKey}")
req.Header.Set("Content-Type", "application/json")

resp, err := http.DefaultClient.Do(req)
if err != nil {
	// handle err
}
defer resp.Body.Close()

 

추가할 내용은 다음과 같다.

 

(1) 패키지명을 선언하고 필요한 라이브러리를 불러온다. 그리고 앞서 curl 명령어를 변환해 얻은 코드를 main 함수로 선언한다.

 

(2) API 콜을 할 때 넘겨줄 데이터를 "fill struct" 부분에 채워준다. 

 

(3) API 호출 결과를 출력하기 위한 코드를 추가한다. 

 

구체적인 코드와 설명은 아래와 같다.

 

// Generated by curl-to-Go: https://mholt.github.io/curl-to-go 
// curl -X POST "https://api.odcloud.kr/api/nts-businessman/v1/status?serviceKey={serviceKey}" -H "accept: application/json" -H "Authorization: {serviceKey}" -H "Content-Type: application/json" -d "{ \"b_no\": [ \"0000000000\" ]}" 

//(1)

package main

import (
	"net/http"
	"encoding/json"
	"fmt"
	"bytes"
	"io"  // API 호출 결과를 문자열로 출력하는 데 필요
)

func main() {
	type Payload struct {
		BNo []string `json:"b_no"` 
	} 
	data := Payload{
    BNo: []string{"0000000000"} // (2) 사업자등록번호를 입력
    } 
	payloadBytes, err := json.Marshal(data) 
	if err != nil { 	
		// handle err 
	} 
	body := bytes.NewReader(payloadBytes) 
	req, err := http.NewRequest("POST", "https://api.odcloud.kr/api/nts-businessman/v1/status?serviceKey={serviceKey}", body) 
	if err != nil { 	
		// handle err 
	} 
	req.Header.Set("Accept", "application/json") 
	req.Header.Set("Authorization", "serviceKey") 
	req.Header.Set("Content-Type", "application/json") 
	resp, err := http.DefaultClient.Do(req) 
	if err != nil { 	
		// handle err 
	} 
	defer resp.Body.Close()
    
    // (3)
    
	re, _ := io.ReadAll(resp.Body)
	fmt.Printf("%s", re)
}

 

위와 같이 작성한 뒤, 터미널로 돌아가 go run 커맨드로 실행해 보면 다음과 같이 API 호출 결과가 출력된다.

 

{"request_cnt":1,"status_code":"OK","data":[{"b_no":"0000000000","b_stt":"","b_stt_cd":"","tax_type":"국세청에 등록되지 않은 사업자등록번호입니다.","tax_type_cd":"","end_dt":"","utcc_yn":"","tax_type_change_dt":"","invoice_apply_dt":""}]}

 

참고로, io 패키지를 이용하지 않고 바로 Println이나 Printf 메서드를 이용해 resp.Body를 출력하면 다음과 같이 새람이 이해할 수 없는 형식으로 출력된다.

Println 사용시
{0x4000096300}

Printf 사용시
{%!s(*http.http2clientStream=&{0x400007e180 0x400011c000 1 {{0 0} {{} 0x400007e330 {0 0 0 } 274878423912} 0x40003d2840 0 0x4000112110 0x59458da540} true false {0 {0 0}} 0x4000207920 0x40002078c0 0x40002079e0 0x4000207980 0x4000430090 {[] 65535 0x400007e1e0} {[] 4194045 0x400007e1f0} 259 0x40001261e0 23 true true t

그리고 io 패키지를 이용하더라도 Printf 메서드가 아닌 Println 메서드로 출력하게 되면 마찬가지로 아래처럼 이해할 수 없는 형태로 출력이 된다.

[123 34 114 101 113 117 101 115 116 95 99 110 116 34 58 49 44 34 115 116 97 116 117 115 95 99 111 100 101 34 58 34 79 75 34 44 34 100 97 116 97 34 58 91 123 34 98 95 110 111 34 58 34 48 48 48 48 48 48 48 48 48 48 34 44 34 98 95 115 116 116 34 58 34 34 44 34 98 95 115 116 116 95 99 100 34 58 34 34 44 34 116 97 120 95 116 121 112 101 34 58 34 234 181 173 236 132 184 236 178 173 236 151 144 32 235 147 177 235 161 157 235 144 152 236 167 128 32 236 149 138 236 157 128 32 236 130 172 236 151 133 236 158 144 235 147 177 235 161 157 235 178 136 237 152 184 236 158 133 235 139 136 235 139 164 46 34 44 34 116 97 120 95 116 121 112 101 95 99 100 34 58 34 34 44 34 101 110 100 95 100 116 34 58 34 34 44 34 117 116 99 99 95 121 110 34 58 34 34 44 34 116 97 120 95 116 121 112 101 95 99 104 97 110 103 101 95 100 116 34 58 34 34 44 34 105 110 118 111 105 99 101 95 97 112 112 108 121 95 100 116 34 58 34 34 125 93 125 10]

 

그런데 출력 결과가 보기에 좀 안 좋으니 보기 좋게 바꿔 보자. 맨 아랫줄을 삭제하고, 아래 코드를 추가한다.

 

type Result struct{ // 호출 결과를 저장할 구조체를 Result 타입으로 정의한다.
	Request_cnt int `json:"request_cnt"`
	Match_cnt int `json:"match_cnt"`
	Status_code string `json:"status_code"`
	Data []map[string]string `json:"data"` // Data는 키와 값이 모두 문자열인 맵의 슬라이스(리스트)이다. 예제에서는 1개의 사업자등록번호만 넘겨주고 있으므로 1개의 맵만 회신이 된다.
}

var result Result // 위에서 선언한 Result 타입의 result 변수를 선언한다.
json.Unmarshal(re, &result) // API 호출 결과인 re를 Result 타입으로 변환한다. re는 uint8 타입의 슬라이스 형태이므로 변환이 필요하다.

fmt.Println(result.Data[0]["tax_type"]) // result에서 Data 부분(.Data)의 첫번째 항목([0]) 중에서 과세유형(["tax_type"])만 출력한다.

 

위처럼 수정하면, API 호출 결과 가운데 "tax_type" 부분만 출력이 된다.

반응형

댓글