Skip to content

Commit 6de5516

Browse files
committed
Add websearch mcp tool
1 parent f931f48 commit 6de5516

3 files changed

Lines changed: 190 additions & 0 deletions

File tree

websearch/pom.xml

Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
2+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
3+
<modelVersion>4.0.0</modelVersion>
4+
<parent>
5+
<groupId>org.tinystruct</groupId>
6+
<artifactId>tinystruct-mcp</artifactId>
7+
<version>1.0.0</version>
8+
</parent>
9+
<packaging>jar</packaging>
10+
<artifactId>tinystruct-mcp-websearch</artifactId>
11+
<dependencies>
12+
</dependencies>
13+
<build>
14+
<plugins>
15+
<plugin>
16+
<groupId>org.apache.maven.plugins</groupId>
17+
<artifactId>maven-compiler-plugin</artifactId>
18+
<version>3.12.1</version>
19+
</plugin>
20+
<plugin>
21+
<groupId>org.apache.maven.plugins</groupId>
22+
<artifactId>maven-surefire-plugin</artifactId>
23+
<version>3.0.0</version>
24+
<configuration>
25+
<includes>
26+
<include>**/*Test.java</include>
27+
</includes>
28+
</configuration>
29+
</plugin>
30+
<plugin>
31+
<groupId>org.apache.maven.plugins</groupId>
32+
<artifactId>maven-dependency-plugin</artifactId>
33+
<executions>
34+
<execution>
35+
<id>copy-dependencies</id>
36+
<phase>compile</phase>
37+
<goals>
38+
<goal>copy-dependencies</goal>
39+
</goals>
40+
<configuration>
41+
<outputDirectory>../lib</outputDirectory>
42+
<overWriteReleases>false</overWriteReleases>
43+
<overWriteSnapshots>false</overWriteSnapshots>
44+
<overWriteIfNewer>true</overWriteIfNewer>
45+
</configuration>
46+
</execution>
47+
</executions>
48+
</plugin>
49+
<plugin>
50+
<groupId>org.apache.maven.plugins</groupId>
51+
<artifactId>maven-jar-plugin</artifactId>
52+
<configuration>
53+
<archive>
54+
<manifest>
55+
<addClasspath>true</addClasspath>
56+
<classpathPrefix>lib/</classpathPrefix>
57+
<mainClass>org.tinystruct.system.Dispatcher</mainClass>
58+
</manifest>
59+
</archive>
60+
</configuration>
61+
</plugin>
62+
<!-- Copy built JAR to parent project's lib folder -->
63+
<plugin>
64+
<groupId>org.apache.maven.plugins</groupId>
65+
<artifactId>maven-antrun-plugin</artifactId>
66+
<version>3.0.0</version>
67+
<executions>
68+
<execution>
69+
<id>copy-jar</id>
70+
<phase>package</phase>
71+
<goals>
72+
<goal>run</goal>
73+
</goals>
74+
<configuration>
75+
<target>
76+
<copy file="${project.build.directory}/${project.build.finalName}.jar"
77+
todir="../lib" />
78+
</target>
79+
</configuration>
80+
</execution>
81+
</executions>
82+
</plugin>
83+
</plugins>
84+
</build>
85+
</project>
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
package org.tinystruct.mcp.websearch;
2+
3+
import org.tinystruct.mcp.MCPServer;
4+
import org.tinystruct.mcp.MCPTool;
5+
6+
import java.util.logging.Logger;
7+
8+
/**
9+
* WebSearch MCP Server
10+
*/
11+
public class WebSearch extends MCPServer {
12+
private static final Logger LOGGER = Logger.getLogger(WebSearch.class.getName());
13+
private static final String WEBSEARCH_PROTOCOL_VERSION = "1.0.0";
14+
15+
@Override
16+
public void init() {
17+
super.init();
18+
19+
// Register WebSearch tool methods
20+
WebSearchTool websearchTool = new WebSearchTool();
21+
this.registerTool(websearchTool);
22+
}
23+
24+
@Override
25+
public String version() {
26+
return WEBSEARCH_PROTOCOL_VERSION;
27+
}
28+
}
Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
package org.tinystruct.mcp.websearch;
2+
3+
import org.tinystruct.ApplicationException;
4+
import org.tinystruct.data.component.Builder;
5+
import org.tinystruct.mcp.MCPClient;
6+
import org.tinystruct.mcp.MCPException;
7+
import org.tinystruct.mcp.MCPTool;
8+
import org.tinystruct.net.URLRequest;
9+
import org.tinystruct.net.handlers.HTTPHandler;
10+
import org.tinystruct.system.annotation.Action;
11+
import org.tinystruct.system.annotation.Argument;
12+
13+
import java.net.MalformedURLException;
14+
import java.net.URI;
15+
import java.net.URL;
16+
import java.net.URLEncoder;
17+
import java.nio.charset.StandardCharsets;
18+
import java.util.logging.Level;
19+
import java.util.logging.Logger;
20+
21+
/**
22+
* WebSearch tool using DuckDuckGo Instant Answer API (JSON)
23+
*/
24+
public class WebSearchTool extends MCPTool {
25+
private static final Logger LOGGER = Logger.getLogger(WebSearchTool.class.getName());
26+
27+
public WebSearchTool() {
28+
super("websearch", "Tool for performing web searches", null, null, true);
29+
}
30+
31+
public WebSearchTool(MCPClient client) {
32+
super("websearch", "Tool for performing web searches", null, client, true);
33+
}
34+
35+
@Action(value = "websearch/search", description = "Perform a web search using DuckDuckGo Instant Answer API", arguments = {
36+
@Argument(key = "query", description = "The search query", type = "string")
37+
})
38+
public Builder search(String query) throws MCPException {
39+
try {
40+
return searchInternal(query);
41+
} catch (Exception e) {
42+
LOGGER.log(Level.SEVERE, "Error performing web search: " + e.getMessage(), e);
43+
throw new MCPException("Error performing web search: " + e.getMessage());
44+
}
45+
}
46+
47+
private Builder searchInternal(String query) throws Exception {
48+
String encodedQuery = URLEncoder.encode(query, StandardCharsets.UTF_8);
49+
String apiUrl = "https://api.duckduckgo.com/?q=" + encodedQuery + "&format=json";
50+
51+
URL url = URI.create(apiUrl).toURL();
52+
URLRequest request = new URLRequest(url);
53+
request.setMethod("GET");
54+
55+
HTTPHandler handler = new HTTPHandler();
56+
final StringBuilder content = new StringBuilder();
57+
58+
try {
59+
handler.handleRequest(request, chunk -> {
60+
content.append(chunk);
61+
});
62+
} catch (ApplicationException e) {
63+
throw new MCPException("HTTP request failed: " + e.getMessage());
64+
}
65+
66+
Builder json = new Builder();
67+
json.parse(content.toString());
68+
69+
Builder result = new Builder();
70+
result.put("status", "success");
71+
result.put("query", query);
72+
result.put("results", json);
73+
74+
LOGGER.info("Successfully fetched search results for query: " + query);
75+
return result;
76+
}
77+
}

0 commit comments

Comments
 (0)