Skip to main content
Glama
KallivdH

NS Travel Information Server

by KallivdH

get_travel_advice

Plan train journeys between Dutch stations with real-time routes, transfers, platform details, and crowding information. Optimize trips for departure or arrival times.

Instructions

Get detailed travel routes between two train stations, including transfers, real-time updates, platform information, and journey duration. Can plan trips for immediate departure or for a specific future time, with options to optimize for arrival time. Returns multiple route options with status and crowding information.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
fromStationYesName or code of departure station
toStationYesName or code of destination station
dateTimeNoFormat - date-time (as date-time in RFC3339). Datetime that the user want to depart from his origin or or arrive at his destination
searchForArrivalNoIf true, dateTime is treated as desired arrival time

Implementation Reference

  • Core handler function that executes the tool logic by querying the NS API trips endpoint with user-provided station and datetime parameters.
    async getTravelAdvice(args: GetTravelAdviceArgs): Promise<TravelAdvice[]> { this.ensureApiKeyConfigured(); const response = await this.axiosInstance.get<TravelAdvice[]>( NSApiService.ENDPOINTS.TRIPS, { params: { fromStation: args.fromStation, toStation: args.toStation, dateTime: args.dateTime, searchForArrival: args.searchForArrival, }, } ); return response.data; }
  • Type definitions and validation function for the input arguments of get_travel_advice.
    export interface GetTravelAdviceArgs { fromStation: string; // Departure station toStation: string; // Destination station dateTime?: string; // Optional departure/arrival time searchForArrival?: boolean; // If true, dateTime is treated as arrival time } /** * Type guard for travel advice arguments */ export function isValidTravelAdviceArgs(args: unknown): args is GetTravelAdviceArgs { if (!args || typeof args !== "object") { return false; } const typedArgs = args as Record<string, unknown>; // Required fields if (typeof typedArgs.fromStation !== "string" || typeof typedArgs.toStation !== "string") { return false; } // Optional fields if (typedArgs.dateTime !== undefined && typeof typedArgs.dateTime !== "string") { return false; } if (typedArgs.searchForArrival !== undefined && typeof typedArgs.searchForArrival !== "boolean") { return false; } return true; }
  • src/index.ts:72-96 (registration)
    Tool metadata registration (name, description, inputSchema) in the MCP server's listTools response.
    name: 'get_travel_advice', description: 'Get detailed travel routes between two train stations, including transfers, real-time updates, platform information, and journey duration. Can plan trips for immediate departure or for a specific future time, with options to optimize for arrival time. Returns multiple route options with status and crowding information.', inputSchema: { type: 'object', properties: { fromStation: { type: 'string', description: 'Name or code of departure station', }, toStation: { type: 'string', description: 'Name or code of destination station', }, dateTime: { type: 'string', description: 'Format - date-time (as date-time in RFC3339). Datetime that the user want to depart from his origin or or arrive at his destination', }, searchForArrival: { type: 'boolean', description: 'If true, dateTime is treated as desired arrival time', }, }, required: ['fromStation', 'toStation'], }, },
  • src/index.ts:298-307 (registration)
    Tool dispatch in MCP callTool handler: argument validation and invocation of the NSApiService handler.
    case 'get_travel_advice': { if (!isValidTravelAdviceArgs(rawArgs)) { throw ResponseFormatter.createMcpError( ErrorCode.InvalidParams, 'Invalid arguments for get_travel_advice' ); } const data = await this.nsApiService.getTravelAdvice(rawArgs); return ResponseFormatter.formatSuccess(data); }
  • Identical tool metadata registration in the HTTP MCP server.
    }; // Connect the transport to the server await this.server.connect(transport); } else { res.status(400).json({ error: 'Invalid or missing session ID' }); return; } // Handle the request through the transport await transport.handleRequest(req, res, req.body); } catch (error) { console.error('MCP endpoint error:', error); if (!res.headersSent) { res.status(500).json({ error: 'Internal server error' }); } } }); // MCP GET endpoint - establishes SSE stream for existing sessions this.app.get('/mcp', async (req: Request, res: Response) => { const sessionId = req.headers['mcp-session-id'] as string | undefined; if (!sessionId || !this.transports.has(sessionId)) { res.status(400).send('Invalid or missing session ID'); return; } try { const transport = this.transports.get(sessionId)!; await transport.handleRequest(req, res); } catch (error) { console.error('SSE connection error:', error); if (!res.headersSent) { res.status(500).send('Error establishing SSE connection'); } } }); // MCP DELETE endpoint - terminates sessions this.app.delete('/mcp', async (req: Request, res: Response) => { const sessionId = req.headers['mcp-session-id'] as string | undefined; if (!sessionId || !this.transports.has(sessionId)) { res.status(400).send('Invalid or missing session ID'); return; } try { const transport = this.transports.get(sessionId)!; await transport.handleRequest(req, res); } catch (error) { console.error('Session termination error:', error); if (!res.headersSent) { res.status(500).send('Error processing session termination'); } } }); } private setupErrorHandling(): void { this.server.onerror = (error) => { console.error('[MCP Error]', error); }; process.on('SIGINT', async () => { console.log('Shutting down server...'); await this.server.close(); process.exit(0); }); process.on('SIGTERM', async () => { console.log('Shutting down server...'); await this.server.close(); process.exit(0); }); } private setupHandlers(): void { this.setupToolHandlers(); } private setupToolHandlers(): void { this.server.setRequestHandler(ListToolsRequestSchema, async () => ({ tools: [ { name: 'get_disruptions', description: 'Get comprehensive information about current and planned disruptions on the Dutch railway network. Returns details about maintenance work, unexpected disruptions, alternative transport options, impact on travel times, and relevant advice. Can filter for active disruptions and specific disruption types.', inputSchema: { type: 'object', properties: { isActive: { type: 'boolean', description: 'Filter to only return active disruptions', }, type: { type: 'string', description: 'Type of disruptions to return (e.g., MAINTENANCE, DISRUPTION)', enum: ['MAINTENANCE', 'DISRUPTION'] }, }, }, }, { name: 'get_travel_advice',

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/KallivdH/ns-mcp-server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server