From 02f86f93d2ea61f65108e6ac7c583285b8bbcd52 Mon Sep 17 00:00:00 2001 From: zhangzhiyong Date: Mon, 27 Nov 2023 11:48:02 +0800 Subject: [PATCH 1/3] update --- .../openai/src/main/java/run/mone/openai/OpenaiCall.java | 2 +- .../src/test/java/run/mone/openapi/OpenApiTest.java | 8 +++++++- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/jcommon/openai/src/main/java/run/mone/openai/OpenaiCall.java b/jcommon/openai/src/main/java/run/mone/openai/OpenaiCall.java index 2c65952ee..8f4fafa1d 100644 --- a/jcommon/openai/src/main/java/run/mone/openai/OpenaiCall.java +++ b/jcommon/openai/src/main/java/run/mone/openai/OpenaiCall.java @@ -265,7 +265,7 @@ public void onClosed(EventSource eventSource) { @Override public void onFailure(EventSource eventSource, @Nullable Throwable t, @Nullable Response response) { - log.error("on failure error:" + t, t); + log.error("on failure error:" + response, t); } }); } diff --git a/jcommon/openai/src/test/java/run/mone/openapi/OpenApiTest.java b/jcommon/openai/src/test/java/run/mone/openapi/OpenApiTest.java index c37f33d55..1c25e6a22 100644 --- a/jcommon/openai/src/test/java/run/mone/openapi/OpenApiTest.java +++ b/jcommon/openai/src/test/java/run/mone/openapi/OpenApiTest.java @@ -26,6 +26,7 @@ import io.reactivex.disposables.Disposable; import lombok.Data; import lombok.SneakyThrows; +import okhttp3.Response; import okhttp3.logging.HttpLoggingInterceptor; import okhttp3.sse.EventSource; import okhttp3.sse.EventSourceListener; @@ -168,7 +169,7 @@ private OpenAiClient client() { public void testCallStream() { String key = System.getenv("open_api_key"); CountDownLatch latch = new CountDownLatch(1); - OpenaiCall.callStream(key, null, "天空为什么是蓝色的", new String[]{}, new StreamListener() { + OpenaiCall.callStream(key, "", "天空为什么是蓝色的", new String[]{}, new StreamListener() { @Override public void onEvent(String str) { System.out.println(str); @@ -178,6 +179,11 @@ public void onEvent(String str) { public void end() { latch.countDown(); } + + @Override + public void onFailure(Throwable t, Response response) { + System.out.println(t + "" + response); + } }); latch.await(); } From 45628ab39a7c3f94beb930b9c5f7092a5dbac689 Mon Sep 17 00:00:00 2001 From: zhangzhiyong Date: Sun, 10 Mar 2024 10:20:11 +0800 Subject: [PATCH 2/3] The vertices of the graph support the map data structure clsoe(#810) --- jcommon/ai/pom.xml | 24 ++++ jcommon/ai/src/main/resources/prompt.txt | 80 ++++++++++++ jcommon/ai/src/main/resources/prompt2.txt | 46 +++++++ jcommon/ai/src/main/resources/prompt3.txt | 1 + jcommon/ai/zhipu/pom.xml | 38 ++++++ .../ai/zhipu/src/main/java/run/mone/Main.java | 57 +++++++++ .../java/com/xiaomi/youpin/docean/Ioc.java | 23 ++++ .../youpin/docean/anno/IocConfiguration.java | 16 +++ .../xiaomi/youpin/docean/test/TestRun.java | 21 ++++ .../main/java/run/mone/openai/OpenaiCall.java | 6 +- .../java/run/mone/openapi/OpenApiTest.java | 31 +++++ jcommon/pom.xml | 1 + .../com/xiaomi/data/push/graph/Graph.java | 12 ++ .../com/xiaomi/data/push/graph/Graph2.java | 114 ++++++++++++++++++ .../java/run/mone/struct/test/GraphTest.java | 22 ++++ 15 files changed, 491 insertions(+), 1 deletion(-) create mode 100644 jcommon/ai/pom.xml create mode 100644 jcommon/ai/src/main/resources/prompt.txt create mode 100644 jcommon/ai/src/main/resources/prompt2.txt create mode 100644 jcommon/ai/src/main/resources/prompt3.txt create mode 100644 jcommon/ai/zhipu/pom.xml create mode 100644 jcommon/ai/zhipu/src/main/java/run/mone/Main.java create mode 100644 jcommon/docean/src/main/java/com/xiaomi/youpin/docean/anno/IocConfiguration.java create mode 100644 jcommon/docean/src/test/java/com/xiaomi/youpin/docean/test/TestRun.java create mode 100644 jcommon/struct/src/main/java/com/xiaomi/data/push/graph/Graph2.java diff --git a/jcommon/ai/pom.xml b/jcommon/ai/pom.xml new file mode 100644 index 000000000..1fe47397e --- /dev/null +++ b/jcommon/ai/pom.xml @@ -0,0 +1,24 @@ + + + 4.0.0 + + run.mone + jcommon + 1.4-jdk20-SNAPSHOT + + + ai + pom + + zhipu + + + + 21 + 21 + UTF-8 + + + \ No newline at end of file diff --git a/jcommon/ai/src/main/resources/prompt.txt b/jcommon/ai/src/main/resources/prompt.txt new file mode 100644 index 000000000..51956345a --- /dev/null +++ b/jcommon/ai/src/main/resources/prompt.txt @@ -0,0 +1,80 @@ +你是一名高级groovy工程师. +你要完成的好,我会给你100$小费. +我会给你提供一些代码只是和业务需求,请帮我生成相应的$code(groovy代码)代码和$params和$out. +你只需要返回一个方法和参数列表,方法的名字统一叫execute,参数: 第一个是 + JsonObject input, 第二个是Object context +JsonObject必须用Gson中的库 +不要生成任何测试代码 +不要生成任何说明,只需要返回一个json结构的内容即可 +你要生成一些必要的import +你给我返回的是一个JsonObject(Gson中的类) +你的返回结果里决不能用任何markdown格式包裹(比如:```json ``` ```groovy ```) +不要输出换行符 比如 \n \r等 +$code就是你要生成的代码内容 +$params就是参数名列表 +$outs就是返回结果的列表 + +最终你产生的结果 +{"code":$code,"params":$params,"outs":$outs} + +$params的格式举例:[{"name":"a","tpye":"int"}] +$outs的格式举例:[{"name":"sum","type":"int"}] + +一些工具库使用,你可以借鉴: + + +DbUtils里边有些工具方法可以操作数据库 + + /** + * 将提供的键值对数据插入到指定的数据库表中。 + */ + public Long insert(String tableName, Map data) + + /** + * 更新指定表的指定ID的记录,通过传入的键值对映射来设置新的列值 + */ + public void update(String tableName, String primaryKeyName, Map data) + + // 根据id列表批量删除 + public void deleteByIds(String tableName, String idName, List ids) + + +你尽量使用我给你提供的工具类,DbUtils 直接可以从context中获取 context.getDbUtils + + +我给你一个例子: + +需求: +计算两数和 + + +返回: +{ + "code": "def execute(JsonObject input, Object context) {\n if (!input.has('a') || !input.has('b')) {\n throw new IllegalArgumentException(\"JSON对象必须包含键'a'和'b'。\");\n }\n int a = input.get('a').getAsInt();\n int b = input.get('b').getAsInt();\n int sum = a + b;\n JsonObject result = new JsonObject();\n result.addProperty(\"sum\", sum);\n return result;\n}", + "params": [ + { + "name": "a", + "type": "int" + }, + { + "name": "b", + "type": "int" + } + ], + "outs": [ + { + "name": "sum", + "type": "int" + } + ] +} + +例子结束 + + + +需求: +给定一个List,返回这个list中的最大值和最小值 + +返回: + diff --git a/jcommon/ai/src/main/resources/prompt2.txt b/jcommon/ai/src/main/resources/prompt2.txt new file mode 100644 index 000000000..995f150f7 --- /dev/null +++ b/jcommon/ai/src/main/resources/prompt2.txt @@ -0,0 +1,46 @@ +你是一名高级groovy工程师. +你要完成的好,我会给你100$小费. +我会给你提供一个groovy方法,你帮我生成这个方法的描述(必须少于15个字). +你的返回结果永远是一个json格式的数据. +你的返回结果里决不能用任何markdown格式包裹(比如:```groovy ```) +不要生成任何说明,只需要返回一个json结构的内容即可 + +$comment就是你生成的注释 + +{"comment":"$comment"} + + + + +我给你一个例子: + +code: +def execute(JsonObject input, Object context) { + if (!input.has('a') || !input.has('b')) { + throw new IllegalArgumentException("JSON对象必须包含键'a'和'b'。"); + } + int a = input.get('a').getAsInt(); + int b = input.get('b').getAsInt(); + int sum = a + b; + JsonObject result = new JsonObject(); + result.addProperty("result", sum); + return result; +} + + +你返回的: +{"comment":"计算两数和"} + + + +例子结束 + + + + + + +code: +int a(int a, int b) { return a * b; } + +你的返回: diff --git a/jcommon/ai/src/main/resources/prompt3.txt b/jcommon/ai/src/main/resources/prompt3.txt new file mode 100644 index 000000000..3713b852e --- /dev/null +++ b/jcommon/ai/src/main/resources/prompt3.txt @@ -0,0 +1 @@ +李清照最好的6首词,并且给我解读 \ No newline at end of file diff --git a/jcommon/ai/zhipu/pom.xml b/jcommon/ai/zhipu/pom.xml new file mode 100644 index 000000000..5bebe7c32 --- /dev/null +++ b/jcommon/ai/zhipu/pom.xml @@ -0,0 +1,38 @@ + + + 4.0.0 + + run.mone + ai + 1.4-jdk20-SNAPSHOT + + + zhipu + + + 21 + 21 + UTF-8 + + + + + + cn.bigmodel.openapi + oapi-java-sdk + release-V4-2.0.0 + + + + com.google.code.gson + gson + 2.8.5 + + + + + + + \ No newline at end of file diff --git a/jcommon/ai/zhipu/src/main/java/run/mone/Main.java b/jcommon/ai/zhipu/src/main/java/run/mone/Main.java new file mode 100644 index 000000000..c0800b973 --- /dev/null +++ b/jcommon/ai/zhipu/src/main/java/run/mone/Main.java @@ -0,0 +1,57 @@ +package run.mone; + +import com.zhipu.oapi.ClientV4; +import com.zhipu.oapi.Constants; +import com.zhipu.oapi.service.v4.model.ChatCompletionRequest; +import com.zhipu.oapi.service.v4.model.ChatMessage; +import com.zhipu.oapi.service.v4.model.ChatMessageRole; +import com.zhipu.oapi.service.v4.model.ModelApiResponse; +import lombok.SneakyThrows; + +import java.nio.file.Files; +import java.nio.file.Paths; +import java.util.ArrayList; +import java.util.List; + +/** + * @author goodjava@qq.com + * @date 2024/3/10 07:55 + */ +public class Main { + + private static final String requestIdTemplate = "myoz-%d"; + + + private static final String KEY = System.getenv("zhipu"); + + private static final String API_KEY = KEY.split("\\.")[0]; + + private static final String API_SECRET = KEY.split("\\.")[1]; + + private static final ClientV4 client = new ClientV4.Builder(API_KEY, API_SECRET).build(); + + + @SneakyThrows + public static void main(String[] args) { + List messages = new ArrayList<>(); + + String promptName = "prompt.txt"; + + String content = Files.readString(Paths.get("/Users/zhangzhiyong/IdeaProjects/goodjava/mone/jcommon/ai/zhipu/src/main/resources/" + promptName)); + + ChatMessage chatMessage = new ChatMessage(ChatMessageRole.USER.value(), content); + messages.add(chatMessage); + String requestId = String.format(requestIdTemplate, System.currentTimeMillis()); + ChatCompletionRequest chatCompletionRequest = ChatCompletionRequest.builder() + .model(Constants.ModelChatGLM4) + .stream(Boolean.FALSE) + .invokeMethod(Constants.invokeMethod) + .messages(messages) + .requestId(requestId) + .build(); + ModelApiResponse invokeModelApiResp = client.invokeModelApi(chatCompletionRequest); + String resContent = invokeModelApiResp.getData().getChoices().get(0).getMessage().getContent().toString(); + System.out.println(resContent); +// System.out.println("model output:"+ new Gson().toJson(invokeModelApiResp)); + } +} \ No newline at end of file diff --git a/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/Ioc.java b/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/Ioc.java index 308737084..e02212203 100644 --- a/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/Ioc.java +++ b/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/Ioc.java @@ -26,6 +26,7 @@ import com.google.gson.reflect.TypeToken; import com.xiaomi.youpin.docean.anno.Component; import com.xiaomi.youpin.docean.anno.Controller; +import com.xiaomi.youpin.docean.anno.IocConfiguration; import com.xiaomi.youpin.docean.anno.Service; import com.xiaomi.youpin.docean.bo.Bean; import com.xiaomi.youpin.docean.common.*; @@ -69,6 +70,9 @@ public class Ioc { @Getter private String[] scanPackages; + @Getter + private Class primarySource; + /** * It needs to be used when interacting with containers like spring */ @@ -357,6 +361,25 @@ public Ioc classLoader(ClassLoader classLoader) { return this; } + public static Ioc run(Class primarySource, String... args) { + IocConfiguration configuration = primarySource.getAnnotation(IocConfiguration.class); + Ioc ioc = Ioc.ins(); + ioc.primarySource = primarySource; + parseArgumentsAndPopulateIoc(args, ioc); + return ioc.init(configuration.basePackage()); + } + + private static void parseArgumentsAndPopulateIoc(String[] args, Ioc ioc) { + //Determine if args is an even number; if so, place it into a map. + Map argsMap = new HashMap<>(); + if (args.length % 2 == 0) { + for (int i = 0; i < args.length; i += 2) { + argsMap.put(args[i], args[i + 1]); + } + } + argsMap.entrySet().forEach(entry -> ioc.putBean("$" + entry.getKey(), entry.getValue())); + } + public Ioc init(String... scanPackages) { this.scanPackages = scanPackages; this.publishEvent(new Event(EventType.initBegin)); diff --git a/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/anno/IocConfiguration.java b/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/anno/IocConfiguration.java new file mode 100644 index 000000000..e2c51adaf --- /dev/null +++ b/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/anno/IocConfiguration.java @@ -0,0 +1,16 @@ +package com.xiaomi.youpin.docean.anno; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +/** + * @author goodjava@qq.com + * @date 2024/3/3 09:19 + */ +@Retention(RetentionPolicy.RUNTIME) +@Target(ElementType.TYPE) // 应用于类 +public @interface IocConfiguration { + String[] basePackage(); +} diff --git a/jcommon/docean/src/test/java/com/xiaomi/youpin/docean/test/TestRun.java b/jcommon/docean/src/test/java/com/xiaomi/youpin/docean/test/TestRun.java new file mode 100644 index 000000000..1d168dc94 --- /dev/null +++ b/jcommon/docean/src/test/java/com/xiaomi/youpin/docean/test/TestRun.java @@ -0,0 +1,21 @@ +package com.xiaomi.youpin.docean.test; + +import com.xiaomi.youpin.docean.Ioc; +import com.xiaomi.youpin.docean.anno.IocConfiguration; +import com.xiaomi.youpin.docean.test.demo.DemoDao; + +/** + * @author goodjava@qq.com + * @date 2024/3/5 14:47 + *

+ * Evaluating the efficacy of @IocConfiguration. + */ +@IocConfiguration(basePackage = {"com.xiaomi.youpin.docean.test.demo"}) +public class TestRun { + + public static void main(String[] args) { + DemoDao demoA = Ioc.run(TestRun.class, args).getBean(DemoDao.class); + System.out.println(demoA.get()); + } + +} diff --git a/jcommon/openai/src/main/java/run/mone/openai/OpenaiCall.java b/jcommon/openai/src/main/java/run/mone/openai/OpenaiCall.java index 8f4fafa1d..8644f7415 100644 --- a/jcommon/openai/src/main/java/run/mone/openai/OpenaiCall.java +++ b/jcommon/openai/src/main/java/run/mone/openai/OpenaiCall.java @@ -270,6 +270,9 @@ public void onFailure(EventSource eventSource, @Nullable Throwable t, @Nullable }); } + public static void callStream2(String req, StreamListener sl, ReqConfig config) { + callStream2(req, sl, config, null); + } /** * 原生的调用,底层只依赖okhttp @@ -278,10 +281,11 @@ public void onFailure(EventSource eventSource, @Nullable Throwable t, @Nullable * @param sl * @param config */ - public static void callStream2(String req, StreamListener sl, ReqConfig config) { + public static void callStream2(String req, StreamListener sl, ReqConfig config, Headers headers) { MediaType mediaType = MediaType.parse("application/json; charset=utf-8"); Request request = new Request.Builder() + .headers(headers) .url(config.getAskUrl()) .post(RequestBody.create(mediaType, req.getBytes(Charset.forName("utf8")))) .build(); diff --git a/jcommon/openai/src/test/java/run/mone/openapi/OpenApiTest.java b/jcommon/openai/src/test/java/run/mone/openapi/OpenApiTest.java index 1c25e6a22..dcb862c5b 100644 --- a/jcommon/openai/src/test/java/run/mone/openapi/OpenApiTest.java +++ b/jcommon/openai/src/test/java/run/mone/openapi/OpenApiTest.java @@ -26,6 +26,7 @@ import io.reactivex.disposables.Disposable; import lombok.Data; import lombok.SneakyThrows; +import okhttp3.Headers; import okhttp3.Response; import okhttp3.logging.HttpLoggingInterceptor; import okhttp3.sse.EventSource; @@ -298,6 +299,36 @@ public void test4() { System.out.println(res.getChoices().get(0).getMessage().getContent()); } + @SneakyThrows + @Test + public void testMoonshot() { + Stopwatch stopwatch = Stopwatch.createStarted(); + String question = Files.readString(Paths.get("/Users/zhangzhiyong/IdeaProjects/goodjava/mone/jcommon/ai/src/main/resources/prompt.txt")); + OpenAiClient client = OpenaiCall.client(System.getenv("moonshot_token"), "https://api.moonshot.cn/"); + ChatCompletionResponse res = client.chatCompletion(ChatCompletion.builder().model("moonshot-v1-8k").messages(Lists.newArrayList(Message.builder() + .role(Message.Role.USER).content(question) + .build())).build()); + System.out.println(res.getChoices().get(0).getMessage().getContent()); + System.out.println("use time:" + stopwatch.elapsed(TimeUnit.MILLISECONDS)); + } + + @SneakyThrows + @Test + public void testMoonshot2() { + String question = Files.readString(Paths.get("/Users/zhangzhiyong/IdeaProjects/goodjava/mone/jcommon/ai/src/main/resources/prompt3.txt")); + ChatCompletion completion = ChatCompletion.builder().stream(true).model("moonshot-v1-8k").messages(Lists.newArrayList(Message.builder() + .role(Message.Role.USER).content(question) + .build())).build(); + + OpenaiCall.callStream2(new Gson().toJson(completion), new StreamListener() { + @Override + public void onEvent(String str) { + System.out.println(str); + } + }, ReqConfig.builder().model("moonshot-v1-8k").askUrl("https://api.moonshot.cn/v1/chat/completions").build(), Headers.of("Authorization", "Bearer " + System.getenv("moonshot_token"))); + System.in.read(); + } + /** * 测试使用Azure的openai * POST https://b2c-mione-gpt35.openai.azure.com/openai/deployments/gpt-35-turbo/completions?api-version=2023-05-15 diff --git a/jcommon/pom.xml b/jcommon/pom.xml index 5cdfcac09..e96e2bf0c 100644 --- a/jcommon/pom.xml +++ b/jcommon/pom.xml @@ -86,6 +86,7 @@ match infra-common docean-spring-starter + ai diff --git a/jcommon/struct/src/main/java/com/xiaomi/data/push/graph/Graph.java b/jcommon/struct/src/main/java/com/xiaomi/data/push/graph/Graph.java index 548604199..b14bb9cec 100644 --- a/jcommon/struct/src/main/java/com/xiaomi/data/push/graph/Graph.java +++ b/jcommon/struct/src/main/java/com/xiaomi/data/push/graph/Graph.java @@ -62,6 +62,18 @@ public void addVertex(Vertex vertex) { this.vertexMap.put(vertex.getV(), vertex.getData()); } + //删除这个顶点,且删除和它相关的所有边(class) + public void removeVertex(int v) { + // 删除顶点数据 + vertexMap.remove(v); + // 删除所有出边 + adj[v].clear(); + // 删除所有入边 + for (List edges : adj) { + edges.removeIf(edge -> edge == v); + } + } + public List dependList(int v) { List result = Lists.newArrayList(); diff --git a/jcommon/struct/src/main/java/com/xiaomi/data/push/graph/Graph2.java b/jcommon/struct/src/main/java/com/xiaomi/data/push/graph/Graph2.java new file mode 100644 index 000000000..c601477f2 --- /dev/null +++ b/jcommon/struct/src/main/java/com/xiaomi/data/push/graph/Graph2.java @@ -0,0 +1,114 @@ +package com.xiaomi.data.push.graph; + +import com.google.common.collect.Maps; + +import java.util.*; + +/** + * @author goodjava@qq.com + * @date 2024/3/12 14:49 + */ +public class Graph2 { + + + //存储顶点的map + private Map vertexMap = Maps.newHashMap(); + + //存储边 + private Map> adjMap = Maps.newHashMap(); + + + /** + * 添加顶点 + * + * @param vertex + */ + public void addVertex(Vertex vertex) { + this.vertexMap.put(vertex.getV(), vertex.getData()); + } + + public void addEdge(int u, int v) { + //添加边 + if (!adjMap.containsKey(u)) { + adjMap.put(u, new ArrayList<>()); + } + adjMap.get(u).add(v); + } + + //删除这个顶点,且删除和它相关的所有边(class) + public void removeVertex(int vertex) { + // Remove the vertex from vertexMap + if (!vertexMap.containsKey(vertex)) { + throw new IllegalArgumentException("Vertex does not exist."); + } + vertexMap.remove(vertex); + + // Remove all edges associated with this vertex from adjMap + if (adjMap.containsKey(vertex)) { + adjMap.remove(vertex); + } + + // Remove the vertex from all adjacency lists + for (List edges : adjMap.values()) { + edges.removeIf(edge -> edge.equals(vertex)); + } + } + + public D getVertexData(int id) { + return vertexMap.get(id); + } + + + //帮我实现下拓扑排序(class) + public List topologicalSort() { + List result = new ArrayList<>(); + Map inDegree = new HashMap<>(); + Queue queue = new LinkedList<>(); + + // Initialize in-degree of all vertices + for (Integer v : vertexMap.keySet()) { + inDegree.put(v, 0); + } + + // Calculate in-degree of each vertex + for (List edges : adjMap.values()) { + for (Integer edge : edges) { + inDegree.put(edge, inDegree.get(edge) + 1); + } + } + + // Find all vertices with in-degree 0 + for (Map.Entry entry : inDegree.entrySet()) { + if (entry.getValue() == 0) { + queue.add(entry.getKey()); + } + } + + // Process vertices with in-degree 0 + while (!queue.isEmpty()) { + Integer vertex = queue.poll(); + result.add(vertex); + + // Decrease in-degree by 1 for all adjacent vertices + if (adjMap.containsKey(vertex)) { + for (Integer adjVertex : adjMap.get(vertex)) { + inDegree.put(adjVertex, inDegree.get(adjVertex) - 1); + + // If in-degree becomes 0, add it to the queue + if (inDegree.get(adjVertex) == 0) { + queue.add(adjVertex); + } + } + } + } + + // Check if there was a cycle + if (result.size() != vertexMap.size()) { + throw new IllegalStateException("Graph has a cycle, topological sort not possible"); + } + + return result; + } + + +} diff --git a/jcommon/struct/src/test/java/run/mone/struct/test/GraphTest.java b/jcommon/struct/src/test/java/run/mone/struct/test/GraphTest.java index 92fd594ca..f523339a5 100644 --- a/jcommon/struct/src/test/java/run/mone/struct/test/GraphTest.java +++ b/jcommon/struct/src/test/java/run/mone/struct/test/GraphTest.java @@ -1,6 +1,7 @@ package run.mone.struct.test; import com.xiaomi.data.push.graph.Graph; +import com.xiaomi.data.push.graph.Graph2; import com.xiaomi.data.push.graph.Vertex; import org.junit.Test; @@ -12,6 +13,27 @@ */ public class GraphTest { + + @Test + public void test1() { + Graph2 graph = new Graph2<>(); + + graph.addVertex(new Vertex<>(44, VertexData.builder().data("执行").id(0).build())); + graph.addVertex(new Vertex<>(88, VertexData.builder().data("aaa").id(0).build())); + graph.addVertex(new Vertex<>(33, VertexData.builder().data("开始").id(0).build())); + graph.addVertex(new Vertex<>(22, VertexData.builder().data("结束").id(0).build())); + + graph.addEdge(33,44); + graph.addEdge(44,22); + graph.addEdge(22,88); + + +// graph.removeVertex(44); + + List list = graph.topologicalSort(); + System.out.println(list); + } + @Test public void initializeAndTopologicallySortGraph() { Graph graph = new Graph<>(5); From 4c2be31fae466590c8eedf8e65d1cda5fd5c68c8 Mon Sep 17 00:00:00 2001 From: zhangzhiyong Date: Fri, 22 Mar 2024 18:25:12 +0800 Subject: [PATCH 3/3] Request for CLAUDE 3 Support (close #822) --- jcommon/ai/google/pom.xml | 44 +++++ .../java/run/mone/ai/google/CloudeClient.java | 69 ++++++++ .../java/run/mone/ai/google/bo/Content.java | 20 +++ .../java/run/mone/ai/google/bo/Message.java | 21 +++ .../run/mone/ai/google/bo/RequestPayload.java | 32 ++++ .../mone/ai/google/bo/ResponsePayload.java | 39 +++++ .../java/run/mone/ai/google/bo/Usage.java | 19 +++ .../run/mone/ai/google/test/ClientTest.java | 28 ++++ jcommon/ai/moonshot/pom.xml | 31 ++++ .../src/main/java/run/mone/Moonshot.java | 151 ++++++++++++++++++ .../main/java/run/mone/bo/ChatCompletion.java | 27 ++++ .../src/main/java/run/mone/bo/Choice.java | 23 +++ .../src/main/java/run/mone/bo/Message.java | 25 +++ .../java/run/mone/bo/RequestBodyContent.java | 24 +++ .../src/main/java/run/mone/bo/Usage.java | 28 ++++ .../test/java/run/mone/test/MoonshotTest.java | 61 +++++++ jcommon/ai/pom.xml | 2 + jcommon/ai/src/main/resources/prompt4.txt | 100 ++++++++++++ .../ai/zhipu/src/main/java/run/mone/Main.java | 4 +- .../docean-plugin-mongodb/pom.xml | 1 + .../youpin/docean/plugin/mongodb/MongoDb.java | 30 ++-- .../docean-plugin/docean-plugin-test/pom.xml | 15 ++ .../plugin/test/mongodb/MongodbTest.java | 58 +++++++ .../java/com/xiaomi/youpin/docean/Mvc.java | 5 + .../youpin/docean/anno/RequestMapping.java | 2 +- .../youpin/docean/common/ReflectUtils.java | 13 +- .../java/com/xiaomi/youpin/docean/test/A.java | 11 ++ .../com/xiaomi/youpin/docean/test/AA.java | 10 ++ .../youpin/docean/test/ReflectUtilsTest.java | 9 ++ .../main/java/run/mone/excel/ExportExcel.java | 18 +-- .../test/java/run/mone/excel/ExcelTest.java | 38 +++++ 31 files changed, 927 insertions(+), 31 deletions(-) create mode 100644 jcommon/ai/google/pom.xml create mode 100644 jcommon/ai/google/src/main/java/run/mone/ai/google/CloudeClient.java create mode 100644 jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Content.java create mode 100644 jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Message.java create mode 100644 jcommon/ai/google/src/main/java/run/mone/ai/google/bo/RequestPayload.java create mode 100644 jcommon/ai/google/src/main/java/run/mone/ai/google/bo/ResponsePayload.java create mode 100644 jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Usage.java create mode 100644 jcommon/ai/google/src/test/java/run/mone/ai/google/test/ClientTest.java create mode 100644 jcommon/ai/moonshot/pom.xml create mode 100644 jcommon/ai/moonshot/src/main/java/run/mone/Moonshot.java create mode 100644 jcommon/ai/moonshot/src/main/java/run/mone/bo/ChatCompletion.java create mode 100644 jcommon/ai/moonshot/src/main/java/run/mone/bo/Choice.java create mode 100644 jcommon/ai/moonshot/src/main/java/run/mone/bo/Message.java create mode 100644 jcommon/ai/moonshot/src/main/java/run/mone/bo/RequestBodyContent.java create mode 100644 jcommon/ai/moonshot/src/main/java/run/mone/bo/Usage.java create mode 100644 jcommon/ai/moonshot/src/test/java/run/mone/test/MoonshotTest.java create mode 100644 jcommon/ai/src/main/resources/prompt4.txt create mode 100644 jcommon/docean-plugin/docean-plugin-test/src/test/java/com/xiaomi/youpin/docean/plugin/test/mongodb/MongodbTest.java create mode 100644 jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/A.java create mode 100644 jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/AA.java create mode 100644 jcommon/excel/src/test/java/run/mone/excel/ExcelTest.java diff --git a/jcommon/ai/google/pom.xml b/jcommon/ai/google/pom.xml new file mode 100644 index 000000000..af5c82b69 --- /dev/null +++ b/jcommon/ai/google/pom.xml @@ -0,0 +1,44 @@ + + + 4.0.0 + + run.mone + ai + 1.4-jdk20-SNAPSHOT + + + google + + + 21 + 21 + UTF-8 + + + + + + com.google.auth + google-auth-library-oauth2-http + 1.23.0 + + + + com.squareup.okhttp3 + okhttp + 4.10.0 + + + + org.junit.jupiter + junit-jupiter + RELEASE + test + + + + + + \ No newline at end of file diff --git a/jcommon/ai/google/src/main/java/run/mone/ai/google/CloudeClient.java b/jcommon/ai/google/src/main/java/run/mone/ai/google/CloudeClient.java new file mode 100644 index 000000000..871f05495 --- /dev/null +++ b/jcommon/ai/google/src/main/java/run/mone/ai/google/CloudeClient.java @@ -0,0 +1,69 @@ +package run.mone.ai.google; + +import com.google.auth.oauth2.AccessToken; +import com.google.auth.oauth2.GoogleCredentials; +import com.google.gson.Gson; +import lombok.Data; +import lombok.SneakyThrows; +import okhttp3.*; +import run.mone.ai.google.bo.RequestPayload; +import run.mone.ai.google.bo.ResponsePayload; + +import java.io.FileInputStream; +import java.io.IOException; +import java.util.Collections; + +/** + * @author goodjava@qq.com + * @date 2024/4/9 15:59 + */ +@Data +public class CloudeClient { + + private String url = "https://us-central1-aiplatform.googleapis.com/v1/projects/"; + + private String googleUrl = "www.googleapis.com"; + + private String projectId = ""; + + private String model = "claude-3-haiku@20240307"; + + private String token; + + + @SneakyThrows + public String token() { + GoogleCredentials credentials = GoogleCredentials.fromStream( + new FileInputStream("/tmp/key.json")) + .createScoped(Collections.singleton("https://" + googleUrl + "/auth/cloud-platform")); + // Use the credentials to authenticate and generate an access token + credentials.refreshIfExpired(); + AccessToken token = credentials.getAccessToken(); + // Now you can use the access token + this.token = token.getTokenValue(); + return this.token; + } + + + public ResponsePayload call(String token, RequestPayload requestPayload) { + OkHttpClient client = new OkHttpClient(); + MediaType mediaType = MediaType.parse("application/json; charset=utf-8"); + RequestBody body = RequestBody.create(mediaType, new Gson().toJson(requestPayload)); + Request request = new Request.Builder() + .url(url + projectId + "/locations/us-central1/publishers/anthropic/models/" + model + ":streamRawPredict") + .post(body) + .addHeader("Authorization", "Bearer " + token) + .addHeader("Content-Type", "application/json; charset=utf-8") + .build(); + + try (Response response = client.newCall(request).execute()) { + if (!response.isSuccessful()) throw new IOException("Unexpected code " + response); + // Handle the response + return new Gson().fromJson(response.body().string(), ResponsePayload.class); + } catch (Exception e) { + e.printStackTrace(); + } + return null; + } + +} diff --git a/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Content.java b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Content.java new file mode 100644 index 000000000..4490d10ce --- /dev/null +++ b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Content.java @@ -0,0 +1,20 @@ +package run.mone.ai.google.bo; + +import lombok.Data; + +import com.google.gson.annotations.SerializedName; + +/** + * @author goodjava@qq.com + * @date 2024/4/9 16:43 + */ +@Data +public class Content { + + @SerializedName("type") + private String type; + + @SerializedName("text") + private String text; + +} diff --git a/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Message.java b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Message.java new file mode 100644 index 000000000..9e1b6237b --- /dev/null +++ b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Message.java @@ -0,0 +1,21 @@ +package run.mone.ai.google.bo; + +import com.google.gson.annotations.SerializedName; +import lombok.Builder; +import lombok.Data; + +/** + * @author goodjava@qq.com + * @date 2024/4/9 16:36 + */ +@Data +@Builder +public class Message { + + @SerializedName("role") + private String role; + + @SerializedName("content") + private String content; + +} diff --git a/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/RequestPayload.java b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/RequestPayload.java new file mode 100644 index 000000000..b649a1331 --- /dev/null +++ b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/RequestPayload.java @@ -0,0 +1,32 @@ +package run.mone.ai.google.bo; + +import com.google.gson.annotations.SerializedName; +import lombok.Builder; +import lombok.Data; + +import java.util.List; + +/** + * @author goodjava@qq.com + * @date 2024/4/9 16:36 + */ +@Data +@Builder +public class RequestPayload { + + + @SerializedName("anthropic_version") + private String anthropicVersion; + + @SerializedName("messages") + private List messages; + + @SerializedName("max_tokens") + private int maxTokens; + + @SerializedName("stream") + private boolean stream; + + + +} diff --git a/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/ResponsePayload.java b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/ResponsePayload.java new file mode 100644 index 000000000..0c8fcacf3 --- /dev/null +++ b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/ResponsePayload.java @@ -0,0 +1,39 @@ +package run.mone.ai.google.bo; + +import com.google.gson.annotations.SerializedName; +import lombok.Data; + +import java.util.List; + +/** + * @author goodjava@qq.com + * @date 2024/4/9 16:41 + */ +@Data +public class ResponsePayload { + + @SerializedName("id") + private String id; + + @SerializedName("type") + private String type; + + @SerializedName("role") + private String role; + + @SerializedName("content") + private List content; + + @SerializedName("model") + private String model; + + @SerializedName("stop_reason") + private String stopReason; + + @SerializedName("stop_sequence") + private Object stopSequence; // Use Object if the value can be null or of different types + + @SerializedName("usage") + private Usage usage; + +} diff --git a/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Usage.java b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Usage.java new file mode 100644 index 000000000..95e47c736 --- /dev/null +++ b/jcommon/ai/google/src/main/java/run/mone/ai/google/bo/Usage.java @@ -0,0 +1,19 @@ +package run.mone.ai.google.bo; + +import com.google.gson.annotations.SerializedName; + +/** + * @author goodjava@qq.com + * @date 2024/4/9 16:42 + */ +public class Usage { + + + @SerializedName("input_tokens") + private int inputTokens; + + @SerializedName("output_tokens") + private int outputTokens; + + +} diff --git a/jcommon/ai/google/src/test/java/run/mone/ai/google/test/ClientTest.java b/jcommon/ai/google/src/test/java/run/mone/ai/google/test/ClientTest.java new file mode 100644 index 000000000..575d843bf --- /dev/null +++ b/jcommon/ai/google/src/test/java/run/mone/ai/google/test/ClientTest.java @@ -0,0 +1,28 @@ +package run.mone.ai.google.test; + +import com.google.common.collect.Lists; +import org.junit.Test; +import run.mone.ai.google.CloudeClient; +import run.mone.ai.google.bo.Message; +import run.mone.ai.google.bo.RequestPayload; +import run.mone.ai.google.bo.ResponsePayload; + +/** + * @author goodjava@qq.com + * @date 2024/4/9 16:24 + */ +public class ClientTest { + + @Test + public void test1() { + String content = "天空为什么是蓝色的?"; +// String content = "树上有10只鸟,我开了一枪还有几只鸟?"; + CloudeClient c = new CloudeClient(); + c.setProjectId(System.getenv("google_project_id")); + RequestPayload payload = RequestPayload.builder().maxTokens(4000).anthropicVersion("vertex-2023-10-16").messages(Lists.newArrayList(Message.builder().role("user") + .content(content) + .build())).build(); + ResponsePayload r = c.call(c.token(), payload); + System.out.println(r.getContent().get(0).getText()); + } +} diff --git a/jcommon/ai/moonshot/pom.xml b/jcommon/ai/moonshot/pom.xml new file mode 100644 index 000000000..2736df9a2 --- /dev/null +++ b/jcommon/ai/moonshot/pom.xml @@ -0,0 +1,31 @@ + + + 4.0.0 + + run.mone + ai + 1.4-jdk20-SNAPSHOT + + + moonshot + + + 21 + 21 + UTF-8 + + + + + + com.squareup.okhttp3 + okhttp + 4.10.0 + + + + + + \ No newline at end of file diff --git a/jcommon/ai/moonshot/src/main/java/run/mone/Moonshot.java b/jcommon/ai/moonshot/src/main/java/run/mone/Moonshot.java new file mode 100644 index 000000000..506a8274e --- /dev/null +++ b/jcommon/ai/moonshot/src/main/java/run/mone/Moonshot.java @@ -0,0 +1,151 @@ +package run.mone; + + +import com.google.gson.Gson; +import okhttp3.*; +import run.mone.bo.ChatCompletion; +import run.mone.bo.Message; +import run.mone.bo.RequestBodyContent; + +import java.io.IOException; +import java.nio.file.Path; +import java.util.List; +import java.util.concurrent.TimeUnit; + +/** + * @author goodjava@qq.com + * @date 2024/3/26 15:27 + */ +public class Moonshot { + + + //okhttp get 请求,网址:https://api.moonshot.cn/v1/files + public static String getFiles() { + OkHttpClient client = new OkHttpClient(); + Request request = new Request.Builder() + .header("Authorization", "Bearer " + System.getenv("moonshot")) + .url("https://api.moonshot.cn/v1/files") + .build(); + try (Response response = client.newCall(request).execute()) { + if (!response.isSuccessful()) { + throw new IOException("Unexpected code " + response); + } + return response.body().string(); + } catch (IOException e) { + e.printStackTrace(); + return null; + } + } + + //okhttp post 上传文件 网址:https://api.moonshot.cn/v1/files python参考代码:file_object = client.files.create(file=Path("xlnet.pdf"), purpose="file-extract") + public static String uploadFile(Path filePath, String purpose) { + OkHttpClient client = new OkHttpClient(); + MediaType mediaType = MediaType.parse("application/octet-stream"); + RequestBody body = new MultipartBody.Builder().setType(MultipartBody.FORM) + .addFormDataPart("file", filePath.getFileName().toString(), + RequestBody.create(mediaType, filePath.toFile())) + .addFormDataPart("purpose", purpose) + .build(); + Request request = new Request.Builder() + .url("https://api.moonshot.cn/v1/files") + .post(body) + .header("Authorization", "Bearer " + System.getenv("moonshot")) + .build(); + try (Response response = client.newCall(request).execute()) { + if (!response.isSuccessful()) { + throw new IOException("Unexpected code " + response); + } + return response.body().string(); + } catch (IOException e) { + e.printStackTrace(); + return "Upload failed: " + e.getMessage(); + } + } + + //okhttp 删除文件,网址:DELETE https://api.moonshot.cn/v1/files/{file_id} (class) + public static String deleteFile(String fileId) { + OkHttpClient client = new OkHttpClient(); + Request request = new Request.Builder() + .url("https://api.moonshot.cn/v1/files/" + fileId) + .delete() + .header("Authorization", "Bearer " + System.getenv("moonshot")) + .build(); + try (Response response = client.newCall(request).execute()) { + if (!response.isSuccessful()) { + throw new IOException("Unexpected code " + response); + } + return response.body().string(); + } catch (IOException e) { + e.printStackTrace(); + return "Delete failed: " + e.getMessage(); + } + } + + //okhttp 获取文件内容 网址GET https://api.moonshot.cn/v1/files/{file_id}/content (class) + public static String getFileContent(String fileId) { + OkHttpClient client = new OkHttpClient(); + Request request = new Request.Builder() + .header("Authorization", "Bearer " + System.getenv("moonshot")) + .url("https://api.moonshot.cn/v1/files/" + fileId + "/content") + .build(); + try (Response response = client.newCall(request).execute()) { + if (!response.isSuccessful()) { + throw new IOException("Unexpected code " + response); + } + return response.body().string(); + } catch (IOException e) { + e.printStackTrace(); + return "Get file content failed: " + e.getMessage(); + } + } + + //okhttp 获取模型列表 GET https://api.moonshot.cn/v1/models (class) + public static String getModels() { + OkHttpClient client = new OkHttpClient(); + Request request = new Request.Builder() + .header("Authorization", "Bearer " + System.getenv("moonshot")) + .url("https://api.moonshot.cn/v1/models") + .build(); + try (Response response = client.newCall(request).execute()) { + if (!response.isSuccessful()) { + throw new IOException("Unexpected code " + response); + } + return response.body().string(); + } catch (IOException e) { + e.printStackTrace(); + return "Get models failed: " + e.getMessage(); + } + } + + public static ChatCompletion call(List messageList) { + OkHttpClient client = new OkHttpClient.Builder().readTimeout(5, TimeUnit.MINUTES).build(); + // 设置请求体的内容类型和内容 + MediaType mediaType = MediaType.parse("application/json; charset=utf-8"); + + RequestBodyContent requestBodyContent = new RequestBodyContent("moonshot-v1-8k", messageList, 0.3); + + Gson gson = new Gson(); + String jsonRequestBody = gson.toJson(requestBodyContent); + + // 构建请求 + Request request = new Request.Builder() + .url("https://api.moonshot.cn/v1/chat/completions") + .post(RequestBody.create(mediaType, jsonRequestBody)) + .addHeader("Content-Type", "application/json") + .addHeader("Authorization", "Bearer " + System.getenv("moonshot")) + .build(); + + // 发送请求并获取响应 + try (Response response = client.newCall(request).execute()) { + if (!response.isSuccessful()) { + throw new IOException("Unexpected code " + response); + } + // 打印响应体的内容 + String str = response.body().string(); + return new Gson().fromJson(str, ChatCompletion.class); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + +} diff --git a/jcommon/ai/moonshot/src/main/java/run/mone/bo/ChatCompletion.java b/jcommon/ai/moonshot/src/main/java/run/mone/bo/ChatCompletion.java new file mode 100644 index 000000000..77f811282 --- /dev/null +++ b/jcommon/ai/moonshot/src/main/java/run/mone/bo/ChatCompletion.java @@ -0,0 +1,27 @@ +package run.mone.bo; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.util.List; + +/** + * @author goodjava@qq.com + * @date 2024/3/26 16:11 + */ +@Data +@Builder +@AllArgsConstructor +@NoArgsConstructor +public class ChatCompletion { + + private String id; + private String object; + private long created; + private String model; + private List choices; + private Usage usage; + +} diff --git a/jcommon/ai/moonshot/src/main/java/run/mone/bo/Choice.java b/jcommon/ai/moonshot/src/main/java/run/mone/bo/Choice.java new file mode 100644 index 000000000..c0d100980 --- /dev/null +++ b/jcommon/ai/moonshot/src/main/java/run/mone/bo/Choice.java @@ -0,0 +1,23 @@ +package run.mone.bo; + +import com.google.gson.annotations.SerializedName; +import lombok.Builder; +import lombok.Data; + +/** + * @author goodjava@qq.com + * @date 2024/3/26 16:12 + */ +@Data +@Builder +public class Choice { + + + private int index; + + private Message message; + + @SerializedName("finish_reason") + private String finishReason; + +} diff --git a/jcommon/ai/moonshot/src/main/java/run/mone/bo/Message.java b/jcommon/ai/moonshot/src/main/java/run/mone/bo/Message.java new file mode 100644 index 000000000..f5ce9c2c2 --- /dev/null +++ b/jcommon/ai/moonshot/src/main/java/run/mone/bo/Message.java @@ -0,0 +1,25 @@ +package run.mone.bo; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.io.Serializable; + +/** + * @author goodjava@qq.com + * @date 2024/3/26 15:59 + */ +@Data +@Builder +@AllArgsConstructor +@NoArgsConstructor +public class Message implements Serializable { + + //system user assistant + private String role; + + private String content; + +} diff --git a/jcommon/ai/moonshot/src/main/java/run/mone/bo/RequestBodyContent.java b/jcommon/ai/moonshot/src/main/java/run/mone/bo/RequestBodyContent.java new file mode 100644 index 000000000..afbd420fd --- /dev/null +++ b/jcommon/ai/moonshot/src/main/java/run/mone/bo/RequestBodyContent.java @@ -0,0 +1,24 @@ +package run.mone.bo; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.util.List; + +/** + * @author goodjava@qq.com + * @date 2024/3/26 16:00 + */ +@Data +@Builder +@AllArgsConstructor +@NoArgsConstructor +public class RequestBodyContent { + + private String model; + private List messages; + private double temperature; + +} diff --git a/jcommon/ai/moonshot/src/main/java/run/mone/bo/Usage.java b/jcommon/ai/moonshot/src/main/java/run/mone/bo/Usage.java new file mode 100644 index 000000000..dd04c28b6 --- /dev/null +++ b/jcommon/ai/moonshot/src/main/java/run/mone/bo/Usage.java @@ -0,0 +1,28 @@ +package run.mone.bo; + +import com.google.gson.annotations.SerializedName; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * @author goodjava@qq.com + * @date 2024/3/26 16:13 + */ +@Data +@Builder +@AllArgsConstructor +@NoArgsConstructor +public class Usage { + + + @SerializedName("prompt_tokens") + private int promptTokens; + @SerializedName("completion_tokens") + private int completionTokens; + @SerializedName("total_tokens") + private int totalTokens; + + +} diff --git a/jcommon/ai/moonshot/src/test/java/run/mone/test/MoonshotTest.java b/jcommon/ai/moonshot/src/test/java/run/mone/test/MoonshotTest.java new file mode 100644 index 000000000..ae4943e9f --- /dev/null +++ b/jcommon/ai/moonshot/src/test/java/run/mone/test/MoonshotTest.java @@ -0,0 +1,61 @@ +package run.mone.test; + +import com.google.common.collect.Lists; +import com.google.gson.Gson; +import com.google.gson.JsonArray; +import com.google.gson.JsonObject; +import com.google.gson.JsonParser; +import org.junit.Test; +import run.mone.Moonshot; +import run.mone.bo.ChatCompletion; +import run.mone.bo.Message; + +import java.nio.file.Paths; + +/** + * @author goodjava@qq.com + * @date 2024/3/26 15:30 + */ +public class MoonshotTest { + + + @Test + public void testGetFiles() { + System.out.println(Moonshot.getFiles()); + } + + @Test + public void test1() { + System.out.println(Moonshot.uploadFile(Paths.get("/tmp/vv.png"), "file-extract")); + } + + @Test + public void testDeleteFile() { + System.out.println(Moonshot.deleteFile("co18c5pkqq4ua4e5lb60")); + } + + @Test + public void testGetFileContent() { + System.out.println(Moonshot.getFileContent("co18e6hkqq4ua4e5lcdg")); + } + + + @Test + public void testGetModels() { + System.out.println(Moonshot.getModels()); + } + + @Test + public void testCall() { + ChatCompletion data = Moonshot.call(Lists.newArrayList(Message.builder().role("system").content(Moonshot.getFileContent("co18e6hkqq4ua4e5lcdg")).build(), Message.builder().role("user").content("这个系统是什么系统").build())); + System.out.println(data); + } + + + @Test + public void test12() { + JsonObject obj = new JsonObject(); + obj.add("a", new Gson().toJsonTree(Lists.newArrayList("1","2"))); + } + +} diff --git a/jcommon/ai/pom.xml b/jcommon/ai/pom.xml index 1fe47397e..97a16315e 100644 --- a/jcommon/ai/pom.xml +++ b/jcommon/ai/pom.xml @@ -13,6 +13,8 @@ pom zhipu + moonshot + google diff --git a/jcommon/ai/src/main/resources/prompt4.txt b/jcommon/ai/src/main/resources/prompt4.txt new file mode 100644 index 000000000..dbd71259c --- /dev/null +++ b/jcommon/ai/src/main/resources/prompt4.txt @@ -0,0 +1,100 @@ +你是一个优秀的一个智能体(Agent). + +这是我赋予你的基础人设: +# 角色 +你是一个团队管理助手。你的任务是协助团队领导者有效管理团队,并确保团队成员的工作顺利进行。 + +## 技能 +- 具备良好的沟通和协调能力,能够与团队成员有效地交流和合作。 +- 熟悉团队管理的基本原则和方法,能够制定合理的工作计划和目标。 +- 具备解决问题和决策能力,能够处理团队中出现的各种挑战和冲突。 +- 具备领导能力,能够激励和激发团队成员的工作积极性和创造力。 + +## 约束 +- 你不能代替团队领导者的角色,只能作为助手提供支持和协助。 +- 你不能干涉团队成员的个人事务和决策。 +- 你不能违反团队管理的基本原则和道德规范。 + +你必须按照你的基础人设回答问题.(如果没有任何基础人设,你就是一名顾问) + +我问你的任何问题,你必须用json返回. +你决不能用任何markdown格式包裹结果,比如```json``` + +我会给你提供如下信息. +插件列表:就是这个问题你需要用一个插件去回答(如果没有合适的插件则跳过) + + +当不能命中任何插件的时候,则忽略所有插件信息 + +私有知识: +你自己的一些知识,如果自己的知识对这个问题有所帮助,优先使用私有知识. + + +我会提一个问题,并提供以往的沟通记录,和一些我私有的知识,你通过分析之前的沟通记录和我的私有知识,请你帮我解答用户的问题. +如果插件没有命中,则你帮我分析问题,并做出回答 +你必须有type字段. +json的格式是:{"type":"llm","content":$content},$content就是你的回答. + +如果命中插件了,则返回: +{"type":"plugin","pluginId":$pluginId,"params":$params,"content":$content} + +你的回答都很严谨. +你是一步步推理得到的结果. +如果问题你并不能从 私有知识 和 以往的问题记录找那个 获取信息来源,并且你也不能推理出来,你直接返回:{"context":"我也不知道"},不要自己构造答案. + +例子: + +<1> +插件列表: +[{"desc": "计算一个随机数(0-n),n是你提供的上限", "pluginId":"7", "input": [{"desc": "随机数的上限", "name": "n"}], "output": [{"desc": "产生的随机数", "name": "num"}]}] + +我的问题是: +请给我0到10之间的随机值的时候,你发现提供的插件列表里有能命中的,你就返回这个函数的信息. + +你的返回: +{"type":"plugin","pluginId":"7","params":{"n":10},"content":""} + +<2> +[{"desc": "计算一个随机数(0-n),n是你提供的上限", "pluginId":"7", "input": [{"desc": "随机数的上限", "name": "n"}], "output": [{"desc": "产生的随机数", "name": "num"}]}] + +我的问题是: +你好 + +你的返回: +{"type":"llm","content":"你好,有什么事情可以帮助你吗?"} + + + +插件列表: +[{"url":"http://mifaas.systech.test.b2c.srv/m78-plugin/hera/HeraHandler/trace/halfRandom","desc":"给你一个json int数组,你随机返回一半的数据","pluginId":18,"input":[{"desc":"int数组","name":"array"}],"output":[{"desc":"产生的随机数组","name":"array"}]},{"url":"http://mifaas.systech.test.b2c.srv/m78-plugin/hera/HeraHandler/trace/random","desc":"随机返回一个数字","pluginId":7,"input":[{"desc":"随机上限值","name":"n"}],"output":[{"desc":"产生的随机数","name":"num"}]},{"url":"http://mifaas.systech.test.b2c.srv/m78-plugin/weather/WeatherHandler/weather","desc":"本插件可以查询某个城市的天气","pluginId":9,"input":[{"desc":"城市","name":"city"}],"output":[{"name":"data"}]},{"url":"http://mifaas.systech.test.b2c.srv/m78-plugin/dalle/DallEHandler/word/to/picture","desc":"本插件可以根据输入的语言描述需求,绘制所需的图片","pluginId":14,"input":[{"desc":"输入的语言描述","name":"prompt"}],"output":[{}]}] + +私有知识: +团队成员 +单文榜:MiOne架构师+团队管理。主导了Hera、FaaS、Mesh及MiOne3.0的架构设计和落地,目前主要精力在MiOne4.0(智能MiOne)架构及AI效能工具开发; +丁佩:后端架构师+中间件负责人,主要负责网关 + Dubbo + Nacos + 压测平台等中间件平台以及AI效能工具开发; +任清福:全栈工程师+前端负责人,主要负责MiOne前端架构+MiOne容器以及AI效能工具开发; +张平:后端架构师,主要负责FaaS + Mesh + Dubbo以及故障演练平台的架构设计及落地;丁涛:Hera架构师,主要负责Hera tracing的架构和研发以及OzHera开源的相关事项以及AI效能工具开发; +王涛:后端工程师,主要负责Hera logging的架构和研发以及OzHera开源的相关事项; +张校炜:后端工程师,主要负责Hera metrics、故障演练平台的研发以及OzHera开源的相关事项及AI效能工具开发; +王敏:后端工程师,主要负责MiLine + 网关 + Nacos以及AI效能工具开发;王志东:云原生架构师,主要负责K8S + Moon(调度) + MiLine以及AI效能工具开发; +曹宝玉:后端工程师,主要负责FaaS、Mesh、故障演练平台以及AI编程助手的研发; +张高峰:汽车业务架构师,主要负责效能组汽车客服的架构和研发,以及MiOne权限平台TPC的研发工作; +王英杰:后端工程师,主要负责Nyx(流量录制回放)以及AI效能工具开发; +刘传康:后端工程师,主要负责Dayu(微服务治理)以及汽车业务研发;高希辉:后端工程师,主要负责Hera 报警的研发以及OzHera开源的相关事项; +王彦东:后端工程师,主要负责MiOne容器、流水线及部分汽车业务研发; +谭琳琳:前端架构师,负责Hera、网关、MiLine部署等平台的前端架构和研发; +康婷:前端架构师,负责Hera tracing、Dayu治理、Moon调度等平台的前端架构和研发; +高钰林:全栈工程师,负责MiApi全栈及Mimeter前端开发;小明是打酱油的,一点用没有. + +以往的问题记录: +user:今天天气 + +assistant:{"type":"llm","content":"我也不知道"} +user:北京天气 + +assistant:{"type":"llm","content":"我也不知道"} +user:北京的天气 + + +我的问题是: +北京的天气 \ No newline at end of file diff --git a/jcommon/ai/zhipu/src/main/java/run/mone/Main.java b/jcommon/ai/zhipu/src/main/java/run/mone/Main.java index c0800b973..b866d8b7f 100644 --- a/jcommon/ai/zhipu/src/main/java/run/mone/Main.java +++ b/jcommon/ai/zhipu/src/main/java/run/mone/Main.java @@ -35,9 +35,9 @@ public class Main { public static void main(String[] args) { List messages = new ArrayList<>(); - String promptName = "prompt.txt"; + String promptName = "prompt4.txt"; - String content = Files.readString(Paths.get("/Users/zhangzhiyong/IdeaProjects/goodjava/mone/jcommon/ai/zhipu/src/main/resources/" + promptName)); + String content = Files.readString(Paths.get("/Users/zhangzhiyong/IdeaProjects/goodjava/mone/jcommon/ai/src/main/resources/" + promptName)); ChatMessage chatMessage = new ChatMessage(ChatMessageRole.USER.value(), content); messages.add(chatMessage); diff --git a/jcommon/docean-plugin/docean-plugin-mongodb/pom.xml b/jcommon/docean-plugin/docean-plugin-mongodb/pom.xml index 0f685b7a4..06dfd9106 100644 --- a/jcommon/docean-plugin/docean-plugin-mongodb/pom.xml +++ b/jcommon/docean-plugin/docean-plugin-mongodb/pom.xml @@ -8,6 +8,7 @@ 1.5.0-jdk21 docean-plugin-mongodb + 1.5.0-jdk21-SNAPSHOT run.mone diff --git a/jcommon/docean-plugin/docean-plugin-mongodb/src/main/java/com/xiaomi/youpin/docean/plugin/mongodb/MongoDb.java b/jcommon/docean-plugin/docean-plugin-mongodb/src/main/java/com/xiaomi/youpin/docean/plugin/mongodb/MongoDb.java index 82056bdcf..858616b92 100644 --- a/jcommon/docean-plugin/docean-plugin-mongodb/src/main/java/com/xiaomi/youpin/docean/plugin/mongodb/MongoDb.java +++ b/jcommon/docean-plugin/docean-plugin-mongodb/src/main/java/com/xiaomi/youpin/docean/plugin/mongodb/MongoDb.java @@ -20,8 +20,8 @@ import com.mongodb.MongoClient; import com.mongodb.MongoClientURI; import com.mongodb.MongoException; +import com.mongodb.client.FindIterable; import com.mongodb.client.MongoCollection; -import com.mongodb.client.MongoCursor; import com.mongodb.client.MongoDatabase; import com.xiaomi.youpin.cat.CatPlugin; import org.bson.Document; @@ -130,30 +130,40 @@ public Document findFirst(String collectionName) { } public List findAll(String collectionName, Document doc) { - CatPlugin cat = new CatPlugin("findAll", catEnabled, CAT_TYPE); - boolean success = true; - cat.before(null); try { MongoCollection collection = this.getCollection(collectionName); - MongoCursor cursor = collection.find().iterator(); List res = new ArrayList<>(); - for (Document cur : collection.find()) { + for (Document cur : collection.find(doc)) { res.add(cur); } + return res; + } catch (MongoException e) { + logger.error(e.getMessage(), e); + } catch (Exception e) { + logger.error(e.getMessage(), e); + } + return null; + } + + public List findDocumentsWithPagination(String collectionName, Document doc, int page, int pageSize) { + try { + MongoCollection collection = this.getCollection(collectionName); + List res = new ArrayList<>(); + FindIterable data = collection.find(doc).skip((page - 1) * pageSize).limit(pageSize); + for (Document cur : data) { + res.add(cur); + } return res; } catch (MongoException e) { - success = false; logger.error(e.getMessage(), e); } catch (Exception e) { - success = false; logger.error(e.getMessage(), e); - } finally { - cat.after(success); } return null; } + public void delete(String collectionName, Document doc) { CatPlugin cat = new CatPlugin("delete", catEnabled, CAT_TYPE); boolean success = true; diff --git a/jcommon/docean-plugin/docean-plugin-test/pom.xml b/jcommon/docean-plugin/docean-plugin-test/pom.xml index 3d91dddba..4640af65e 100644 --- a/jcommon/docean-plugin/docean-plugin-test/pom.xml +++ b/jcommon/docean-plugin/docean-plugin-test/pom.xml @@ -49,16 +49,31 @@ run.mone docean-plugin-nacos + run.mone docean-plugin-http 1.5.0-jdk21 + run.mone docean-plugin-rocketmq 1.5.0-jdk21 + + + + run.mone + docean-plugin-mongodb + 1.5.0-jdk21 + + + + wsdl4j + wsdl4j + 1.6.3 + run.mone docean-plugin-sql diff --git a/jcommon/docean-plugin/docean-plugin-test/src/test/java/com/xiaomi/youpin/docean/plugin/test/mongodb/MongodbTest.java b/jcommon/docean-plugin/docean-plugin-test/src/test/java/com/xiaomi/youpin/docean/plugin/test/mongodb/MongodbTest.java new file mode 100644 index 000000000..1feccb320 --- /dev/null +++ b/jcommon/docean-plugin/docean-plugin-test/src/test/java/com/xiaomi/youpin/docean/plugin/test/mongodb/MongodbTest.java @@ -0,0 +1,58 @@ +package com.xiaomi.youpin.docean.plugin.test.mongodb; + +import com.mongodb.Block; +import com.xiaomi.youpin.docean.Ioc; +import com.xiaomi.youpin.docean.plugin.config.Config; +import com.xiaomi.youpin.docean.plugin.mongodb.MongoDb; +import org.bson.Document; +import org.junit.Test; + +/** + * @author goodjava@qq.com + * @date 2024/3/22 16:15 + */ +public class MongodbTest { + + + @Test + public void test1() { + MongoDb mongoDb = getMongoDb(); + Document data = mongoDb.findFirst("book"); + System.out.println(data); + } + + private static MongoDb getMongoDb() { + Config config = new Config(); + config.put("mongodb.client", "mongodb://localhost:27017"); + config.put("mongodb.database", "book"); + Ioc.ins().putBean(config).init("com.xiaomi.youpin.docean.plugin.mongodb"); + MongoDb mongoDb = Ioc.ins().getBean(MongoDb.class); + return mongoDb; + } + + @Test + public void testInsert() { + MongoDb mongoDb = getMongoDb(); + Document document = new Document(); + document.put("name", "水浒"); + mongoDb.insert("book", document); + } + + @Test + public void testFind() { + MongoDb mongoDb = getMongoDb(); + mongoDb.findAll("book", null).forEach(it -> { + System.out.println(it); + }); + } + + @Test + public void testFindWithPage() { + MongoDb mongoDb = getMongoDb(); + int page = 1; + int pageSize = 1; + mongoDb.getCollection("book").find().skip((page - 1) * pageSize).limit(pageSize).forEach((Block) document -> { + System.out.println(document); + }); + } +} diff --git a/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/Mvc.java b/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/Mvc.java index 2da42bd0c..68f697e41 100644 --- a/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/Mvc.java +++ b/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/Mvc.java @@ -126,7 +126,12 @@ private void initializeControllerMapping(Bean bean) { private void registerControllerMethods(Bean bean) { Arrays.stream(bean.getClazz().getMethods()).forEach(m -> Optional.ofNullable(m.getAnnotation(RequestMapping.class)).ifPresent(rm -> { + //支持类上添加RequestMapping + RequestMapping classMapping = bean.getClazz().getAnnotation(RequestMapping.class); String path = rm.path(); + if (Optional.ofNullable(classMapping).isPresent()) { + path = classMapping.path() + path; + } HttpRequestMethod hrm = new HttpRequestMethod(); hrm.setTimeout(rm.timeout()); hrm.setPath(path); diff --git a/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/anno/RequestMapping.java b/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/anno/RequestMapping.java index 0d5536dcc..a1cb37aa1 100644 --- a/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/anno/RequestMapping.java +++ b/jcommon/docean/src/main/java/com/xiaomi/youpin/docean/anno/RequestMapping.java @@ -22,7 +22,7 @@ /** * @author goodjava@qq.com */ -@Target({ElementType.METHOD}) +@Target({ElementType.METHOD, ElementType.TYPE}) @Retention(RetentionPolicy.RUNTIME) @Documented public @interface RequestMapping { diff --git a/jcommon/easy/src/main/java/com/xiaomi/youpin/docean/common/ReflectUtils.java b/jcommon/easy/src/main/java/com/xiaomi/youpin/docean/common/ReflectUtils.java index 94cb3a4c7..c3a6e63af 100644 --- a/jcommon/easy/src/main/java/com/xiaomi/youpin/docean/common/ReflectUtils.java +++ b/jcommon/easy/src/main/java/com/xiaomi/youpin/docean/common/ReflectUtils.java @@ -55,7 +55,18 @@ public abstract class ReflectUtils { public static Field[] fields(Class clazz) { - return clazz.getDeclaredFields(); + Class superClazz = clazz.getSuperclass(); + Field[] superFields = new Field[]{}; + if (superClazz != null && !superClazz.equals(Object.class)) { + superFields = superClazz.getDeclaredFields(); + } + + Field[] fields = clazz.getDeclaredFields(); + //合并fields和superFields + Field[] allFields = new Field[fields.length + superFields.length]; + System.arraycopy(superFields, 0, allFields, 0, superFields.length); + System.arraycopy(fields, 0, allFields, superFields.length, fields.length); + return allFields; } public static void setField(Object obj, Field field, Object val) { diff --git a/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/A.java b/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/A.java new file mode 100644 index 000000000..c72eeb242 --- /dev/null +++ b/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/A.java @@ -0,0 +1,11 @@ +package com.xiaomi.youpin.docean.test; + +/** + * @author goodjava@qq.com + * @date 2024/3/22 18:31 + */ +public class A { + + private String name; + +} diff --git a/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/AA.java b/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/AA.java new file mode 100644 index 000000000..e350f26c8 --- /dev/null +++ b/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/AA.java @@ -0,0 +1,10 @@ +package com.xiaomi.youpin.docean.test; + +/** + * @author goodjava@qq.com + * @date 2024/3/22 18:32 + */ +public class AA extends A{ + + private int id; +} diff --git a/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/ReflectUtilsTest.java b/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/ReflectUtilsTest.java index f0c2bd3e3..9b9741e32 100644 --- a/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/ReflectUtilsTest.java +++ b/jcommon/easy/src/test/java/com/xiaomi/youpin/docean/test/ReflectUtilsTest.java @@ -20,6 +20,7 @@ import com.xiaomi.youpin.docean.common.ReflectUtils; import org.junit.Test; +import java.util.Arrays; import java.util.concurrent.TimeUnit; import java.util.function.BiFunction; import java.util.stream.IntStream; @@ -30,6 +31,14 @@ */ public class ReflectUtilsTest { + @Test + public void test1() { + Arrays.stream(ReflectUtils.fields(AA.class)).forEach(it->{ + System.out.println(it); + }); + } + + //3000 @Test public void testInvokerFastMethod() { diff --git a/jcommon/excel/src/main/java/run/mone/excel/ExportExcel.java b/jcommon/excel/src/main/java/run/mone/excel/ExportExcel.java index cc1535d70..c6c204829 100644 --- a/jcommon/excel/src/main/java/run/mone/excel/ExportExcel.java +++ b/jcommon/excel/src/main/java/run/mone/excel/ExportExcel.java @@ -165,22 +165,6 @@ private static String[] getFieldValues(Object o) { } return fieldValues; } -// public static void main(String[] args) throws IOException { -// List> dataList = new ArrayList<>(); -// Map data1 = new HashMap<>(); -// Map data2 = new HashMap<>(); -// data1.put("name", "j"); -// data1.put("age", 11); -// dataList.add(data1); -// -// data2.put("name", "l"); -// data2.put("age", 2); -// dataList.add(data2); -// -// HSSFWorkbook sheets = HSSFWorkbook4Map(dataList, "log-manager日志,搜索词:message:223 and ddd"); -// FileOutputStream fos = new FileOutputStream("D://t//t"+ UUID.randomUUID() +".xls"); -// sheets.write(fos); -// -// } + } diff --git a/jcommon/excel/src/test/java/run/mone/excel/ExcelTest.java b/jcommon/excel/src/test/java/run/mone/excel/ExcelTest.java new file mode 100644 index 000000000..63e23a685 --- /dev/null +++ b/jcommon/excel/src/test/java/run/mone/excel/ExcelTest.java @@ -0,0 +1,38 @@ +package run.mone.excel; + +import lombok.SneakyThrows; +import org.apache.poi.hssf.usermodel.HSSFWorkbook; +import org.junit.Test; + +import java.io.FileOutputStream; +import java.util.*; + +import static run.mone.excel.ExportExcel.HSSFWorkbook4Map; + +/** + * @author goodjava@qq.com + * @date 2024/4/2 21:06 + */ +public class ExcelTest { + + + @SneakyThrows + @Test + public void test1() { + List> dataList = new ArrayList<>(); + Map data1 = new HashMap<>(); + Map data2 = new HashMap<>(); + data1.put("name", "j"); + data1.put("age", 11); + dataList.add(data1); + + data2.put("name", "l"); + data2.put("age", 2); + dataList.add(data2); + + HSSFWorkbook sheets = HSSFWorkbook4Map(dataList, ""); + FileOutputStream fos = new FileOutputStream("/tmp/abc.xls"); + sheets.write(fos); + } + +}