actionmcp 0.80.1 → 0.82.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +62 -3
- data/lib/action_mcp/capability.rb +0 -1
- data/lib/action_mcp/client/base.rb +0 -1
- data/lib/action_mcp/client/transport.rb +0 -1
- data/lib/action_mcp/configuration.rb +4 -4
- data/lib/action_mcp/engine.rb +5 -0
- data/lib/action_mcp/json_rpc_handler_base.rb +3 -0
- data/lib/action_mcp/logging/level.rb +84 -0
- data/lib/action_mcp/logging/logger.rb +208 -0
- data/lib/action_mcp/logging/mixin.rb +149 -0
- data/lib/action_mcp/logging/null_logger.rb +94 -0
- data/lib/action_mcp/logging/state.rb +83 -0
- data/lib/action_mcp/logging.rb +81 -5
- data/lib/action_mcp/output_schema_builder.rb +184 -0
- data/lib/action_mcp/resource_template.rb +0 -1
- data/lib/action_mcp/schema_helpers.rb +36 -0
- data/lib/action_mcp/server/handlers/logging_handler.rb +43 -0
- data/lib/action_mcp/server/json_rpc_handler.rb +3 -0
- data/lib/action_mcp/server/tools.rb +4 -5
- data/lib/action_mcp/server/transport_handler.rb +0 -1
- data/lib/action_mcp/tool.rb +104 -19
- data/lib/action_mcp/tool_response.rb +26 -3
- data/lib/action_mcp/version.rb +1 -1
- data/lib/action_mcp.rb +0 -1
- data/lib/generators/action_mcp/tool/templates/tool.rb.erb +12 -1
- metadata +9 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b0ca96b3275c9dcece973bd75cc7eb4585fea06f6a99d8dec6a7603817c28b69
|
4
|
+
data.tar.gz: a188765f7176684ee0875a9eecf25cf07ff4c2338c93be7fc5fe29954f26bbb0
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 678b6231e5c2df59dc9b90c26d5135cfb2ceb2aaa45ed55e774dc9700cf15f634d8a796fa2c9d3e2a78896bf21f41a86d303f2ca97db4445d289f8a24a8892b5
|
7
|
+
data.tar.gz: 2d1458519c3b69045a8f885be8da811544de78e793cc191ca2145d08ebc41a019a209b3f51fc9bcc9138e72b75f6b1fcc11428e01a06b1b6326f7bcc902d7dee
|
data/README.md
CHANGED
@@ -154,9 +154,9 @@ class CalculateSumTool < ApplicationMCPTool
|
|
154
154
|
render(text: "Calculating #{a} + #{b}...")
|
155
155
|
render(text: "The sum is #{sum}")
|
156
156
|
|
157
|
-
# You can
|
157
|
+
# You can report errors if needed
|
158
158
|
if sum > 1000
|
159
|
-
|
159
|
+
report_error("Warning: Sum exceeds recommended limit")
|
160
160
|
end
|
161
161
|
|
162
162
|
# Or even images
|
@@ -279,6 +279,65 @@ end
|
|
279
279
|
|
280
280
|
Resource templates are automatically registered and used when LLMs request resources matching their patterns.
|
281
281
|
|
282
|
+
## 📚 Documentation
|
283
|
+
|
284
|
+
ActionMCP provides comprehensive documentation across multiple specialized guides. Each guide focuses on specific aspects to keep information organized and prevent context overload:
|
285
|
+
|
286
|
+
### Getting Started & Setup
|
287
|
+
- **[Installation & Configuration](README.md#installation)** - Initial setup, database migrations, and basic configuration
|
288
|
+
- **[Authentication with Gateway](README.md#authentication-with-gateway)** - User authentication and authorization patterns
|
289
|
+
|
290
|
+
### Component Development
|
291
|
+
- **[📋 TOOLS.MD](TOOLS.MD)** - Complete guide to developing MCP tools
|
292
|
+
- Generator usage and best practices
|
293
|
+
- Property definitions, validation, and consent management
|
294
|
+
- Output schemas for structured responses
|
295
|
+
- Error handling, testing, and security considerations
|
296
|
+
- Advanced features like additional properties and authentication context
|
297
|
+
|
298
|
+
- **[📝 PROMPTS.MD](PROMPTS.MD)** - Prompt template development guide
|
299
|
+
- Creating reusable prompt templates
|
300
|
+
- Multi-step conversations and mixed content types
|
301
|
+
- Argument validation and prompt chaining
|
302
|
+
|
303
|
+
- **[🔗 RESOURCE_TEMPLATES.md](RESOURCE_TEMPLATES.md)** - Resource template implementation
|
304
|
+
- URI template patterns and parameter extraction
|
305
|
+
- Dynamic resource resolution and collections
|
306
|
+
- Callbacks and validation patterns
|
307
|
+
|
308
|
+
### Client & Integration
|
309
|
+
- **[🔌 CLIENTUSAGE.MD](CLIENTUSAGE.MD)** - Complete client implementation guide
|
310
|
+
- Session management and resumability
|
311
|
+
- Transport configuration and connection handling
|
312
|
+
- Tool, prompt, and resource collections
|
313
|
+
- Production deployment patterns
|
314
|
+
|
315
|
+
### Protocol & Technical Details
|
316
|
+
- **[🚀 The Hitchhiker's Guide to MCP](The_Hitchhikers_Guide_to_MCP.md)** - Protocol versions and migration
|
317
|
+
- Comprehensive comparison of MCP protocol versions (2024-11-05, 2025-03-26, 2025-06-18)
|
318
|
+
- Design decisions and architectural rationale
|
319
|
+
- Migration paths and compatibility considerations
|
320
|
+
- Feature evolution and technical specifications (*Don't Panic!*)
|
321
|
+
|
322
|
+
### Advanced Configuration
|
323
|
+
- **[Session Storage](README.md#session-storage)** - Volatile vs ActiveRecord vs custom session stores
|
324
|
+
- **[Thread Pool Management](README.md#thread-pool-management)** - Performance tuning and graceful shutdown
|
325
|
+
- **[Profiles System](README.md#profiles)** - Multi-tenant capability filtering
|
326
|
+
- **[Production Deployment](README.md#production-deployment-of-mcps0)** - Falcon, Unix sockets, and reverse proxy setup
|
327
|
+
|
328
|
+
### Development & Testing
|
329
|
+
- **[Generators](README.md#generators)** - Rails generators for scaffolding components
|
330
|
+
- **[Testing with TestHelper](README.md#testing-with-testhelper)** - Comprehensive testing strategies
|
331
|
+
- **[Development Commands](README.md#development-commands)** - Rake tasks for debugging and inspection
|
332
|
+
- **[MCP Inspector Integration](README.md#inspecting-your-mcp-server)** - Interactive testing and validation
|
333
|
+
|
334
|
+
### Troubleshooting & Production
|
335
|
+
- **[Error Handling](README.md#error-handling-and-troubleshooting)** - JSON-RPC error codes and debugging
|
336
|
+
- **[Production Considerations](README.md#production-considerations)** - Security, performance, and monitoring
|
337
|
+
- **[Middleware Conflicts](README.md#dealing-with-middleware-conflicts)** - Using `mcp_vanilla.ru` for production
|
338
|
+
|
339
|
+
> **💡 Pro Tip**: Start with the component-specific guides (TOOLS.MD, PROMPTS.MD, RESOURCE_TEMPLATES.md) for hands-on development, then reference the Hitchhiker's Guide for protocol details and CLIENTUSAGE.MD for integration patterns.
|
340
|
+
|
282
341
|
## Configuration
|
283
342
|
|
284
343
|
ActionMCP is configured via `config.action_mcp` in your Rails application.
|
@@ -871,7 +930,7 @@ class MyTool < ApplicationMCPTool
|
|
871
930
|
def perform
|
872
931
|
# Check for error conditions and return clear messages
|
873
932
|
if some_error_condition?
|
874
|
-
|
933
|
+
report_error("Clear error message for the LLM")
|
875
934
|
return
|
876
935
|
end
|
877
936
|
|
@@ -51,9 +51,9 @@ module ActionMCP
|
|
51
51
|
:connects_to
|
52
52
|
|
53
53
|
def initialize
|
54
|
-
@logging_enabled =
|
54
|
+
@logging_enabled = false
|
55
55
|
@list_changed = true
|
56
|
-
@logging_level = :
|
56
|
+
@logging_level = :warning
|
57
57
|
@resources_subscribe = false
|
58
58
|
@elicitation_enabled = false
|
59
59
|
@verbose_logging = false
|
@@ -269,8 +269,8 @@ module ActionMCP
|
|
269
269
|
resources: [ "all" ],
|
270
270
|
options: {
|
271
271
|
list_changed: false,
|
272
|
-
logging_enabled:
|
273
|
-
logging_level: :
|
272
|
+
logging_enabled: false,
|
273
|
+
logging_level: :warning,
|
274
274
|
resources_subscribe: false
|
275
275
|
}
|
276
276
|
},
|
data/lib/action_mcp/engine.rb
CHANGED
@@ -53,6 +53,11 @@ module ActionMCP
|
|
53
53
|
ActionMCP.configuration.load_profiles
|
54
54
|
end
|
55
55
|
|
56
|
+
# Initialize MCP logging system
|
57
|
+
initializer "action_mcp.initialize_logging" do
|
58
|
+
ActionMCP::Logging.initialize_from_config!
|
59
|
+
end
|
60
|
+
|
56
61
|
|
57
62
|
# Configure autoloading for the mcp/tools directory and identifiers
|
58
63
|
initializer "action_mcp.autoloading", before: :set_autoload_paths do |app|
|
@@ -25,6 +25,9 @@ module ActionMCP
|
|
25
25
|
TOOLS_LIST = "tools/list"
|
26
26
|
TOOLS_CALL = "tools/call"
|
27
27
|
|
28
|
+
# Logging methods
|
29
|
+
LOGGING_SET_LEVEL = "logging/setLevel"
|
30
|
+
|
28
31
|
# Notification methods
|
29
32
|
NOTIFICATIONS_INITIALIZED = "notifications/initialized"
|
30
33
|
NOTIFICATIONS_CANCELLED = "notifications/cancelled"
|
@@ -0,0 +1,84 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module ActionMCP
|
4
|
+
module Logging
|
5
|
+
# RFC 5424 log levels for MCP logging
|
6
|
+
# @see https://datatracker.ietf.org/doc/html/rfc5424#section-6.2.1
|
7
|
+
class Level
|
8
|
+
# Log levels in order of severity (ascending)
|
9
|
+
LEVELS = {
|
10
|
+
debug: 0,
|
11
|
+
info: 1,
|
12
|
+
notice: 2,
|
13
|
+
warning: 3,
|
14
|
+
error: 4,
|
15
|
+
critical: 5,
|
16
|
+
alert: 6,
|
17
|
+
emergency: 7
|
18
|
+
}.freeze
|
19
|
+
|
20
|
+
# Reverse mapping for converting integers back to symbols
|
21
|
+
LEVEL_NAMES = LEVELS.invert.freeze
|
22
|
+
|
23
|
+
class << self
|
24
|
+
# Check if a level is valid
|
25
|
+
# @param level [String, Symbol, Integer] The level to check
|
26
|
+
# @return [Boolean] true if valid, false otherwise
|
27
|
+
def valid?(level)
|
28
|
+
case level
|
29
|
+
when String, Symbol
|
30
|
+
LEVELS.key?(level.to_sym)
|
31
|
+
when Integer
|
32
|
+
LEVEL_NAMES.key?(level)
|
33
|
+
else
|
34
|
+
false
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
# Coerce a level to its integer value
|
39
|
+
# @param level [String, Symbol, Integer] The level to coerce
|
40
|
+
# @return [Integer] The integer severity value
|
41
|
+
# @raise [ArgumentError] if level is invalid
|
42
|
+
def coerce(level)
|
43
|
+
case level
|
44
|
+
when String, Symbol
|
45
|
+
symbol_level = level.to_sym
|
46
|
+
LEVELS.fetch(symbol_level) do
|
47
|
+
raise ArgumentError, "Invalid log level: #{level}. Valid levels: #{LEVELS.keys.join(', ')}"
|
48
|
+
end
|
49
|
+
when Integer
|
50
|
+
unless LEVEL_NAMES.key?(level)
|
51
|
+
raise ArgumentError, "Invalid log level: #{level}. Valid levels: 0-7"
|
52
|
+
end
|
53
|
+
level
|
54
|
+
else
|
55
|
+
raise ArgumentError, "Invalid log level type: #{level.class}. Expected String, Symbol, or Integer"
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
# Convert integer level back to symbol
|
60
|
+
# @param level_int [Integer] The integer level
|
61
|
+
# @return [Symbol] The symbol name
|
62
|
+
def name_for(level_int)
|
63
|
+
LEVEL_NAMES.fetch(level_int) do
|
64
|
+
raise ArgumentError, "Invalid log level integer: #{level_int}"
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
# Get all valid level names as symbols
|
69
|
+
# @return [Array<Symbol>] Array of level symbols
|
70
|
+
def all_levels
|
71
|
+
LEVELS.keys
|
72
|
+
end
|
73
|
+
|
74
|
+
# Check if level_a is more severe than level_b
|
75
|
+
# @param level_a [String, Symbol, Integer] First level
|
76
|
+
# @param level_b [String, Symbol, Integer] Second level
|
77
|
+
# @return [Boolean] true if level_a >= level_b in severity
|
78
|
+
def more_severe_or_equal?(level_a, level_b)
|
79
|
+
coerce(level_a) >= coerce(level_b)
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
84
|
+
end
|
@@ -0,0 +1,208 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module ActionMCP
|
4
|
+
module Logging
|
5
|
+
# MCP Logger that sends notifications/message to the MCP client
|
6
|
+
class Logger
|
7
|
+
attr_reader :name, :session, :state
|
8
|
+
|
9
|
+
# Initialize a new MCP logger
|
10
|
+
# @param name [String, nil] Optional logger name
|
11
|
+
# @param session [ActionMCP::Session] The MCP session for transport
|
12
|
+
# @param state [ActionMCP::Logging::State] The global logging state
|
13
|
+
def initialize(name: nil, session:, state:)
|
14
|
+
@name = name
|
15
|
+
@session = session
|
16
|
+
@state = state
|
17
|
+
end
|
18
|
+
|
19
|
+
# Log a debug message
|
20
|
+
# @param message [String, nil] The message (if no block given)
|
21
|
+
# @param data [Object] Additional structured data
|
22
|
+
# @yield Block that returns the message (evaluated only if logging)
|
23
|
+
# @return [void]
|
24
|
+
def debug(message = nil, data: nil, &block)
|
25
|
+
log(:debug, message, data: data, &block)
|
26
|
+
end
|
27
|
+
|
28
|
+
# Log an info message
|
29
|
+
# @param message [String, nil] The message (if no block given)
|
30
|
+
# @param data [Object] Additional structured data
|
31
|
+
# @yield Block that returns the message (evaluated only if logging)
|
32
|
+
# @return [void]
|
33
|
+
def info(message = nil, data: nil, &block)
|
34
|
+
log(:info, message, data: data, &block)
|
35
|
+
end
|
36
|
+
|
37
|
+
# Log a notice message
|
38
|
+
# @param message [String, nil] The message (if no block given)
|
39
|
+
# @param data [Object] Additional structured data
|
40
|
+
# @yield Block that returns the message (evaluated only if logging)
|
41
|
+
# @return [void]
|
42
|
+
def notice(message = nil, data: nil, &block)
|
43
|
+
log(:notice, message, data: data, &block)
|
44
|
+
end
|
45
|
+
|
46
|
+
# Log a warning message
|
47
|
+
# @param message [String, nil] The message (if no block given)
|
48
|
+
# @param data [Object] Additional structured data
|
49
|
+
# @yield Block that returns the message (evaluated only if logging)
|
50
|
+
# @return [void]
|
51
|
+
def warning(message = nil, data: nil, &block)
|
52
|
+
log(:warning, message, data: data, &block)
|
53
|
+
end
|
54
|
+
alias_method :warn, :warning
|
55
|
+
|
56
|
+
# Log an error message
|
57
|
+
# @param message [String, nil] The message (if no block given)
|
58
|
+
# @param data [Object] Additional structured data
|
59
|
+
# @yield Block that returns the message (evaluated only if logging)
|
60
|
+
# @return [void]
|
61
|
+
def error(message = nil, data: nil, &block)
|
62
|
+
log(:error, message, data: data, &block)
|
63
|
+
end
|
64
|
+
|
65
|
+
# Log a critical message
|
66
|
+
# @param message [String, nil] The message (if no block given)
|
67
|
+
# @param data [Object] Additional structured data
|
68
|
+
# @yield Block that returns the message (evaluated only if logging)
|
69
|
+
# @return [void]
|
70
|
+
def critical(message = nil, data: nil, &block)
|
71
|
+
log(:critical, message, data: data, &block)
|
72
|
+
end
|
73
|
+
|
74
|
+
# Log an alert message
|
75
|
+
# @param message [String, nil] The message (if no block given)
|
76
|
+
# @param data [Object] Additional structured data
|
77
|
+
# @yield Block that returns the message (evaluated only if logging)
|
78
|
+
# @return [void]
|
79
|
+
def alert(message = nil, data: nil, &block)
|
80
|
+
log(:alert, message, data: data, &block)
|
81
|
+
end
|
82
|
+
|
83
|
+
# Log an emergency message
|
84
|
+
# @param message [String, nil] The message (if no block given)
|
85
|
+
# @param data [Object] Additional structured data
|
86
|
+
# @yield Block that returns the message (evaluated only if logging)
|
87
|
+
# @return [void]
|
88
|
+
def emergency(message = nil, data: nil, &block)
|
89
|
+
log(:emergency, message, data: data, &block)
|
90
|
+
end
|
91
|
+
|
92
|
+
# Check if debug level is enabled
|
93
|
+
# @return [Boolean] true if debug messages will be logged
|
94
|
+
def debug?
|
95
|
+
state.should_log?(:debug)
|
96
|
+
end
|
97
|
+
|
98
|
+
# Check if info level is enabled
|
99
|
+
# @return [Boolean] true if info messages will be logged
|
100
|
+
def info?
|
101
|
+
state.should_log?(:info)
|
102
|
+
end
|
103
|
+
|
104
|
+
# Check if notice level is enabled
|
105
|
+
# @return [Boolean] true if notice messages will be logged
|
106
|
+
def notice?
|
107
|
+
state.should_log?(:notice)
|
108
|
+
end
|
109
|
+
|
110
|
+
# Check if warning level is enabled
|
111
|
+
# @return [Boolean] true if warning messages will be logged
|
112
|
+
def warning?
|
113
|
+
state.should_log?(:warning)
|
114
|
+
end
|
115
|
+
alias_method :warn?, :warning?
|
116
|
+
|
117
|
+
# Check if error level is enabled
|
118
|
+
# @return [Boolean] true if error messages will be logged
|
119
|
+
def error?
|
120
|
+
state.should_log?(:error)
|
121
|
+
end
|
122
|
+
|
123
|
+
# Check if critical level is enabled
|
124
|
+
# @return [Boolean] true if critical messages will be logged
|
125
|
+
def critical?
|
126
|
+
state.should_log?(:critical)
|
127
|
+
end
|
128
|
+
|
129
|
+
# Check if alert level is enabled
|
130
|
+
# @return [Boolean] true if alert messages will be logged
|
131
|
+
def alert?
|
132
|
+
state.should_log?(:alert)
|
133
|
+
end
|
134
|
+
|
135
|
+
# Check if emergency level is enabled
|
136
|
+
# @return [Boolean] true if emergency messages will be logged
|
137
|
+
def emergency?
|
138
|
+
state.should_log?(:emergency)
|
139
|
+
end
|
140
|
+
|
141
|
+
private
|
142
|
+
|
143
|
+
# Core logging method
|
144
|
+
# @param level [Symbol] The log level
|
145
|
+
# @param message [String, nil] The message
|
146
|
+
# @param data [Object] Additional data
|
147
|
+
# @yield Block that returns message
|
148
|
+
# @return [void]
|
149
|
+
def log(level, message = nil, data: nil, &block)
|
150
|
+
return unless state.should_log?(level)
|
151
|
+
|
152
|
+
# Evaluate message from block if provided
|
153
|
+
final_message = if block_given?
|
154
|
+
yield
|
155
|
+
else
|
156
|
+
message
|
157
|
+
end
|
158
|
+
|
159
|
+
# Send MCP notification
|
160
|
+
send_mcp_notification(level, final_message, data)
|
161
|
+
end
|
162
|
+
|
163
|
+
# Send notifications/message to MCP client
|
164
|
+
# @param level [Symbol] The log level
|
165
|
+
# @param message [String] The message
|
166
|
+
# @param data [Object] Additional data
|
167
|
+
# @return [void]
|
168
|
+
def send_mcp_notification(level, message, data)
|
169
|
+
params = {
|
170
|
+
level: level.to_s,
|
171
|
+
data: build_log_data(message, data)
|
172
|
+
}
|
173
|
+
|
174
|
+
# Add logger name if present
|
175
|
+
params[:logger] = name if name
|
176
|
+
|
177
|
+
# Send via session's messaging service
|
178
|
+
session.messaging_service.send_notification("notifications/message", params)
|
179
|
+
rescue StandardError => e
|
180
|
+
# Fallback to Rails logger if MCP transport fails
|
181
|
+
Rails.logger.error "Failed to send MCP log notification: #{e.message}"
|
182
|
+
end
|
183
|
+
|
184
|
+
# Build the data payload for the log message
|
185
|
+
# @param message [String] The primary message
|
186
|
+
# @param additional_data [Object] Additional structured data
|
187
|
+
# @return [Object] The data to send in the notification
|
188
|
+
def build_log_data(message, additional_data)
|
189
|
+
case additional_data
|
190
|
+
when nil
|
191
|
+
message
|
192
|
+
when Hash
|
193
|
+
if message
|
194
|
+
{ message: message }.merge(additional_data)
|
195
|
+
else
|
196
|
+
additional_data
|
197
|
+
end
|
198
|
+
else
|
199
|
+
if message
|
200
|
+
{ message: message, data: additional_data }
|
201
|
+
else
|
202
|
+
additional_data
|
203
|
+
end
|
204
|
+
end
|
205
|
+
end
|
206
|
+
end
|
207
|
+
end
|
208
|
+
end
|
@@ -0,0 +1,149 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module ActionMCP
|
4
|
+
module Logging
|
5
|
+
# Mixin to provide easy MCP logging access for tools, prompts, and resources
|
6
|
+
module Mixin
|
7
|
+
extend ActiveSupport::Concern
|
8
|
+
|
9
|
+
# Get the MCP logger for this instance
|
10
|
+
# @return [ActionMCP::Logging::Logger, ActionMCP::Logging::NullLogger] logger instance
|
11
|
+
def mcp_logger
|
12
|
+
@mcp_logger ||= ActionMCP::Logging.logger_for_context(
|
13
|
+
name: logger_name,
|
14
|
+
execution_context: execution_context
|
15
|
+
)
|
16
|
+
end
|
17
|
+
|
18
|
+
# Log a debug message
|
19
|
+
# @param message [String, nil] The message (if no block given)
|
20
|
+
# @param data [Object] Additional structured data
|
21
|
+
# @yield Block that returns the message (evaluated only if logging)
|
22
|
+
# @return [void]
|
23
|
+
def mcp_debug(message = nil, data: nil, &block)
|
24
|
+
mcp_logger.debug(message, data: data, &block)
|
25
|
+
end
|
26
|
+
|
27
|
+
# Log an info message
|
28
|
+
# @param message [String, nil] The message (if no block given)
|
29
|
+
# @param data [Object] Additional structured data
|
30
|
+
# @yield Block that returns the message (evaluated only if logging)
|
31
|
+
# @return [void]
|
32
|
+
def mcp_info(message = nil, data: nil, &block)
|
33
|
+
mcp_logger.info(message, data: data, &block)
|
34
|
+
end
|
35
|
+
|
36
|
+
# Log a notice message
|
37
|
+
# @param message [String, nil] The message (if no block given)
|
38
|
+
# @param data [Object] Additional structured data
|
39
|
+
# @yield Block that returns the message (evaluated only if logging)
|
40
|
+
# @return [void]
|
41
|
+
def mcp_notice(message = nil, data: nil, &block)
|
42
|
+
mcp_logger.notice(message, data: data, &block)
|
43
|
+
end
|
44
|
+
|
45
|
+
# Log a warning message
|
46
|
+
# @param message [String, nil] The message (if no block given)
|
47
|
+
# @param data [Object] Additional structured data
|
48
|
+
# @yield Block that returns the message (evaluated only if logging)
|
49
|
+
# @return [void]
|
50
|
+
def mcp_warning(message = nil, data: nil, &block)
|
51
|
+
mcp_logger.warning(message, data: data, &block)
|
52
|
+
end
|
53
|
+
alias_method :mcp_warn, :mcp_warning
|
54
|
+
|
55
|
+
# Log an error message
|
56
|
+
# @param message [String, nil] The message (if no block given)
|
57
|
+
# @param data [Object] Additional structured data
|
58
|
+
# @yield Block that returns the message (evaluated only if logging)
|
59
|
+
# @return [void]
|
60
|
+
def mcp_error(message = nil, data: nil, &block)
|
61
|
+
mcp_logger.error(message, data: data, &block)
|
62
|
+
end
|
63
|
+
|
64
|
+
# Log a critical message
|
65
|
+
# @param message [String, nil] The message (if no block given)
|
66
|
+
# @param data [Object] Additional structured data
|
67
|
+
# @yield Block that returns the message (evaluated only if logging)
|
68
|
+
# @return [void]
|
69
|
+
def mcp_critical(message = nil, data: nil, &block)
|
70
|
+
mcp_logger.critical(message, data: data, &block)
|
71
|
+
end
|
72
|
+
|
73
|
+
# Log an alert message
|
74
|
+
# @param message [String, nil] The message (if no block given)
|
75
|
+
# @param data [Object] Additional structured data
|
76
|
+
# @yield Block that returns the message (evaluated only if logging)
|
77
|
+
# @return [void]
|
78
|
+
def mcp_alert(message = nil, data: nil, &block)
|
79
|
+
mcp_logger.alert(message, data: data, &block)
|
80
|
+
end
|
81
|
+
|
82
|
+
# Log an emergency message
|
83
|
+
# @param message [String, nil] The message (if no block given)
|
84
|
+
# @param data [Object] Additional structured data
|
85
|
+
# @yield Block that returns the message (evaluated only if logging)
|
86
|
+
# @return [void]
|
87
|
+
def mcp_emergency(message = nil, data: nil, &block)
|
88
|
+
mcp_logger.emergency(message, data: data, &block)
|
89
|
+
end
|
90
|
+
|
91
|
+
# Check if debug level is enabled
|
92
|
+
# @return [Boolean] true if debug messages will be logged
|
93
|
+
def mcp_debug?
|
94
|
+
mcp_logger.debug?
|
95
|
+
end
|
96
|
+
|
97
|
+
# Check if info level is enabled
|
98
|
+
# @return [Boolean] true if info messages will be logged
|
99
|
+
def mcp_info?
|
100
|
+
mcp_logger.info?
|
101
|
+
end
|
102
|
+
|
103
|
+
# Check if notice level is enabled
|
104
|
+
# @return [Boolean] true if notice messages will be logged
|
105
|
+
def mcp_notice?
|
106
|
+
mcp_logger.notice?
|
107
|
+
end
|
108
|
+
|
109
|
+
# Check if warning level is enabled
|
110
|
+
# @return [Boolean] true if warning messages will be logged
|
111
|
+
def mcp_warning?
|
112
|
+
mcp_logger.warning?
|
113
|
+
end
|
114
|
+
alias_method :mcp_warn?, :mcp_warning?
|
115
|
+
|
116
|
+
# Check if error level is enabled
|
117
|
+
# @return [Boolean] true if error messages will be logged
|
118
|
+
def mcp_error?
|
119
|
+
mcp_logger.error?
|
120
|
+
end
|
121
|
+
|
122
|
+
# Check if critical level is enabled
|
123
|
+
# @return [Boolean] true if critical messages will be logged
|
124
|
+
def mcp_critical?
|
125
|
+
mcp_logger.critical?
|
126
|
+
end
|
127
|
+
|
128
|
+
# Check if alert level is enabled
|
129
|
+
# @return [Boolean] true if alert messages will be logged
|
130
|
+
def mcp_alert?
|
131
|
+
mcp_logger.alert?
|
132
|
+
end
|
133
|
+
|
134
|
+
# Check if emergency level is enabled
|
135
|
+
# @return [Boolean] true if emergency messages will be logged
|
136
|
+
def mcp_emergency?
|
137
|
+
mcp_logger.emergency?
|
138
|
+
end
|
139
|
+
|
140
|
+
private
|
141
|
+
|
142
|
+
# Generate logger name from class name
|
143
|
+
# @return [String] the logger name
|
144
|
+
def logger_name
|
145
|
+
self.class.name&.underscore || "unknown"
|
146
|
+
end
|
147
|
+
end
|
148
|
+
end
|
149
|
+
end
|