mirror of
https://gitee.com/durcframework/SOP.git
synced 2025-08-11 21:57:56 +08:00
文档分组显示,代码优化
This commit is contained in:
@@ -82,12 +82,6 @@
|
||||
<blockquote class="layui-elem-quote layui-text sop-description">
|
||||
</blockquote>
|
||||
|
||||
|
||||
<div class="site-title">
|
||||
<fieldset class="layui-elem-field layui-field-title site-title">
|
||||
<legend><a name="use">公共参数</a></legend>
|
||||
</fieldset>
|
||||
</div>
|
||||
<div class="site-text">
|
||||
<h3>请求地址</h3>
|
||||
<table class="layui-table">
|
||||
@@ -106,6 +100,12 @@
|
||||
</table>
|
||||
</div>
|
||||
|
||||
<div class="site-title">
|
||||
<fieldset class="layui-elem-field layui-field-title site-title">
|
||||
<legend><a name="use">公共参数</a></legend>
|
||||
</fieldset>
|
||||
</div>
|
||||
|
||||
<div class="site-text">
|
||||
<h3>公共请求参数</h3>
|
||||
<table class="layui-table">
|
||||
|
@@ -0,0 +1,11 @@
|
||||
package com.gitee.sop.websiteserver.bean;
|
||||
|
||||
/**
|
||||
* @author tanghc
|
||||
*/
|
||||
public class WebsiteConstants {
|
||||
/**
|
||||
* zookeeper存放接口路由信息的根目录
|
||||
*/
|
||||
public static final String SOP_SERVICE_ROUTE_PATH = "/com.gitee.sop.route";
|
||||
}
|
@@ -0,0 +1,80 @@
|
||||
package com.gitee.sop.websiteserver.bean;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
import org.apache.commons.lang.math.NumberUtils;
|
||||
import org.apache.curator.framework.CuratorFramework;
|
||||
import org.apache.curator.framework.CuratorFrameworkFactory;
|
||||
import org.apache.curator.framework.recipes.cache.TreeCache;
|
||||
import org.apache.curator.framework.recipes.cache.TreeCacheListener;
|
||||
import org.apache.curator.retry.ExponentialBackoffRetry;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* @author tanghc
|
||||
*/
|
||||
@Slf4j
|
||||
public class ZookeeperContext {
|
||||
|
||||
private static CuratorFramework client;
|
||||
|
||||
public static void setEnvironment(Environment environment) {
|
||||
Assert.notNull(environment, "environment不能为null");
|
||||
initZookeeperClient(environment);
|
||||
}
|
||||
|
||||
public synchronized static void initZookeeperClient(Environment environment) {
|
||||
if (client != null) {
|
||||
return;
|
||||
}
|
||||
String zookeeperServerAddr = environment.getProperty("spring.cloud.zookeeper.connect-string");
|
||||
if (StringUtils.isBlank(zookeeperServerAddr)) {
|
||||
throw new RuntimeException("未指定spring.cloud.zookeeper.connect-string参数");
|
||||
}
|
||||
String baseSleepTimeMs = environment.getProperty("spring.cloud.zookeeper.baseSleepTimeMs");
|
||||
String maxRetries = environment.getProperty("spring.cloud.zookeeper.maxRetries");
|
||||
log.info("初始化zookeeper客户端,zookeeperServerAddr:{}, baseSleepTimeMs:{}, maxRetries:{}",
|
||||
zookeeperServerAddr, baseSleepTimeMs, maxRetries);
|
||||
CuratorFramework client = CuratorFrameworkFactory.builder()
|
||||
.connectString(zookeeperServerAddr)
|
||||
.retryPolicy(new ExponentialBackoffRetry(NumberUtils.toInt(baseSleepTimeMs, 3000), NumberUtils.toInt(maxRetries, 3)))
|
||||
.build();
|
||||
|
||||
client.start();
|
||||
|
||||
setClient(client);
|
||||
}
|
||||
|
||||
public static String getRouteRootPath() {
|
||||
return WebsiteConstants.SOP_SERVICE_ROUTE_PATH;
|
||||
}
|
||||
|
||||
public static CuratorFramework getClient() {
|
||||
return client;
|
||||
}
|
||||
|
||||
public static void setClient(CuratorFramework client) {
|
||||
ZookeeperContext.client = client;
|
||||
}
|
||||
|
||||
/**
|
||||
* 监听子节点,可以自定义层级
|
||||
* @param parentPath 父节点路径
|
||||
* @param maxDepth 层级,从1开始。比如当前监听节点/t1,目录最深为/t1/t2/t3/t4,则maxDepth=3,说明下面3级子目录全
|
||||
* @param listener
|
||||
* @throws Exception
|
||||
*/
|
||||
public static void listenChildren(String parentPath, int maxDepth, TreeCacheListener listener) throws Exception {
|
||||
final TreeCache treeCache = TreeCache
|
||||
.newBuilder(client, parentPath)
|
||||
.setCacheData(true)
|
||||
.setMaxDepth(maxDepth)
|
||||
.build();
|
||||
|
||||
treeCache.getListenable().addListener(listener);
|
||||
//没有开启模式作为入参的方法
|
||||
treeCache.start();
|
||||
}
|
||||
|
||||
}
|
@@ -65,10 +65,13 @@ public class DocController {
|
||||
}
|
||||
|
||||
|
||||
@GetMapping("/doc/reload")
|
||||
public void reload(String pwd) {
|
||||
if (StringUtils.equals(this.pwd, pwd)) {
|
||||
// 后门地址,可手动更新文档内容,一般情况下用不到
|
||||
@GetMapping("/reload")
|
||||
public String reload(String pwd) {
|
||||
boolean correct = StringUtils.equals(this.pwd, pwd);
|
||||
if (correct) {
|
||||
docManager.load();
|
||||
}
|
||||
return String.valueOf(correct);
|
||||
}
|
||||
}
|
||||
|
@@ -8,12 +8,14 @@ import com.gitee.sop.websiteserver.bean.EurekaApplication;
|
||||
import com.gitee.sop.websiteserver.bean.EurekaApps;
|
||||
import com.gitee.sop.websiteserver.bean.EurekaInstance;
|
||||
import com.gitee.sop.websiteserver.bean.EurekaUri;
|
||||
import com.gitee.sop.websiteserver.bean.ZookeeperContext;
|
||||
import com.gitee.sop.websiteserver.vo.ServiceInfoVO;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import okhttp3.OkHttpClient;
|
||||
import okhttp3.Request;
|
||||
import okhttp3.Response;
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
import org.apache.curator.framework.recipes.cache.TreeCacheEvent;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.http.HttpStatus;
|
||||
@@ -29,6 +31,11 @@ import java.util.Collection;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.DelayQueue;
|
||||
import java.util.concurrent.Delayed;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
@@ -53,13 +60,19 @@ public class DocManagerImpl implements DocManager {
|
||||
|
||||
DocParser easyopenDocParser = new EasyopenDocParser();
|
||||
|
||||
private String secret = "b749a2ec000f4f29p";
|
||||
ExecutorService executorService = Executors.newSingleThreadExecutor();
|
||||
|
||||
DelayQueue<Msg> queue = new DelayQueue<>();
|
||||
|
||||
private String secret = "b749a2ec000f4f29";
|
||||
|
||||
@Autowired
|
||||
private Environment environment;
|
||||
|
||||
private String eurekaUrl;
|
||||
|
||||
private volatile boolean listenInited;
|
||||
|
||||
@Override
|
||||
public void load() {
|
||||
try {
|
||||
@@ -70,7 +83,7 @@ public class DocManagerImpl implements DocManager {
|
||||
ServiceInfoVO serviceInfoVo = entry.getValue().get(0);
|
||||
loadDocInfo(serviceInfoVo);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
} catch (Exception e) {
|
||||
log.error("加载失败", e);
|
||||
}
|
||||
}
|
||||
@@ -136,11 +149,13 @@ public class DocManagerImpl implements DocManager {
|
||||
.forEach(eurekaApplication -> {
|
||||
List<EurekaInstance> instanceList = eurekaApplication.getInstance();
|
||||
for (EurekaInstance instance : instanceList) {
|
||||
ServiceInfoVO vo = new ServiceInfoVO();
|
||||
vo.setName(eurekaApplication.getName());
|
||||
vo.setIpAddr(instance.getIpAddr());
|
||||
vo.setServerPort(instance.fetchPort());
|
||||
serviceInfoVoList.add(vo);
|
||||
if ("UP".equals(instance.getStatus())) {
|
||||
ServiceInfoVO vo = new ServiceInfoVO();
|
||||
vo.setName(eurekaApplication.getName());
|
||||
vo.setIpAddr(instance.getIpAddr());
|
||||
vo.setServerPort(instance.fetchPort());
|
||||
serviceInfoVoList.add(vo);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
@@ -162,7 +177,7 @@ public class DocManagerImpl implements DocManager {
|
||||
}
|
||||
|
||||
@PostConstruct
|
||||
protected void after() {
|
||||
protected void after() throws Exception {
|
||||
String eurekaUrls = environment.getProperty("eureka.client.serviceUrl.defaultZone");
|
||||
if (StringUtils.isBlank(eurekaUrls)) {
|
||||
throw new IllegalArgumentException("未指定eureka.client.serviceUrl.defaultZone参数");
|
||||
@@ -172,5 +187,82 @@ public class DocManagerImpl implements DocManager {
|
||||
url = eurekaUrls.substring(0, eurekaUrls.length() - 1);
|
||||
}
|
||||
this.eurekaUrl = url;
|
||||
|
||||
this.listenServiceId();
|
||||
}
|
||||
|
||||
/**
|
||||
* 监听serviceId更改
|
||||
*
|
||||
* @throws Exception
|
||||
*/
|
||||
protected void listenServiceId() throws Exception {
|
||||
|
||||
executorService.execute(new Consumer(queue, this));
|
||||
|
||||
ZookeeperContext.setEnvironment(environment);
|
||||
String routeRootPath = ZookeeperContext.getRouteRootPath();
|
||||
// 如果节点内容有变化则自动更新文档
|
||||
ZookeeperContext.listenChildren(routeRootPath, 1, (client, event) -> {
|
||||
if (listenInited) {
|
||||
long id = System.currentTimeMillis();
|
||||
// 延迟20秒执行
|
||||
queue.offer(new Msg(id, 1000 * 20));
|
||||
}
|
||||
TreeCacheEvent.Type type = event.getType();
|
||||
if (type == TreeCacheEvent.Type.INITIALIZED) {
|
||||
listenInited = true;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
static class Msg implements Delayed {
|
||||
private long id;
|
||||
private long delay;
|
||||
|
||||
// 自定义实现比较方法返回 1 0 -1三个参数
|
||||
|
||||
|
||||
public Msg(long id, long delay) {
|
||||
this.id = id;
|
||||
this.delay = delay + System.currentTimeMillis();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int compareTo(Delayed delayed) {
|
||||
Msg msg = (Msg) delayed;
|
||||
return Long.valueOf(this.id) > Long.valueOf(msg.id) ? 1
|
||||
: (Long.valueOf(this.id) < Long.valueOf(msg.id) ? -1 : 0);
|
||||
}
|
||||
|
||||
// 延迟任务是否到时就是按照这个方法判断如果返回的是负数则说明到期否则还没到期
|
||||
@Override
|
||||
public long getDelay(TimeUnit unit) {
|
||||
return unit.convert(this.delay - System.currentTimeMillis(), TimeUnit.MILLISECONDS);
|
||||
}
|
||||
}
|
||||
|
||||
@Slf4j
|
||||
static class Consumer implements Runnable {
|
||||
private DelayQueue<Msg> queue;
|
||||
private DocManager docManager;
|
||||
|
||||
public Consumer(DelayQueue<Msg> queue, DocManager docManager) {
|
||||
this.queue = queue;
|
||||
this.docManager = docManager;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
while (true) {
|
||||
try {
|
||||
queue.take();
|
||||
log.info("延迟队列触发--重新加载文档信息");
|
||||
docManager.load();
|
||||
} catch (InterruptedException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user