Skip to content
Closed
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
22 changes: 22 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,25 @@ node_modules
out



# Markdown twins + scoped llms.txt indexes generated by
# utils/generate-md-twins.mjs at build time. They are derived from the
# framework docs that gofr-dev/gofr overlays onto this repo, so a copy
# committed here would be permanently stale and would not match what
# ships. Unlike public/llms-full.txt (kept as a committed snapshot),
# there is no fallback value in a stale twin — an agent fetching
# /docs/x.md wants the version that is live.
/public/docs/
/public/**/*.md
!/public/AGENTS.md
!/public/index.md
!/public/auth.md
/public/why-gofr/
/public/comparison/
/public/migrate/
/public/learn/
/public/faq/
/public/openapi.json
/public/schemamap.xml
/public/feeds/
/src/data/md-twin-routes.json
12 changes: 11 additions & 1 deletion next.config.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -66,9 +66,19 @@ const __tw = {
...(__pageMeta.twitter || {}),
};
const __derivedCanonical = ${JSON.stringify(__canonical)};
// Advertise the Markdown twin of this page. static-server's
// _headers file can only express site-wide patterns (no per-URL
// variable), so the per-page alternate has to live in the document
// head. Next renders this as
// <link rel="alternate" type="text/markdown" href="/docs/x.md">
// which is how an agent discovers the twin without guessing.
const __alternates = {
canonical: __derivedCanonical,
...(__pageMeta.alternates || {}),
canonical: __pageMeta.alternates?.canonical || __derivedCanonical,
types: {
'text/markdown': __derivedCanonical === '/' ? '/index.md' : __derivedCanonical + '.md',
...(__pageMeta.alternates?.types || {}),
},
};
// Only emit openGraph / twitter when the page actually carries
// per-page values. If we always emitted an object, Next's metadata
Expand Down
4 changes: 2 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,11 @@
"private": true,
"scripts": {
"dev": "next dev",
"prebuild": "node utils/fetch-github-stars.mjs && node utils/generate-changelog-rss.mjs && node utils/generate-llms-full.mjs",
"prebuild": "node utils/generate-md-twins.mjs && node utils/generate-openapi.mjs && node utils/fetch-github-stars.mjs && node utils/generate-changelog-rss.mjs && node utils/generate-llms-full.mjs",
"build": "next build",
"start": "next start",
"lint": "next lint",
"refresh-data": "node utils/fetch-releases.mjs && node utils/fetch-roadmap.mjs && node utils/fetch-team.mjs && node utils/fetch-github-stars.mjs && node utils/generate-doc-mtimes.mjs && node utils/generate-changelog-rss.mjs && node utils/generate-llms-full.mjs"
"refresh-data": "node utils/fetch-releases.mjs && node utils/fetch-roadmap.mjs && node utils/fetch-team.mjs && node utils/fetch-github-stars.mjs && node utils/generate-doc-mtimes.mjs && node utils/generate-changelog-rss.mjs && node utils/generate-llms-full.mjs && node utils/generate-md-twins.mjs && node utils/generate-openapi.mjs"
},
"browserslist": "defaults, not ie <= 11",
"dependencies": {
Expand Down
61 changes: 61 additions & 0 deletions public/.well-known/agent-card.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
{
"protocolVersion": "0.3.0",
"name": "GoFr Documentation Agent",
"description": "Answers questions about the GoFr Go framework and returns its documentation as Markdown: quick-start, datasource integrations, observability, gRPC/GraphQL/WebSockets/Pub-Sub, deployment, and migration guides from other frameworks.",
"version": "1.0.0",
"url": "https://gofr.dev",
"preferredTransport": "HTTP+JSON",
"provider": {
"organization": "GoFr",
"url": "https://gofr.dev"
},
"documentationUrl": "https://gofr.dev/docs",
"iconUrl": "https://gofr.dev/img/gofr-logo.png",
"capabilities": {
"streaming": false,
"pushNotifications": false,
"stateTransitionHistory": false
},
"defaultInputModes": ["text/plain"],
"defaultOutputModes": ["text/markdown"],
"securitySchemes": {},
"security": [],
"skills": [
{
"id": "fetch-doc-page",
"name": "Fetch a documentation page as Markdown",
"description": "Retrieve any gofr.dev page as clean Markdown by appending .md to its URL or sending Accept: text/markdown. Use when you need the exact wording of a GoFr guide rather than a summary.",
"tags": ["documentation", "markdown", "golang", "gofr"],
"examples": [
"Fetch https://gofr.dev/docs/quick-start/introduction.md",
"Get the GoFr gRPC guide as Markdown"
],
"inputModes": ["text/plain"],
"outputModes": ["text/markdown"]
},
{
"id": "browse-section-index",
"name": "Browse a documentation section",
"description": "List every page in one documentation section (quick-start, advanced-guide, datasources, guides, references) with titles and descriptions, via /docs/{section}/llms.txt.",
"tags": ["documentation", "index", "gofr"],
"examples": [
"What datasources does GoFr support?",
"List the GoFr advanced guide pages"
],
"inputModes": ["text/plain"],
"outputModes": ["text/markdown"]
},
{
"id": "generate-gofr-code",
"name": "Generate GoFr application code",
"description": "Use https://gofr.dev/AGENTS.md as grounding to write idiomatic GoFr handlers, datasource wiring, middleware, and migrations that match framework conventions.",
"tags": ["codegen", "golang", "microservices", "gofr"],
"examples": [
"Write a GoFr REST handler backed by Postgres",
"Migrate this Gin handler to GoFr"
],
"inputModes": ["text/plain"],
"outputModes": ["text/plain"]
}
]
}
29 changes: 29 additions & 0 deletions public/.well-known/agent-skills/index.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
{
"version": "1.0",
"name": "GoFr",
"description": "Agent skills for building and maintaining Go microservices with the GoFr framework.",
"homepage": "https://gofr.dev",
"skills": [
{
"name": "gofr-rest-api",
"description": "Build a production GoFr REST API: gofr.New(), route registration, request binding, typed errors, and AddRESTHandlers for zero-boilerplate CRUD.",
"source": "https://github.com/gofr-dev/gofr/tree/HEAD/skills/gofr-rest-api",
"documentation": "https://gofr.dev/docs/quick-start/introduction.md",
"tags": ["golang", "rest", "microservices"]
},
{
"name": "gofr-datasources",
"description": "Connect a GoFr service to a datasource — Postgres, MySQL, Redis, MongoDB, Cassandra, ClickHouse, Elasticsearch, and 10+ others — with health checks and tracing wired in.",
"source": "https://github.com/gofr-dev/gofr/tree/HEAD/skills/gofr-datasources",
"documentation": "https://gofr.dev/docs/datasources/llms.txt",
"tags": ["golang", "database", "redis", "mongodb"]
},
{
"name": "gofr-observability",
"description": "Instrument a GoFr service: structured logs, Prometheus metrics, custom OpenTelemetry spans, health endpoints, and remote log-level changes.",
"source": "https://github.com/gofr-dev/gofr/tree/HEAD/skills/gofr-observability",
"documentation": "https://gofr.dev/docs/quick-start/observability.md",
"tags": ["golang", "opentelemetry", "prometheus", "observability"]
}
]
}
40 changes: 40 additions & 0 deletions public/.well-known/api-catalog
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
{
"linkset": [
{
"anchor": "https://gofr.dev",
"service-desc": [
{
"href": "https://gofr.dev/openapi.json",
"type": "application/vnd.oai.openapi+json;version=3.1",
"title": "GoFr Documentation Content API"
}
],
"service-doc": [
{
"href": "https://gofr.dev/docs",
"type": "text/html",
"title": "GoFr documentation"
},
{
"href": "https://gofr.dev/llms.txt",
"type": "text/markdown",
"title": "LLM index"
}
],
"service-meta": [
{
"href": "https://gofr.dev/.well-known/oauth-protected-resource",
"type": "application/json",
"title": "Protected resource metadata (RFC 9728)"
}
],
"status": [
{
"href": "https://gofr.dev/changelog",
"type": "text/html",
"title": "Release changelog"
}
]
}
]
}
46 changes: 46 additions & 0 deletions public/.well-known/ard.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
{
"version": "1.0",
"name": "GoFr",
"description": "Documentation and agent resources for GoFr, an opinionated Go framework for production microservices with built-in observability, 15+ datasource integrations, gRPC, GraphQL, WebSockets, Pub/Sub, and cron jobs.",
"homepage": "https://gofr.dev",
"provider": {
"name": "GoFr",
"url": "https://gofr.dev",
"email": "connect@gofr.dev"
},
"resources": [
{
"type": "api",
"name": "GoFr Documentation Content API",
"description": "Read-only HTTP GET access to every documentation page as Markdown, plus site-wide and per-section indexes.",
"specification": "https://gofr.dev/openapi.json",
"specificationFormat": "openapi-3.1",
"authentication": "none"
},
{
"type": "skill",
"name": "GoFr agent primer",
"description": "Framework conventions, datasource patterns, and per-framework migration mappings for AI coding assistants generating GoFr code.",
"url": "https://gofr.dev/AGENTS.md",
"mediaType": "text/markdown"
},
{
"type": "dataset",
"name": "GoFr documentation corpus",
"description": "Every documentation page concatenated into a single Markdown file for long-context ingestion.",
"url": "https://gofr.dev/llms-full.txt",
"mediaType": "text/markdown",
"license": "Apache-2.0"
},
{
"type": "mcp",
"name": "GoFr docs MCP server",
"description": "Model Context Protocol server exposing GoFr documentation search and retrieval as tools. Runs locally over stdio: `go run gofr.dev/mcp/docs-server@latest`.",
"card": "https://gofr.dev/.well-known/mcp/server-card.json"
}
],
"authentication": {
"required": false,
"description": "All resources are public and unauthenticated. See https://gofr.dev/auth.md."
}
}
40 changes: 40 additions & 0 deletions public/.well-known/mcp/server-card.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
{
"name": "gofr-docs",
"description": "Search and retrieve GoFr framework documentation. Use it to answer questions about building Go microservices with GoFr, connecting datasources, observability, gRPC/GraphQL/WebSockets/Pub-Sub, deployment, and migrating from other frameworks.",
"version": "1.0.0",
"serverUrl": "stdio://go run gofr.dev/mcp/docs-server@latest",
"transport": "stdio",
"homepage": "https://gofr.dev",
"repository": "https://github.com/gofr-dev/gofr/tree/HEAD/mcp/docs-server",
"authentication": { "type": "none" },
"tools": [
{
"name": "search_docs",
"description": "Full-text search across all GoFr documentation. Returns matching pages with titles, URLs, and excerpts.",
"inputSchema": {
"type": "object",
"properties": {
"query": { "type": "string", "description": "Search terms, e.g. 'kafka consumer' or 'custom metrics'." },
"limit": { "type": "integer", "description": "Maximum results to return.", "default": 10 }
},
"required": ["query"]
}
},
{
"name": "get_doc",
"description": "Fetch one GoFr documentation page as Markdown by its site path.",
"inputSchema": {
"type": "object",
"properties": {
"path": { "type": "string", "description": "Site path, e.g. '/docs/quick-start/introduction'." }
},
"required": ["path"]
}
},
{
"name": "list_sections",
"description": "List the GoFr documentation sections and how many pages each contains.",
"inputSchema": { "type": "object", "properties": {} }
}
]
}
14 changes: 14 additions & 0 deletions public/.well-known/oauth-protected-resource
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"resource": "https://gofr.dev",
"resource_name": "GoFr Documentation Content API",
"resource_documentation": "https://gofr.dev/openapi.json",
"resource_policy_uri": "https://gofr.dev/privacy",
"authorization_servers": [],
"scopes_supported": [],
"bearer_methods_supported": [],
"agent_auth": {
"identity_endpoint": "https://gofr.dev/agent/identity",
"identity_types_supported": ["anonymous"],
"skill": "https://gofr.dev/auth.md"
}
}
31 changes: 31 additions & 0 deletions public/_headers
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# Static response headers, applied by zopdev/static-server (Netlify /
# Cloudflare Pages `_headers` convention).
#
# Patterns here are literal paths or a trailing `/*` — there is no
# per-request variable, so anything that depends on the specific URL
# (e.g. a per-page markdown alternate) is emitted as a <link> in the
# page <head> instead. See next.config.mjs.

/*
X-Content-Type-Options: nosniff
Referrer-Policy: strict-origin-when-cross-origin
Link: </sitemap.xml>; rel="sitemap", </openapi.json>; rel="service-desc", </.well-known/api-catalog>; rel="api-catalog", </llms.txt>; rel="alternate"; type="text/plain"

# RFC 9727 requires this exact media type for an API catalog; without
# it a client cannot tell a linkset from an arbitrary JSON document.
/.well-known/api-catalog
Content-Type: application/linkset+json;profile="https://www.rfc-editor.org/info/rfc9727"

# A directly-requested twin (/docs/x.md, rather than Accept-negotiated)
# is served by Go's http.ServeFile, whose MIME table has no .md entry —
# it lands as text/plain on a base image without /etc/mime.types.
# Agents check the media type before parsing, so state it here.
/*.md
Content-Type: text/markdown; charset=utf-8

# Extensionless files: static-server would otherwise sniff these as
# text/plain.
/.well-known/oauth-protected-resource
Content-Type: application/json
/agent/identity
Content-Type: application/json
8 changes: 8 additions & 0 deletions public/agent/identity
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"identity_type": "anonymous",
"resource": "https://gofr.dev",
"authentication_required": false,
"message": "gofr.dev serves public, read-only documentation. No registration, credential, or access token is required or issued. Send unauthenticated GET requests; use Accept: text/markdown, or append .md to any page URL, to receive Markdown.",
"documentation": "https://gofr.dev/auth.md",
"rate_limit": "No published rate limit. Prefer https://gofr.dev/llms-full.txt over crawling page-by-page."
}
Loading
Loading