Skip to content

Commit 58787ae

Browse files
authored
Merge pull request #103 from schemacrawler/nextrel
Support streamable HTTP and resources
2 parents bb45fa2 + f2bc81d commit 58787ae

File tree

38 files changed

+552
-220
lines changed

38 files changed

+552
-220
lines changed

.github/README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
<!-- markdownlint-disable MD041 -->
22
[![Quick Build](https://github.com/schemacrawler/SchemaCrawler-AI/workflows/Quick%20Build/badge.svg)](https://github.com/schemacrawler/SchemaCrawler-AI/actions?query=workflow%3A%22Quick+Build%22)
3-
3+
[![Docker Pulls](https://img.shields.io/docker/pulls/schemacrawler/schemacrawler-ai?color=FFDAB9)](https://hub.docker.com/r/schemacrawler/schemacrawler-ai/)
44

55
# <img src="https://raw.githubusercontent.com/schemacrawler/SchemaCrawler/main/schemacrawler-website/src/site/resources/images/schemacrawler_logo.png" height="100px" width="100px" valign="middle"/> SchemaCrawler - AI
66

.github/workflows/publish-mcp.yml

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
name: Publish to MCP Registry
2+
3+
on:
4+
workflow_dispatch:
5+
6+
jobs:
7+
publish:
8+
runs-on: ubuntu-latest
9+
permissions:
10+
id-token: write # Required for OIDC authentication
11+
contents: read
12+
13+
steps:
14+
15+
- id: install-mcp-publisher
16+
name: Install MCP Publisher
17+
run: |
18+
curl -L "https://github.com/modelcontextprotocol/registry/releases/download/v1.0.0/mcp-publisher_1.0.0_$(uname -s | tr '[:upper:]' '[:lower:]')_$(uname -m | sed 's/x86_64/amd64/;s/aarch64/arm64/').tar.gz" | tar xz mcp-publisher
19+
20+
- id: checkout-code
21+
name: Checkout code
22+
uses: actions/checkout@v5
23+
24+
- id: publish-mcp-registry
25+
name: Publish to MCP Registry
26+
shell: bash
27+
run: |
28+
./mcp-publisher login github-oidc
29+
./mcp-publisher publish \
30+
--dry-run \
31+
--file=./schemacrawler-ai-mcpserver/mcp-registration.json
32+
./mcp-publisher publish \
33+
--file=./schemacrawler-ai-mcpserver/mcp-registration.json
34+
./mcp-publisher logout

Dockerfile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
# ========================================================================
88

99
# Provided arguments
10-
ARG FROM_IMAGE=schemacrawler/schemacrawler:v16.28.1
10+
ARG FROM_IMAGE=schemacrawler/schemacrawler:v16.28.2
1111

1212
# BUILDER stage - Build SchemaCrawler AI
1313
FROM maven:3.9-eclipse-temurin-21 AS builder

changelog.md

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,14 +2,21 @@
22

33
SchemaCrawler AI release notes.
44

5+
<a name="v16.28.2-1"></a>
6+
## Release 16.28.2-1 - 2025-09-21
7+
8+
- Support streamable HTTP protocol for MCP Server
9+
- Publish MCP resources for database object metadata
10+
11+
512
<a name="v16.28.1-2"></a>
6-
## Release 16.28.1-2 - 2025-09-17
13+
## Release 16.28.2-2 - 2025-09-17
714

815
- Add tags to publish to https://github.com/modelcontextprotocol/registry/
916

1017

1118
<a name="v16.28.1-1"></a>
12-
## Release 16.28.1-1 - 2025-09-16
19+
## Release 16.28.2-1 - 2025-09-16
1320

1421
- Refactor code to make it more idiomatic in the Spring Frameork
1522
- Format tool error messages in JSON

pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66

77
<groupId>us.fatehi</groupId>
88
<artifactId>schemacrawler-ai-aggregator</artifactId>
9-
<version>16.28.1-2</version>
9+
<version>16.28.2-2</version>
1010
<packaging>pom</packaging>
1111
<name>SchemaCrawler AI [Aggregator]</name>
1212

schemacrawler-ai-aichat/pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
<parent>
55
<groupId>us.fatehi</groupId>
66
<artifactId>schemacrawler-ai-parent</artifactId>
7-
<version>16.28.1-2</version>
7+
<version>16.28.2-2</version>
88
<relativePath>../schemacrawler-ai-parent</relativePath>
99
</parent>
1010
<artifactId>schemacrawler-ai-aichat</artifactId>

schemacrawler-ai-core/pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
<parent>
77
<groupId>us.fatehi</groupId>
88
<artifactId>schemacrawler-ai-parent</artifactId>
9-
<version>16.28.1-2</version>
9+
<version>16.28.2-2</version>
1010
<relativePath>../schemacrawler-ai-parent</relativePath>
1111
</parent>
1212

schemacrawler-ai-core/src/main/java/schemacrawler/tools/ai/tools/AbstractFunctionDefinition.java

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,8 +8,9 @@
88

99
package schemacrawler.tools.ai.tools;
1010

11+
import static schemacrawler.tools.ai.utility.JsonUtility.mapper;
12+
1113
import com.fasterxml.jackson.annotation.JsonIgnore;
12-
import com.fasterxml.jackson.databind.ObjectMapper;
1314
import com.fasterxml.jackson.databind.PropertyNamingStrategies.KebabCaseStrategy;
1415

1516
public abstract class AbstractFunctionDefinition<P extends FunctionParameters>
@@ -44,7 +45,7 @@ private void buildToString() {
4445
try {
4546
final FunctionParameters parametersObject =
4647
getParametersClass().getDeclaredConstructor().newInstance();
47-
parameters = new ObjectMapper().writeValueAsString(parametersObject);
48+
parameters = mapper.writeValueAsString(parametersObject);
4849
} catch (final Exception e) {
4950
parameters =
5051
new KebabCaseStrategy()

schemacrawler-ai-core/src/main/java/schemacrawler/tools/ai/tools/FunctionCallback.java

Lines changed: 28 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -9,11 +9,11 @@
99
package schemacrawler.tools.ai.tools;
1010

1111
import static java.util.Objects.requireNonNull;
12+
import static schemacrawler.tools.ai.utility.JsonUtility.mapper;
1213
import static schemacrawler.tools.ai.utility.JsonUtility.wrapException;
1314
import static us.fatehi.utility.Utility.isBlank;
1415

1516
import com.fasterxml.jackson.databind.JsonNode;
16-
import com.fasterxml.jackson.databind.ObjectMapper;
1717
import com.fasterxml.jackson.databind.node.ObjectNode;
1818
import java.sql.Connection;
1919
import java.util.Optional;
@@ -32,8 +32,6 @@ public final class FunctionCallback {
3232

3333
private static final Logger LOGGER = Logger.getLogger(FunctionCallback.class.getCanonicalName());
3434

35-
private static ObjectMapper objectMapper = new ObjectMapper();
36-
3735
private FunctionDefinition<FunctionParameters> functionDefinition;
3836
private final Catalog catalog;
3937

@@ -71,9 +69,9 @@ public String execute(final String argumentsString, final Connection connection)
7169

7270
requireNonNull(connection, "No database connection provided");
7371

74-
final PropertyName functionName = getFunctionName();
7572
LOGGER.log(
76-
Level.INFO, new StringFormat("Executing%n%s", toObject(argumentsString).toPrettyString()));
73+
Level.FINER,
74+
new StringFormat("Executing%n%s", toCallObject(argumentsString).toPrettyString()));
7775

7876
if (functionDefinition == null) {
7977
return "";
@@ -89,8 +87,7 @@ public String execute(final String argumentsString, final Connection connection)
8987
Level.INFO,
9088
e,
9189
new StringFormat(
92-
"Could not call function with arguments: %s(%s)%n%s",
93-
functionName, argumentsString, e.getMessage()));
90+
"Exception executing: %s%n%s", toCallObject(argumentsString), e.getMessage()));
9491
return wrapException(e);
9592
}
9693
}
@@ -110,9 +107,31 @@ public PropertyName getFunctionName() {
110107
return functionName;
111108
}
112109

110+
public JsonNode toCallObject(final String argumentsString) {
111+
final ObjectNode objectNode = mapper.createObjectNode();
112+
113+
final PropertyName functionName = getFunctionName();
114+
objectNode.put("name", functionName.getName());
115+
116+
try {
117+
final String functionArguments;
118+
if (isBlank(argumentsString)) {
119+
functionArguments = "{}";
120+
} else {
121+
functionArguments = argumentsString;
122+
}
123+
final JsonNode arguments = mapper.readTree(functionArguments);
124+
objectNode.set("arguments", arguments);
125+
} catch (final Exception e) {
126+
objectNode.set("arguments", mapper.createObjectNode());
127+
}
128+
129+
return objectNode;
130+
}
131+
113132
@Override
114133
public String toString() {
115-
return toObject(null).toPrettyString();
134+
return toCallObject(null).toPrettyString();
116135
}
117136

118137
private String executeFunction(final FunctionParameters arguments, final Connection connection)
@@ -141,9 +160,8 @@ private <P extends FunctionParameters> P instantiateArguments(final String argum
141160
} else {
142161
functionArguments = argumentsString;
143162
}
144-
final ObjectMapper objectMapper = new ObjectMapper();
145163
try {
146-
final P parameters = objectMapper.readValue(functionArguments, parametersClass);
164+
final P parameters = mapper.readValue(functionArguments, parametersClass);
147165
LOGGER.log(Level.FINE, String.valueOf(parameters));
148166
return parameters;
149167
} catch (final Exception e) {
@@ -156,26 +174,4 @@ private <P extends FunctionParameters> P instantiateArguments(final String argum
156174
return parametersClass.getDeclaredConstructor().newInstance();
157175
}
158176
}
159-
160-
private ObjectNode toObject(final String argumentsString) {
161-
final ObjectNode objectNode = objectMapper.createObjectNode();
162-
163-
final PropertyName functionName = getFunctionName();
164-
objectNode.put("name", functionName.getName());
165-
166-
try {
167-
final String functionArguments;
168-
if (isBlank(argumentsString)) {
169-
functionArguments = "{}";
170-
} else {
171-
functionArguments = argumentsString;
172-
}
173-
final JsonNode arguments = objectMapper.readTree(functionArguments);
174-
objectNode.set("arguments", arguments);
175-
} catch (final Exception e) {
176-
objectNode.set("arguments", objectMapper.createObjectNode());
177-
}
178-
179-
return objectNode;
180-
}
181177
}

schemacrawler-ai-core/src/main/java/schemacrawler/tools/ai/tools/ToolSpecification.java

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,8 +8,9 @@
88

99
package schemacrawler.tools.ai.tools;
1010

11+
import static schemacrawler.tools.ai.utility.JsonUtility.mapper;
12+
1113
import com.fasterxml.jackson.databind.JsonNode;
12-
import com.fasterxml.jackson.databind.ObjectMapper;
1314
import com.fasterxml.jackson.databind.node.ObjectNode;
1415

1516
public record ToolSpecification(String name, String description, JsonNode parameters) {
@@ -18,10 +19,8 @@ public String getParametersAsString() {
1819
return parameters.toPrettyString();
1920
}
2021

21-
private static final ObjectMapper OBJECT_MAPPER = new ObjectMapper();
22-
2322
public JsonNode getToolSpecification() {
24-
final ObjectNode toolSpecification = OBJECT_MAPPER.createObjectNode();
23+
final ObjectNode toolSpecification = mapper.createObjectNode();
2524
toolSpecification.put("name", name);
2625
toolSpecification.put("description", description);
2726
toolSpecification.set("parameters", parameters);

0 commit comments

Comments
 (0)