|
1 | 1 | import Map "mo:map/Map"; |
2 | 2 | import { thash } "mo:map/Map"; |
3 | 3 | import Result "mo:base/Result"; |
4 | | -import Text "mo:base/Text"; |
5 | | -import Option "mo:base/Option"; |
6 | | -import Blob "mo:base/Blob"; |
7 | | -import Time "mo:base/Time"; |
8 | 4 | import Principal "mo:base/Principal"; |
9 | 5 | import Json "../../../src/json"; |
10 | 6 | import HttpTypes "mo:http-types"; |
11 | | -import BaseX "mo:base-x-encoder"; |
12 | 7 |
|
13 | 8 | // The only SDK import the user needs! |
14 | 9 | import Mcp "../../../src/mcp/Mcp"; |
@@ -107,44 +102,30 @@ shared persistent actor class McpServer() = self { |
107 | 102 |
|
108 | 103 | // --- PUBLIC ENTRY POINTS --- |
109 | 104 |
|
110 | | - // The streaming callback MUST be a public function of the main actor. |
111 | | - public query func http_request_streaming_callback(token : HttpTypes.StreamingToken) : async ?HttpTypes.StreamingCallbackResponse { |
112 | | - let token_key = BaseX.toBase64(token.vals(), #standard({ includePadding = true })); |
113 | | - // It has access to the actor's state. |
114 | | - if (Option.isNull(Map.get(appContext.activeStreams, thash, token_key))) { |
115 | | - return ?{ body = Blob.fromArray([]); token = null }; |
116 | | - }; |
117 | | - |
118 | | - // Update the timestamp to prove the stream is still active. |
119 | | - Map.set(appContext.activeStreams, thash, token_key, Time.now()); |
120 | | - |
121 | | - let chunk = Text.encodeUtf8("data: {\"type\":\"keep-alive\"}\n\n"); |
122 | | - return ?{ body = chunk; token = ?token }; |
123 | | - }; |
124 | | - |
125 | | - public query func http_request(req : SrvTypes.HttpRequest) : async SrvTypes.HttpResponse { |
126 | | - // Construct the context object on the fly. |
127 | | - let ctx : HttpHandler.Context = { |
128 | | - self = Principal.fromActor(self); // Pass the server principal |
| 105 | + // Helper to avoid repeating context creation. |
| 106 | + private func _create_http_context() : HttpHandler.Context { |
| 107 | + return { |
| 108 | + self = Principal.fromActor(self); |
129 | 109 | active_streams = appContext.activeStreams; |
130 | 110 | mcp_server = mcpServer; |
131 | 111 | streaming_callback = http_request_streaming_callback; |
132 | | - auth = null; // No authentication in this example. |
133 | | - http_asset_cache = null; // No HTTP asset cache in this example. |
| 112 | + auth = null; |
| 113 | + http_asset_cache = null; |
134 | 114 | }; |
135 | | - // Delegate the complex logic to the handler module. |
| 115 | + }; |
| 116 | + |
| 117 | + public query func http_request(req : SrvTypes.HttpRequest) : async SrvTypes.HttpResponse { |
| 118 | + let ctx : HttpHandler.Context = _create_http_context(); |
136 | 119 | return HttpHandler.http_request(ctx, req); |
137 | 120 | }; |
138 | 121 |
|
139 | 122 | public func http_request_update(req : SrvTypes.HttpRequest) : async SrvTypes.HttpResponse { |
140 | | - let ctx : HttpHandler.Context = { |
141 | | - self = Principal.fromActor(self); // Pass the server principal |
142 | | - active_streams = appContext.activeStreams; |
143 | | - mcp_server = mcpServer; |
144 | | - streaming_callback = http_request_streaming_callback; |
145 | | - auth = null; // No authentication in this example. |
146 | | - http_asset_cache = null; // No HTTP asset cache in this example. |
147 | | - }; |
| 123 | + let ctx : HttpHandler.Context = _create_http_context(); |
148 | 124 | return await HttpHandler.http_request_update(ctx, req); |
149 | 125 | }; |
| 126 | + |
| 127 | + public query func http_request_streaming_callback(token : HttpTypes.StreamingToken) : async ?HttpTypes.StreamingCallbackResponse { |
| 128 | + let ctx : HttpHandler.Context = _create_http_context(); |
| 129 | + return HttpHandler.http_request_streaming_callback(ctx, token); |
| 130 | + }; |
150 | 131 | }; |
0 commit comments