package com.supervision.police.service.impl; import com.fasterxml.jackson.core.type.TypeReference; import com.fasterxml.jackson.databind.ObjectMapper; import com.supervision.common.constant.XxlJobConstants; import com.supervision.common.utils.StringUtils; import com.supervision.police.domain.XxlJobInfo; import com.supervision.police.service.XxlJobService; import lombok.extern.slf4j.Slf4j; import org.apache.hc.client5.http.classic.methods.HttpPost; import org.apache.hc.client5.http.impl.classic.CloseableHttpClient; import org.apache.hc.client5.http.impl.classic.CloseableHttpResponse; import org.apache.hc.client5.http.impl.classic.HttpClients; import org.apache.hc.core5.http.ContentType; import org.apache.hc.core5.http.Header; import org.apache.hc.core5.http.HttpHeaders; import org.apache.hc.core5.http.io.entity.EntityUtils; import org.apache.hc.core5.http.io.entity.StringEntity; import org.springframework.beans.factory.annotation.Value; import org.springframework.stereotype.Service; import java.util.HashMap; import java.util.List; import java.util.Map; @Slf4j @Service public class XxlJobServiceImpl implements XxlJobService { public static String token = ""; private static final Map jobHandlerIdMap = new HashMap<>(); @Value("${xxl.job.admin.addresses}") private String xxlJobAdminAddress; @Value("${xxl.job.admin.username}") private String username; @Value("${xxl.job.admin.password}") private String password; @Override public String login() throws Exception { try (CloseableHttpClient httpClient = HttpClients.createDefault()) { HttpPost httpPost = new HttpPost(xxlJobAdminAddress + XxlJobConstants.URL_LOGIN); httpPost.setHeader("Content-Type", "application/x-www-form-urlencoded"); String params = "userName=" + username + "&password=" + password + "&ifRemember=on"; log.info("xxl-job-admin登录请求参数: {}", params); StringEntity entity = new StringEntity(params, ContentType.APPLICATION_FORM_URLENCODED); httpPost.setEntity(entity); try (CloseableHttpResponse response = httpClient.execute(httpPost)) { if (response.getCode() == 200) { Header[] headers = response.getHeaders(); for (Header header : headers) { if ("Set-Cookie".equals(header.getName())) { log.info("Set-Cookie: {}", header.getValue()); token = header.getValue(); break; } } } } catch (Exception e) { e.printStackTrace(); } } log.info("token: {}", token); return token; } public String getLoginToken() throws Exception { if (StringUtils.isEmpty(token)) { return login(); } return token; } @Override public List pageList(XxlJobInfo xxlJobInfo) throws Exception { try (CloseableHttpClient httpClient = HttpClients.createDefault()) { HttpPost httpPost = new HttpPost(xxlJobAdminAddress + XxlJobConstants.URL_JOB_INFO_PAGE_LIST); httpPost.setHeader(HttpHeaders.CONTENT_TYPE, "application/x-www-form-urlencoded"); httpPost.setHeader(HttpHeaders.COOKIE, getLoginToken()); String params = "jobGroup=-1&triggerStatus=-1&executorHandler=" + xxlJobInfo.getExecutorHandler() + "&start=0&length=10"; StringEntity entity = new StringEntity(params, ContentType.APPLICATION_FORM_URLENCODED); httpPost.setEntity(entity); try (CloseableHttpResponse response = httpClient.execute(httpPost)) { String responseBody = EntityUtils.toString(response.getEntity()); log.info("Response Body: {}", responseBody); ObjectMapper objectMapper = new ObjectMapper(); Map responseMap = objectMapper.readValue(responseBody, new TypeReference>() { }); if (responseMap.get("data") != null) { return objectMapper.convertValue(responseMap.get("data"), new TypeReference>() { }); } } catch (Exception e) { e.printStackTrace(); } } return null; } @Override public void executeTaskById(String id, String param) throws Exception { try (CloseableHttpClient httpClient = HttpClients.createDefault()) { // 查询任务 HttpPost httpPost = new HttpPost(xxlJobAdminAddress + XxlJobConstants.URL_JOB_INFO_TRIGGER); httpPost.setHeader(HttpHeaders.CONTENT_TYPE, "application/x-www-form-urlencoded"); httpPost.setHeader(HttpHeaders.COOKIE, getLoginToken()); String params = "id=" + id + "&executorParam=" + param; StringEntity entity = new StringEntity(params, ContentType.APPLICATION_FORM_URLENCODED); httpPost.setEntity(entity); try (CloseableHttpResponse response = httpClient.execute(httpPost)) { log.info("Task executed: {}", EntityUtils.toString(response.getEntity())); } catch (Exception e) { e.printStackTrace(); } } } @Override public void executeTaskByJobHandler(String jobHandler, String param) { try { //尝试从缓存中获取任务id,获取不到则查询任务后再执行 String jobId = jobHandlerIdMap.get(jobHandler); if (jobId != null) { log.info("根据任务名称【{}】获取到任务id【{}】,直接开始执行任务。", jobHandler, jobId); executeTaskById(jobId, param); } else { log.info("根据任务名称【{}】未获取到任务id,尝试远程获取任务信息。", jobHandler); XxlJobInfo xxlJobInfo = new XxlJobInfo(); xxlJobInfo.setExecutorHandler(jobHandler); List xxlJobInfoList = pageList(xxlJobInfo); if (xxlJobInfoList != null && !xxlJobInfoList.isEmpty()) { log.info("根据任务名称【{}】获取到任务信息【{}】,加入缓存并开始执行任务。", jobHandler, xxlJobInfoList.get(0)); jobId = String.valueOf(xxlJobInfoList.get(0).getId()); jobHandlerIdMap.put(jobHandler, jobId); executeTaskById(jobId, param); } else { log.info("未找到名称匹配的任务【{}】", xxlJobInfo.getExecutorHandler()); } } } catch (Exception e) { throw new RuntimeException(e); } } }