Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 5 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,7 @@ The Spring integration module provides seamless integration with Spring AI and S
### Annotations

#### Client
- **`@McpLogging`** - Annotates methods that handle logging message notifications from MCP servers
- **`@McpLogging`** - Annotates methods that handle logging message notifications from MCP servers (requires `clientId` parameter)
- **`@McpSampling`** - Annotates methods that handle sampling requests from MCP servers
- **`@McpElicitation`** - Annotates methods that handle elicitation requests to gather additional information from users
- **`@McpProgress`** - Annotates methods that handle progress notifications for long-running operations
Expand Down Expand Up @@ -931,21 +931,23 @@ public class LoggingHandler {

/**
* Handle logging message notifications with a single parameter.
* Note: clientId is now required for all @McpLogging annotations.
* @param notification The logging message notification
*/
@McpLogging
@McpLogging(clientId = "default-client")
public void handleLoggingMessage(LoggingMessageNotification notification) {
System.out.println("Received logging message: " + notification.level() + " - " + notification.logger() + " - "
+ notification.data());
}

/**
* Handle logging message notifications with individual parameters.
* Note: clientId is now required for all @McpLogging annotations.
* @param level The logging level
* @param logger The logger name
* @param data The log message data
*/
@McpLogging
@McpLogging(clientId = "default-client")
public void handleLoggingMessageWithParams(LoggingLevel level, String logger, String data) {
System.out.println("Received logging message with params: " + level + " - " + logger + " - " + data);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,9 +52,9 @@
public @interface McpLogging {

/**
* Used as connection or client identifier to select the MCP client, the logging
* consumer is associated with. If not specified, is applied to all clients.
* Used as connection or client identifier to select the MCP clients, the logging
* consumer is associated with. At least one client ID must be specified.
*/
String clientId() default "";
String clientId();

}
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,21 @@

package org.springaicommunity.mcp.method.logging;

import java.util.Objects;
import java.util.function.Function;

import io.modelcontextprotocol.spec.McpSchema.LoggingMessageNotification;
import reactor.core.publisher.Mono;

public record AsyncLoggingSpecification(String clientId,
Function<LoggingMessageNotification, Mono<Void>> loggingHandler) {

public AsyncLoggingSpecification {
Objects.requireNonNull(clientId, "clientId must not be null");
if (clientId.trim().isEmpty()) {
throw new IllegalArgumentException("clientId must not be empty");
}
Objects.requireNonNull(loggingHandler, "loggingHandler must not be null");
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,18 @@

package org.springaicommunity.mcp.method.logging;

import java.util.Objects;
import java.util.function.Consumer;

import io.modelcontextprotocol.spec.McpSchema.LoggingMessageNotification;

public record SyncLoggingSpecification(String clientId, Consumer<LoggingMessageNotification> loggingHandler) {
}

public SyncLoggingSpecification {
Objects.requireNonNull(clientId, "clientId must not be null");
if (clientId.trim().isEmpty()) {
throw new IllegalArgumentException("clientId must not be empty");
}
Objects.requireNonNull(loggingHandler, "loggingHandler must not be null");
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ public class AsyncMcpLoggingMethodCallbackExample {
* @param notification The logging message notification
* @return A Mono that completes when the processing is done
*/
@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> handleLoggingMessage(LoggingMessageNotification notification) {
return Mono.fromRunnable(() -> {
System.out.println("Received logging message: " + notification.level() + " - " + notification.logger()
Expand All @@ -45,7 +45,7 @@ public Mono<Void> handleLoggingMessage(LoggingMessageNotification notification)
* @param data The log message data
* @return A Mono that completes when the processing is done
*/
@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> handleLoggingMessageWithParams(LoggingLevel level, String logger, String data) {
return Mono.fromRunnable(() -> {
System.out.println("Received logging message with params: " + level + " - " + logger + " - " + data);
Expand All @@ -56,7 +56,7 @@ public Mono<Void> handleLoggingMessageWithParams(LoggingLevel level, String logg
* Example method that accepts a LoggingMessageNotification with void return type.
* @param notification The logging message notification
*/
@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessageVoid(LoggingMessageNotification notification) {
System.out.println("Received logging message (void): " + notification.level() + " - " + notification.logger()
+ " - " + notification.data());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,14 +41,14 @@ static class ValidMethods {

private String lastData;

@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> handleLoggingMessage(LoggingMessageNotification notification) {
return Mono.fromRunnable(() -> {
this.lastNotification = notification;
});
}

@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> handleLoggingMessageWithParams(LoggingLevel level, String logger, String data) {
return Mono.fromRunnable(() -> {
this.lastLevel = level;
Expand All @@ -57,7 +57,7 @@ public Mono<Void> handleLoggingMessageWithParams(LoggingLevel level, String logg
});
}

@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessageVoid(LoggingMessageNotification notification) {
this.lastNotification = notification;
}
Expand All @@ -69,27 +69,27 @@ public void handleLoggingMessageVoid(LoggingMessageNotification notification) {
*/
static class InvalidMethods {

@McpLogging
@McpLogging(clientId = "test-client")
public String invalidReturnType(LoggingMessageNotification notification) {
return "Invalid";
}

@McpLogging
@McpLogging(clientId = "test-client")
public Mono<String> invalidMonoReturnType(LoggingMessageNotification notification) {
return Mono.just("Invalid");
}

@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> invalidParameterCount(LoggingMessageNotification notification, String extra) {
return Mono.empty();
}

@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> invalidParameterType(String invalidType) {
return Mono.empty();
}

@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> invalidParameterTypes(String level, int logger, boolean data) {
return Mono.empty();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ public class SyncMcpLoggingMethodCallbackExample {
* Example method that accepts a LoggingMessageNotification.
* @param notification The logging message notification
*/
@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessage(LoggingMessageNotification notification) {
System.out.println("Received logging message: " + notification.level() + " - " + notification.logger() + " - "
+ notification.data());
Expand All @@ -39,7 +39,7 @@ public void handleLoggingMessage(LoggingMessageNotification notification) {
* @param logger The logger name
* @param data The log message data
*/
@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessageWithParams(LoggingLevel level, String logger, String data) {
System.out.println("Received logging message with params: " + level + " - " + logger + " - " + data);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,12 +39,12 @@ static class ValidMethods {

private String lastData;

@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessage(LoggingMessageNotification notification) {
this.lastNotification = notification;
}

@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessageWithParams(LoggingLevel level, String logger, String data) {
this.lastLevel = level;
this.lastLogger = logger;
Expand All @@ -58,22 +58,22 @@ public void handleLoggingMessageWithParams(LoggingLevel level, String logger, St
*/
static class InvalidMethods {

@McpLogging
@McpLogging(clientId = "test-client")
public String invalidReturnType(LoggingMessageNotification notification) {
return "Invalid";
}

@McpLogging
@McpLogging(clientId = "test-client")
public void invalidParameterCount(LoggingMessageNotification notification, String extra) {
// Invalid parameter count
}

@McpLogging
@McpLogging(clientId = "test-client")
public void invalidParameterType(String invalidType) {
// Invalid parameter type
}

@McpLogging
@McpLogging(clientId = "test-client")
public void invalidParameterTypes(String level, int logger, boolean data) {
// Invalid parameter types
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,14 +38,14 @@ static class TestAsyncLoggingProvider {

private String lastData;

@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> handleLoggingMessage(LoggingMessageNotification notification) {
return Mono.fromRunnable(() -> {
this.lastNotification = notification;
});
}

@McpLogging
@McpLogging(clientId = "test-client")
public Mono<Void> handleLoggingMessageWithParams(LoggingLevel level, String logger, String data) {
return Mono.fromRunnable(() -> {
this.lastLevel = level;
Expand All @@ -54,7 +54,7 @@ public Mono<Void> handleLoggingMessageWithParams(LoggingLevel level, String logg
});
}

@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessageVoid(LoggingMessageNotification notification) {
this.lastNotification = notification;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,12 +36,12 @@ static class LoggingHandler {

private String lastData;

@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessage(LoggingMessageNotification notification) {
this.lastNotification = notification;
}

@McpLogging
@McpLogging(clientId = "test-client")
public void handleLoggingMessageWithParams(LoggingLevel level, String logger, String data) {
this.lastLevel = level;
this.lastLogger = logger;
Expand Down