Koog:JetBrains 推出的 JVM AI 框架,为 Java 开发者开启 AI 智能体新时代
Overview
Koog 是一个基于 Kotlin 的框架,专门用于构建和运行完全用 Kotlin 编写的 AI 智能体。它让您能够创建可以与工具交互、处理复杂工作流并与用户通信的智能体。
该框架支持以下类型的智能体:
- 单次运行智能体:具有最小配置,处理单个输入并提供响应。此类智能体在单个工具调用周期内运行以完成任务并提供响应。
- 复杂工作流智能体:具有高级功能,支持自定义策略和配置。
核心特性
Koog 的核心特性包括:
- 纯 Kotlin 实现:完全用自然和惯用的 Kotlin 构建 AI 智能体
- MCP 集成:连接到模型控制协议以增强模型管理
- 嵌入功能:使用向量嵌入进行语义搜索和知识检索
- 自定义工具创建:通过访问外部系统和 API 的工具扩展您的智能体
- 即用组件:使用预构建的解决方案加速常见 AI 工程挑战的开发
- 智能历史压缩:使用各种预构建策略优化 token 使用,同时保持对话上下文
- 强大的流式 API:通过流式支持和并行工具调用实时处理响应
- 持久化智能体记忆:支持跨会话甚至不同智能体的知识保留
- 全面追踪:通过详细和可配置的追踪调试和监控智能体执行
- 灵活的图工作流:使用直观的基于图的工作流设计复杂的智能体行为
- 模块化功能系统:通过可组合架构自定义智能体功能
- 可扩展架构:处理从简单聊天机器人到企业应用的工作负载
- 多平台支持:在 JVM、JS、WasmJS 目标上运行智能体,支持 Kotlin 多平台
可用的 LLM 提供商和平台
您可以使用以下 LLM 提供商和平台的 LLM 来为您的智能体功能提供支持:
- Google
- OpenAI
- Anthropic
- OpenRouter
- Ollama
在人工智能技术飞速发展的今天,JetBrains 作为业界领先的开发工具提供商,正式推出了 AI 开源框架 Koog。这个框架专门为构建和运行健壮、可扩展且可投入生产的 AI 智能体而设计,为 Java 开发者提供了一个强大的 AI 开发平台。
🚀 Koog 框架核心特性
多平台支持
Koog 支持多种平台开发,包括:
- 后端服务:构建企业级 AI 服务
- Android/iOS:移动端 AI 应用开发
- JVM 环境:与现有 Java 生态系统无缝集成
- 浏览器环境:前端 AI 功能实现
响应式架构设计
- 基于 Kotlin 协程实现异步处理流水线
- 提供高性能的任务执行和资源管理
- 支持大规模并发处理
核心组件
- 代理运行时:管理 AI 智能体的生命周期
- 工具总线:提供统一的工具调用接口
- 记忆引擎:智能化的上下文管理
- 追踪系统:完整的可观测性支持
🔧 技术亮点
Model Control Protocol (MCP)
Koog 支持动态模型加载机制,允许:
- 在不同 LLM 提供商之间进行热切换
- 根据需求动态调整模型配置
- 提高模型管理的灵活性
智能历史压缩算法
- 采用层次化注意力机制优化上下文处理
- 相比传统方法减少 42% 的 token 消耗
- 显著提高模型响应效率
💼 典型应用场景
智能客服系统
电商平台可以利用 Koog 构建智能客服代理:
- 订单查询和处理
- 退货流程自动化
- 实时产品推荐
- 多轮对话管理
金融合规审核
银行和金融机构可以构建合规代理:
- 文档语义分析
- 风险模式识别
- 合规性检查
- 异常交易监控
企业级 AI 应用
- 智能文档处理
- 自动化工作流
- 决策支持系统
- 知识图谱构建
🛠️ Java 开发者集成优势
无缝互操作性
- Kotlin 与 Java 的100% 互操作性
- 可以直接在现有 Java 项目中使用
- 渐进式迁移策略
生态系统兼容
- 与 Spring Boot 完美集成
- 支持现有的 Java 企业级框架
- 兼容 Maven 和 Gradle 构建系统
开发体验优化
- 利用 JetBrains IDE 的强大支持
- 丰富的调试和性能分析工具
- 完善的文档和社区支持
📈 性能优势
高效处理
可扩展性
🎯 开始使用 Koog
环境要求
- Kotlin 1.9.0+
- Java 8+
- 支持 Maven 或 Gradle
快速开始
1 2 3 4 5 6 7 8
| val agent = Agent.Builder() .withModel("gpt-4") .withTools(listOf(webSearchTool, calculatorTool)) .build()
val result = agent.execute("帮我查询今天的天气")
|
📚 官方案例详解
案例一:智能客服系统
官方提供的智能客服案例展示了如何构建一个完整的客服代理:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| val customerServiceAgent = Agent.Builder() .withModel("gpt-4") .withTools(listOf( orderQueryTool, refundProcessTool, productRecommendationTool, knowledgeBaseTool )) .withMemory(ConversationMemory.Builder() .maxHistoryLength(10) .enableContextCompression(true) .build()) .withPersonality("友好、专业、耐心") .build()
suspend fun handleCustomerInquiry(query: String): String { return customerServiceAgent.execute(query) }
|
功能特性:
- 订单状态查询
- 退货流程处理
- 产品智能推荐
- 多轮对话记忆
- 情感分析处理
案例二:金融合规审核系统
银行级别的合规审核代理实现:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
| val complianceAgent = Agent.Builder() .withModel("gpt-4") .withTools(listOf( documentAnalysisTool, riskAssessmentTool, regulationCheckTool, auditLogTool )) .withMemory(ComplianceMemory.Builder() .enableAuditTrail(true) .retentionPeriod(Duration.ofDays(365)) .build()) .withSecurityLevel(SecurityLevel.HIGH) .build()
suspend fun checkDocumentCompliance(document: Document): ComplianceResult { val analysis = complianceAgent.execute( "请分析以下文档的合规性:${document.content}" ) return ComplianceResult.fromAnalysis(analysis) }
|
核心功能:
- 文档语义分析
- 风险模式识别
- 法规条款匹配
- 审计日志记录
- 异常行为检测
案例三:企业知识管理助手
基于 Koog 构建的企业级知识管理解决方案:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
| val knowledgeAgent = Agent.Builder() .withModel("gpt-4") .withTools(listOf( documentSearchTool, knowledgeGraphTool, translationTool, summarizationTool )) .withMemory(KnowledgeMemory.Builder() .enableSemanticSearch(true) .enableVectorIndexing(true) .build()) .build()
suspend fun searchKnowledge(query: String): KnowledgeResponse { return knowledgeAgent.execute( "基于企业知识库回答:$query" ) }
|
应用场景:
- 技术文档检索
- 内部知识问答
- 多语言文档翻译
- 会议纪要生成
- 最佳实践推荐
案例四:Spring Boot 完整集成方案
基于 Koog 官方 Spring Boot 文档,展示完整的集成方案:
1. 依赖配置
1 2 3 4 5 6
| dependencies { implementation("ai.koog:koog-spring-boot-starter:$koogVersion") implementation("org.springframework.boot:spring-boot-starter-web") implementation("org.springframework.boot:spring-boot-starter-validation") }
|
2. 配置文件设置
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| ai: koog: openai: api-key: ${OPENAI_API_KEY} base-url: https://api.openai.com anthropic: api-key: ${ANTHROPIC_API_KEY} base-url: https://api.anthropic.com google: api-key: ${GOOGLE_API_KEY} base-url: https://generativelanguage.googleapis.com deepseek: api-key: ${DEEPSEEK_API_KEY} base-url: https://api.deepseek.com ollama: base-url: http://localhost:11434
|
3. 基础服务实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
| @Service class AIService( private val openAIExecutor: SingleLLMPromptExecutor?, private val anthropicExecutor: SingleLLMPromptExecutor?, private val deepSeekExecutor: SingleLLMPromptExecutor? ) {
suspend fun generateResponse(input: String): String { val prompt = prompt { system("你是一个有用的AI助手") user(input) }
return when { openAIExecutor != null -> { val result = openAIExecutor.execute(prompt) result.text } anthropicExecutor != null -> { val result = anthropicExecutor.execute(prompt) result.text } deepSeekExecutor != null -> { val result = deepSeekExecutor.execute(prompt) result.text } else -> throw IllegalStateException("未配置任何LLM提供商") } } }
|
4. REST 控制器实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66
| @RestController @RequestMapping("/api/ai") class AIController( private val aiService: AIService, private val anthropicExecutor: SingleLLMPromptExecutor? ) { @PostMapping("/chat") suspend fun chat(@RequestBody @Valid request: ChatRequest): ResponseEntity<ChatResponse> { return try { val response = aiService.generateResponse(request.message) ResponseEntity.ok(ChatResponse(response)) } catch (e: Exception) { ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR) .body(ChatResponse("处理请求时发生错误: ${e.message}")) } } @PostMapping("/analyze") suspend fun analyzeDocument(@RequestBody @Valid document: Document): ResponseEntity<AnalysisResult> { return if (anthropicExecutor != null) { try { val prompt = prompt { system("你是一个专业的文档分析助手") user("请分析以下文档:${document.content}") } val result = anthropicExecutor.execute(prompt) val analysis = AnalysisResult( summary = extractSummary(result.text), keywords = extractKeywords(result.text), sentiment = analyzeSentiment(result.text) ) ResponseEntity.ok(analysis) } catch (e: Exception) { ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR) .body(AnalysisResult("分析失败", emptyList(), "未知")) } } else { ResponseEntity.status(HttpStatus.SERVICE_UNAVAILABLE) .body(AnalysisResult("AI服务未配置", emptyList(), "未知")) } } }
data class ChatRequest( @field:NotBlank(message = "消息不能为空") val message: String )
data class ChatResponse( val response: String )
data class Document( @field:NotBlank(message = "文档内容不能为空") val content: String, val title: String? = null )
data class AnalysisResult( val summary: String, val keywords: List<String>, val sentiment: String )
|
5. 多提供商容错处理
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
| @Service class RobustAIService( private val openAIExecutor: SingleLLMPromptExecutor?, private val anthropicExecutor: SingleLLMPromptExecutor?, private val openRouterExecutor: SingleLLMPromptExecutor? ) {
suspend fun generateWithFallback(input: String): String { val prompt = prompt { system("你是一个有用的AI助手") user(input) }
val executors = listOfNotNull(openAIExecutor, anthropicExecutor, openRouterExecutor)
for (executor in executors) { try { val result = executor.execute(prompt) return result.text } catch (e: Exception) { logger.warn("执行器失败,尝试下一个: ${e.message}") continue } }
throw IllegalStateException("所有AI提供商都失败了") }
companion object { private val logger = LoggerFactory.getLogger(RobustAIService::class.java) } }
|
6. 配置属性注入
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| @Service class ConfigurableAIService( private val openAIExecutor: SingleLLMPromptExecutor?, @Value("\${ai.koog.openai.api-key:}") private val openAIKey: String, @Value("\${ai.koog.anthropic.api-key:}") private val anthropicKey: String ) {
fun isOpenAIConfigured(): Boolean = openAIKey.isNotBlank() && openAIExecutor != null fun isAnthropicConfigured(): Boolean = anthropicKey.isNotBlank()
suspend fun processIfConfigured(input: String): String? { return when { isOpenAIConfigured() -> { val result = openAIExecutor!!.execute(prompt { user(input) }) result.text } else -> null } } }
|
7. 高级配置示例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55
| @Configuration @EnableConfigurationProperties(KoogProperties::class) class KoogConfiguration {
@Bean @ConditionalOnProperty("ai.koog.openai.api-key") fun openAIConfiguration(properties: KoogProperties): OpenAIConfiguration { return OpenAIConfiguration( apiKey = properties.openai.apiKey, baseUrl = properties.openai.baseUrl ?: "https://api.openai.com" ) }
@Bean @ConditionalOnProperty("ai.koog.anthropic.api-key") fun anthropicConfiguration(properties: KoogProperties): AnthropicConfiguration { return AnthropicConfiguration( apiKey = properties.anthropic.apiKey, baseUrl = properties.anthropic.baseUrl ?: "https://api.anthropic.com" ) } }
@ConfigurationProperties(prefix = "ai.koog") data class KoogProperties( val openai: OpenAIProperties = OpenAIProperties(), val anthropic: AnthropicProperties = AnthropicProperties(), val google: GoogleProperties = GoogleProperties(), val deepseek: DeepSeekProperties = DeepSeekProperties(), val ollama: OllamaProperties = OllamaProperties() )
data class OpenAIProperties( var apiKey: String = "", var baseUrl: String = "https://api.openai.com" )
data class AnthropicProperties( var apiKey: String = "", var baseUrl: String = "https://api.anthropic.com" )
data class GoogleProperties( var apiKey: String = "", var baseUrl: String = "https://generativelanguage.googleapis.com" )
data class DeepSeekProperties( var apiKey: String = "", var baseUrl: String = "https://api.deepseek.com" )
data class OllamaProperties( var baseUrl: String = "http://localhost:11434" )
|
8. 测试配置
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
| @SpringBootTest @TestPropertySource(properties = [ "ai.koog.openai.api-key=test-key", "ai.koog.openai.base-url=https://api.openai.com" ]) class AIServiceTest {
@Autowired private lateinit var aiService: AIService
@MockBean private lateinit var openAIExecutor: SingleLLMPromptExecutor
@Test fun `should generate response successfully`() = runTest { val input = "你好" val expectedResponse = "你好!我是AI助手" val mockResult = PromptResult(text = expectedResponse) whenever(openAIExecutor.execute(any())).thenReturn(mockResult)
val result = aiService.generateResponse(input)
assertEquals(expectedResponse, result) } }
|
9. 环境变量配置
1 2 3 4 5
| OPENAI_API_KEY=your_openai_api_key_here ANTHROPIC_API_KEY=your_anthropic_api_key_here GOOGLE_API_KEY=your_google_api_key_here DEEPSEEK_API_KEY=your_deepseek_api_key_here
|
核心特性:
- 自动配置多个 LLM 提供商
- 支持环境变量配置
- 多提供商容错处理
- 完整的 REST API 支持
- 配置属性验证
- 单元测试支持
10. Spring Boot 最佳实践
Bean 限定符使用:
1 2 3 4 5 6 7
| @Service class MultiProviderService( @Qualifier("openAIExecutor") private val openAIExecutor: SingleLLMPromptExecutor?, @Qualifier("anthropicExecutor") private val anthropicExecutor: SingleLLMPromptExecutor? ) { }
|
条件配置:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| @Configuration class ConditionalKoogConfig {
@Bean @ConditionalOnProperty("ai.koog.openai.api-key") fun openAIService(): AIService { return AIService(provider = "OpenAI") }
@Bean @ConditionalOnProperty("ai.koog.anthropic.api-key") fun anthropicService(): AIService { return AIService(provider = "Anthropic") } }
|
错误处理策略:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| @Service class ErrorHandlingAIService( private val executors: List<SingleLLMPromptExecutor> ) { suspend fun safeExecute(input: String): Result<String> { return try { val prompt = prompt { user(input) } val result = executors.first().execute(prompt) Result.success(result.text) } catch (e: Exception) { logger.error("AI执行失败", e) Result.failure(e) } } }
|
11. 常见问题解决
问题1:Bean 未找到
1
| No qualifying bean of type 'SingleLLMPromptExecutor' available
|
解决方案: 确保在配置文件中设置了至少一个提供商的 API 密钥。
问题2:多个 Bean 冲突
1
| Multiple qualifying beans of type 'SingleLLMPromptExecutor' available
|
解决方案: 使用 @Qualifier 注解指定具体的 Bean。
问题3:API 密钥未加载
1
| API key is required but not provided
|
解决方案: 检查环境变量是否正确设置。
问题4:配置属性不生效
1 2 3 4 5 6
| @ConfigurationProperties(prefix = "ai.koog") @Validated data class KoogProperties( @field:Valid val openai: OpenAIProperties = OpenAIProperties() )
|
12. 生产环境配置
安全配置:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| ai: koog: openai: api-key: ${OPENAI_API_KEY} base-url: ${OPENAI_BASE_URL:https://api.openai.com} anthropic: api-key: ${ANTHROPIC_API_KEY} base-url: ${ANTHROPIC_BASE_URL:https://api.anthropic.com}
logging: level: ai.koog: DEBUG org.springframework.web: INFO
|
监控配置:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| @Component class KoogMetrics( private val meterRegistry: MeterRegistry ) { private val executionCounter = Counter.builder("koog.executions") .description("AI execution count") .register(meterRegistry) private val executionTimer = Timer.builder("koog.execution.time") .description("AI execution time") .register(meterRegistry) fun recordExecution(duration: Duration) { executionCounter.increment() executionTimer.record(duration) } }
|
案例五:多平台移动应用
使用 Koog 构建跨平台移动 AI 应用:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
| expect class PlatformAI { suspend fun processImage(image: ByteArray): String suspend fun processText(text: String): String }
actual class PlatformAI { actual suspend fun processImage(image: ByteArray): String { return koogAgent.execute("分析这张图片:${image.toBase64()}") } actual suspend fun processText(text: String): String { return koogAgent.execute(text) } }
actual class PlatformAI { actual suspend fun processImage(image: ByteArray): String { return koogAgent.execute("分析这张图片:${image.toBase64()}") } actual suspend fun processText(text: String): String { return koogAgent.execute(text) } }
|
🔧 高级配置示例
自定义工具开发
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
| class WeatherTool : Tool { override val name = "weather_query" override val description = "查询指定城市的天气信息" override suspend fun execute(parameters: Map<String, Any>): String { val city = parameters["city"] as String return weatherApi.getCurrentWeather(city) } }
val agent = Agent.Builder() .withModel("gpt-4") .withTools(listOf( WeatherTool(), CalculatorTool(), WebSearchTool() )) .build()
|
记忆引擎配置
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| val memory = ConversationMemory.Builder() .maxHistoryLength(50) .enableContextCompression(true) .compressionRatio(0.7) .enableSemanticSearch(true) .vectorDimensions(1536) .similarityThreshold(0.8) .build()
val agent = Agent.Builder() .withModel("gpt-4") .withMemory(memory) .build()
|
追踪和监控
1 2 3 4 5 6 7 8 9 10 11 12
| val tracer = AgentTracer.Builder() .enablePerformanceMetrics(true) .enableTokenUsageTracking(true) .enableErrorTracking(true) .enableCustomMetrics(true) .build()
val agent = Agent.Builder() .withModel("gpt-4") .withTracer(tracer) .build()
|
🏢 企业级应用案例
案例六:电商智能推荐系统
基于 Koog 构建的电商推荐引擎:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
| val recommendationAgent = Agent.Builder() .withModel("gpt-4") .withTools(listOf( userProfileTool, productCatalogTool, purchaseHistoryTool, realTimeAnalyticsTool )) .withMemory(RecommendationMemory.Builder() .enableCollaborativeFiltering(true) .enableContentBasedFiltering(true) .enableRealTimeLearning(true) .build()) .build()
suspend fun getPersonalizedRecommendations(userId: String): List<Product> { val recommendations = recommendationAgent.execute( "为用户 $userId 推荐相关产品" ) return parseRecommendations(recommendations) }
|
案例七:医疗诊断辅助系统
医院级别的 AI 诊断辅助工具:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
| val medicalAgent = Agent.Builder() .withModel("gpt-4") .withTools(listOf( symptomAnalysisTool, medicalKnowledgeBaseTool, drugInteractionTool, patientHistoryTool )) .withMemory(MedicalMemory.Builder() .enablePatientPrivacy(true) .enableAuditTrail(true) .complianceLevel(ComplianceLevel.HIPAA) .build()) .withSafetyGuardrails(true) .build()
suspend fun analyzeSymptoms(symptoms: List<String>): DiagnosticSuggestion { val analysis = medicalAgent.execute( "分析以下症状:${symptoms.joinToString(", ")}" ) return DiagnosticSuggestion.fromAnalysis(analysis) }
|
案例八:智能代码审查助手
开发团队使用的代码质量检查工具:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
| val codeReviewAgent = Agent.Builder() .withModel("gpt-4") .withTools(listOf( staticAnalysisTool, securityScanTool, performanceAnalysisTool, codeStyleCheckerTool )) .withMemory(CodeReviewMemory.Builder() .enableLearningFromReviews(true) .enableTeamKnowledgeSharing(true) .build()) .build()
suspend fun reviewCode(code: String, language: String): CodeReviewResult { val review = codeReviewAgent.execute( "审查以下 $language 代码:\n$code" ) return CodeReviewResult.fromReview(review) }
|
📊 性能基准测试
官方性能数据
根据 JetBrains 官方测试数据:
| 指标 |
传统方法 |
Koog 框架 |
提升幅度 |
| 响应时间 |
2.5s |
1.2s |
52% |
| Token 消耗 |
100% |
58% |
42% |
| 内存使用 |
100% |
75% |
25% |
| 并发处理 |
100 req/s |
300 req/s |
200% |
实际应用性能
某大型电商平台使用 Koog 后的性能提升:
- 客服响应时间:从 30 秒降至 8 秒
- 推荐准确率:从 65% 提升至 89%
- 系统吞吐量:提升 150%
- 运维成本:降低 40%
🛡️ 安全性和合规性
数据安全
1 2 3 4 5 6 7 8 9 10
| val secureAgent = Agent.Builder() .withModel("gpt-4") .withSecurityConfig(SecurityConfig.Builder() .enableDataEncryption(true) .enableAccessControl(true) .enableAuditLogging(true) .complianceStandards(listOf("GDPR", "HIPAA", "SOX")) .build()) .build()
|
隐私保护
- 端到端加密
- 数据脱敏处理
- 访问权限控制
- 审计日志记录
🔮 未来展望
Koog 作为 JetBrains 的官方 AI 框架,将持续获得:
- 定期的功能更新
- 性能优化
- 新模型支持
- 社区贡献
- 企业级安全增强
- 更多行业解决方案
总结
Koog 框架为 Java 开发者提供了一个强大而灵活的 AI 开发平台。通过利用 Kotlin 的多平台特性和与 Java 的无缝集成,开发者可以在熟悉的开发环境中构建现代化的 AI 智能体应用。
无论是构建智能客服系统、金融合规工具,还是企业级 AI 应用,Koog 都能提供稳定、高效、可扩展的解决方案。随着 AI 技术的不断发展,Koog 将成为 Java 开发者进入 AI 领域的重要工具。
Koog 是 JetBrains 的开源项目,项目地址:https://github.com/JetBrains/koog
更多信息请访问:https://docs.koog.ai/