hn-mcp-server
Version:
Model Context Protocol server for HackerNews API access
95 lines (91 loc) • 3.07 kB
JavaScript
/**
* get-front-page MCP Tool
*
* Retrieves current HackerNews front page posts.
* Uses the search API with front_page tag filter.
*/
import { z } from "zod";
import { HNAPIClient } from "../services/hn-api.js";
import { createSuccessResult, handleAPIError } from "../utils/error-handlers.js";
/**
* Input schema for get-front-page tool
*/
export const GetFrontPageInputSchema = z.object({
page: z.number().int().nonnegative().default(0).describe("Page number (0-indexed)"),
hitsPerPage: z.number().int().min(1).max(1000).default(30).describe("Results per page (1-1000)"),
});
/**
* Output schema for get-front-page tool (SearchResult)
*/
export const GetFrontPageOutputSchema = z.object({
hits: z.array(z.any()),
nbHits: z.number().int().nonnegative(),
page: z.number().int().nonnegative(),
nbPages: z.number().int().positive(),
hitsPerPage: z.number().int().positive(),
processingTimeMS: z.number().nonnegative(),
query: z.string(),
params: z.string().min(1),
});
/**
* Get front page posts handler
*
* @param input - Input parameters (page, hitsPerPage)
* @returns Tool result with front page posts
*/
export async function getFrontPageHandler(input) {
try {
// Validate input
const validatedParams = GetFrontPageInputSchema.parse(input);
// Create API client
const client = new HNAPIClient();
// Call search API with front_page tag
const result = await client.search({
query: "",
tags: ["front_page"],
page: validatedParams.page,
hitsPerPage: validatedParams.hitsPerPage,
});
// Validate output
const validatedResult = GetFrontPageOutputSchema.parse(result);
return createSuccessResult(validatedResult);
}
catch (error) {
return handleAPIError(error, "get-front-page");
}
}
/**
* Tool metadata for MCP registration
*/
export const getFrontPageTool = {
name: "get-front-page",
description: `Retrieve posts currently on the HackerNews front page.
Returns stories sorted by HackerNews ranking algorithm. The front page typically contains the most popular and trending stories.
Supports:
- Pagination to view beyond the first page
- Customizable results per page (default: 30)
- All posts are tagged with 'front_page'
Examples:
- Get first page: { }
- Get with custom page size: { "hitsPerPage": 50 }
- Get second page: { "page": 1 }
Returns the same structure as search results with hits, pagination info, and metadata.`,
inputSchema: {
type: "object",
properties: {
page: {
type: "number",
description: "Page number (0-indexed, default: 0)",
default: 0,
},
hitsPerPage: {
type: "number",
description: "Results per page (1-1000, default: 30)",
default: 30,
minimum: 1,
maximum: 1000,
},
},
},
};
//# sourceMappingURL=get-front-page.js.map