package com.nuojing.media.auth.client; import com.fasterxml.jackson.databind.JsonNode; import com.fasterxml.jackson.databind.ObjectMapper; import com.nuojing.admin.common.BusinessException; import com.nuojing.media.auth.domain.entity.MediaAuthConfig; import lombok.RequiredArgsConstructor; import org.springframework.http.HttpEntity; import org.springframework.http.HttpHeaders; import org.springframework.http.HttpMethod; import org.springframework.http.MediaType; import org.springframework.http.ResponseEntity; import org.springframework.stereotype.Component; import org.springframework.util.StringUtils; import org.springframework.web.client.RestTemplate; import org.springframework.web.util.UriComponentsBuilder; import java.util.HashMap; import java.util.Map; @Component @RequiredArgsConstructor public class BytedanceMediaClient { private static final String TOKEN_URL = "https://ad.oceanengine.com/open_api/oauth2/access_token/"; private static final String ADVERTISER_LIST_URL = "https://ad.oceanengine.com/open_api/oauth2/advertiser/get/"; private static final String USER_INFO_URL = "https://api.oceanengine.com/open_api/2/user/info/"; private static final String CC_ADVERTISER_LIST_URL = "https://api.oceanengine.com/open_api/2/customer_center/advertiser/list/"; private final ObjectMapper objectMapper; private final RestTemplate restTemplate = new RestTemplate(); public JsonNode exchangeToken(MediaAuthConfig config, String authCode) { Map body = new HashMap<>(); body.put("app_id", config.getAppId()); body.put("secret", config.getAppSecret()); body.put("auth_code", authCode); return postJson(TOKEN_URL, body); } public JsonNode advertiserList(String accessToken) { String url = UriComponentsBuilder.fromUriString(ADVERTISER_LIST_URL) .queryParam("access_token", accessToken) .build() .encode() .toUriString(); return parse(restTemplate.getForObject(url, String.class)); } public JsonNode ccAdvertiserList(String accessToken, long ccAccountId, int page) { String url = UriComponentsBuilder.fromUriString(CC_ADVERTISER_LIST_URL) .queryParam("cc_account_id", ccAccountId) .queryParam("page", page) .queryParam("page_size", 100) .queryParam("account_source", "AD") .build() .encode() .toUriString(); HttpHeaders headers = new HttpHeaders(); headers.set("Access-Token", accessToken); ResponseEntity response = restTemplate.exchange(url, HttpMethod.GET, new HttpEntity<>(headers), String.class); return parse(response.getBody()); } public JsonNode userInfo(String accessToken) { HttpHeaders headers = new HttpHeaders(); headers.set("Access-Token", accessToken); ResponseEntity response = restTemplate.exchange(USER_INFO_URL, HttpMethod.GET, new HttpEntity<>(headers), String.class); return parse(response.getBody()); } public JsonNode requireSuccess(JsonNode response, String action) { if (response == null || response.isMissingNode() || response.isNull()) { throw new BusinessException(500, action + "返回信息为空"); } int code = response.path("code").asInt(-1); if (code != 0) { String message = response.path("message").asText(action + "失败"); throw new BusinessException(500, message); } JsonNode data = response.path("data"); if (data.isMissingNode() || data.isNull()) { throw new BusinessException(500, action + "data信息为空"); } return data; } private JsonNode postJson(String url, Map body) { HttpHeaders headers = new HttpHeaders(); headers.setContentType(MediaType.APPLICATION_JSON); return parse(restTemplate.postForObject(url, new HttpEntity<>(body, headers), String.class)); } private JsonNode parse(String response) { if (!StringUtils.hasText(response)) { return objectMapper.missingNode(); } try { return objectMapper.readTree(response); } catch (Exception ex) { throw new BusinessException(500, "媒体响应解析失败"); } } }