-
Notifications
You must be signed in to change notification settings - Fork 112
docs: add LLMs.txt and Changelog section #645
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
🦋 Changeset detectedLatest commit: 73fc502 The changes in this PR will be included in the next version bump. This PR includes changesets to release 1 package
Not sure what this means? Click here to learn what changesets are. Click here if you're a maintainer who wants to add another changeset to this PR |
Deploying with
|
| Status | Name | Latest Commit | Preview URL | Updated (UTC) |
|---|---|---|---|---|
| ✅ Deployment successful! View logs |
stackflow-docs | 73fc502 | Commit Preview URL | Nov 25 2025, 03:46 AM |
|
Warning Rate limit exceeded@orionmiz has exceeded the limit for the number of commits or files that can be reviewed per hour. Please wait 16 minutes and 14 seconds before requesting another review. ⌛ How to resolve this issue?After the wait time has elapsed, a review can be triggered using the We recommend that you space out your commits to avoid hitting the rate limit. 🚦 How do rate limits work?CodeRabbit enforces hourly rate limits for each developer per organization. Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout. Please see our FAQ for further information. 📒 Files selected for processing (1)
📝 WalkthroughSummary by CodeRabbit
✏️ Tip: You can customize this high-level summary in your review settings. WalkthroughAdds AI-integration docs and changelog pages, new scripts/utilities to generate LLMs.txt and changelog content, updates docs build scripts and dependencies, updates gitignore, and introduces a large Yarn PnP runtime patch that implements a virtual ZIP-backed filesystem and module resolution overlay. Changes
Sequence Diagram(s)sequenceDiagram
participant CLI as build / scripts
participant Gen as generate-llms-txt.ts
participant Pages as docs pages
participant FS as public dir (fs)
CLI->>Gen: run generate:llms
Gen->>Pages: getAllPages()
Pages-->>Gen: list of Page objects (frontmatter + content)
Gen->>FS: write llms-full.txt, llms-changelog.txt, llms.txt
FS-->>CLI: files created
sequenceDiagram
autonumber
participant Node as Node.js loader
participant PnP as .pnp.cjs resolver
participant VFS as VirtualFS/ZipFS
participant NativeFS as native fs
Node->>PnP: module request (require/import)
PnP->>VFS: try resolve via virtual ZIP overlay
alt Found in virtual ZIP
VFS-->>PnP: resolved virtual path / buffer
PnP->>Node: load module from virtual buffer
else Not found in virtual
PnP->>NativeFS: fallback resolution
NativeFS-->>PnP: resolved native path
PnP->>Node: load module from native path
end
Estimated code review effort🎯 4 (Complex) | ⏱️ ~60 minutes
Pre-merge checks and finishing touches❌ Failed checks (1 warning, 1 inconclusive)
✅ Passed checks (1 passed)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 5
🧹 Nitpick comments (12)
docs/pages/docs/get-started/ai-integration.ko.mdx (2)
1-3: Add a short description to frontmatter for SEO/social cards.--- title: AI 통합 +description: LLMs.txt, llms-full.txt, llms-changelog.txt를 통해 Stackflow 문서를 LLM에 제공하고 AI 도구에서 활용하는 방법을 소개합니다. ---
15-17: Use relative URLs to work on preview/local environments.
Absolute links lock to production. Relative paths keep docs portable.-- [llms.txt](https://stackflow.so/api/llms.txt): LLMs.txt 파일들의 구조를 제공하는 메인 파일입니다. -- [llms-full.txt](https://stackflow.so/api/llms-full.txt): Stackflow의 모든 문서를 포함합니다. -- [llms-changelog.txt](https://stackflow.so/api/llms-changelog.txt): 최신 업데이트와 변경사항을 포함하여 버전별 변경 내역을 확인할 수 있습니다. +- [llms.txt](/api/llms.txt): LLMs.txt 파일들의 구조를 제공하는 메인 파일입니다. +- [llms-full.txt](/api/llms-full.txt): Stackflow의 모든 문서를 포함합니다. +- [llms-changelog.txt](/api/llms-changelog.txt): 최신 업데이트와 변경사항을 포함하여 버전별 변경 내역을 확인할 수 있습니다.docs/pages/docs/get-started/ai-integration.en.mdx (2)
1-3: Add a concise description to frontmatter.--- title: AI Integration +description: Introduces LLMs.txt, llms-full.txt, and llms-changelog.txt and how to use them with AI tools like Cursor. ---
15-17: Prefer relative URLs for portability across preview/local.-- [llms.txt](https://stackflow.so/api/llms.txt): The main file that describes the structure of all LLMs.txt files. -- [llms-full.txt](https://stackflow.so/api/llms-full.txt): Includes all Stackflow documentation. -- [llms-changelog.txt](https://stackflow.so/api/llms-changelog.txt): Contains the latest updates and changes so you can review version-by-version history. +- [llms.txt](/api/llms.txt): The main file that describes the structure of all LLMs.txt files. +- [llms-full.txt](/api/llms-full.txt): Includes all Stackflow documentation. +- [llms-changelog.txt](/api/llms-changelog.txt): Contains the latest updates and changes so you can review version-by-version history.docs/pages/api/llms-full.txt.ts (2)
8-14: Tighten handler: remove unnecessary await, add try/catch, charset, and caching.
Current code awaits a sync function, lacks error handling, and omits charset/cache headers.-import type { NextApiRequest, NextApiResponse } from "next"; -import { getAllPages } from "../../utils/get-all-pages"; +import type { NextApiRequest, NextApiResponse } from "next"; +import { getAllPages } from "../../utils/get-all-pages"; -export default async function handler( - req: NextApiRequest, - res: NextApiResponse, -) { - const pages = await getAllPages(); - const content = pages - .map((page) => `# ${page.title}\n\n${page.content}`) - .join("\n\n"); - - res.setHeader("Content-Type", "text/plain"); - res.status(200).send(content); -} +export default async function handler( + _req: NextApiRequest, + res: NextApiResponse, +) { + try { + const pages = getAllPages(); + const content = pages + .map((page) => `# ${page.title || page.path}\n\n${page.content}`) + .join("\n\n"); + + res.setHeader("Content-Type", "text/plain; charset=utf-8"); + // Cache for 1 day at the edge; allow 1 day stale-while-revalidate + res.setHeader("Cache-Control", "public, s-maxage=86400, stale-while-revalidate=86400"); + res.status(200).send(content); + } catch (error) { + console.error("LLMs full generation error:", error); + res.status(500).send("Error generating LLMs full document"); + } +}
10-11: Optional: convert MDX to plain text for consistency with llms-changelog.
If desired, process MD/MDX into plain text like the changelog route to reduce markup noise. Based on the referenced pattern in docs/pages/api/llms-changelog.txt.ts.+// import { processContent } from "../../utils/process-content"; - const content = pages - .map((page) => `# ${page.title || page.path}\n\n${page.content}`) - .join("\n\n"); + const parts = await Promise.all( + pages.map(async (page) => { + const body = await processContent(page.content); + return `# ${page.title || page.path}\n\n${body}`; + }), + ); + const content = parts.join("\n\n");docs/utils/constants.ts (1)
1-4: Port 6006 confirmed. Consider deriving base URL from request for better preview/staging support.
- Verified: docs/package.json has
"dev": "next -p 6006"— port is correct.- The baseUrl constant is used in
docs/pages/api/llms.txt.ts(an API handler with access toreq), making request-scoped derivation feasible and beneficial. Current static constant works but won't adapt if deployed to preview/staging URLs.- Fallback scheme is correct (
https://stackflow.so); no issues with env setup.Optional improvement:
// docs/utils/url.ts import type { NextApiRequest } from "next"; export function absoluteUrlFromReq(req: NextApiRequest): URL { const proto = (req.headers["x-forwarded-proto"] as string) || "https"; const host = (req.headers["x-forwarded-host"] as string) || (req.headers.host as string) || "localhost:6006"; return new URL(`${proto}://${host}`); }Then call
absoluteUrlFromReq(req)in the handler instead of the static constant to handle preview/staging environments correctly.docs/pages/api/llms.txt.ts (1)
4-6: Set UTF-8 and tidy unused param
- Add charset to Content-Type for safer text decoding.
- req is unused; prefix with underscore to satisfy noUnusedParameters.
-export default function handler(req: NextApiRequest, res: NextApiResponse) { - res.setHeader("Content-Type", "text/plain"); +export default function handler(_req: NextApiRequest, res: NextApiResponse) { + res.setHeader("Content-Type", "text/plain; charset=utf-8");docs/utils/get-all-pages.ts (1)
5-11: Tighten types for frontmatterUse unknown instead of any to preserve strictness and force narrowing at use-sites.
- data: Record<string, any>; + data: Record<string, unknown>;docs/pages/api/llms-changelog.txt.ts (2)
21-26: Remove unused frontmatter data or use itdata is parsed but unused. Drop it or surface metadata in the response header.
- const { data, content } = matter(fileContent); + const { content } = matter(fileContent);
9-13: Method guard and basic caching (optional)Restrict to GET and add a modest cache to reduce cold starts.
export default async function handler( req: NextApiRequest, res: NextApiResponse, ) { + if (req.method !== "GET") { + res.setHeader("Allow", "GET"); + return res.status(405).end("Method Not Allowed"); + } @@ - res.setHeader("Content-Type", "text/plain; charset=utf-8"); + res.setHeader("Content-Type", "text/plain; charset=utf-8"); + res.setHeader("Cache-Control", "public, max-age=0, s-maxage=3600, stale-while-revalidate=86400");Also applies to: 31-36
scripts/generate-changelog.ts (1)
56-59: Escape user-controlled parts of regex (correctness and ReDoS hygiene)date includes dots and optional suffix; escape it before constructing the regex.
- const dateRegex = new RegExp(`## ${date}(?: #\\d+)?`, "g"); + const escaped = date.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"); + const dateRegex = new RegExp(`## ${escaped}(?: #\\d+)?`, "g");
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Jira integration is disabled by default for public repositories
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
⛔ Files ignored due to path filters (43)
.yarn/cache/@changesets-assemble-release-plan-npm-6.0.9-e01af97ef4-f84656eabb.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@changesets-git-npm-3.0.4-c1d351b2f6-4f5a1f3354.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@changesets-read-npm-0.6.5-fc55502eb7-fec0ac2880.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-find-and-replace-npm-3.0.2-700884f061-446561aa95.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-from-markdown-npm-2.0.2-b327f875e3-69b207913f.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-autolink-literal-npm-2.0.1-dd870d9308-d933b42feb.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-footnote-npm-2.1.0-d8da32ba7c-5fac0f64d1.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-npm-3.1.0-933de2cdb5-d66809a070.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-strikethrough-npm-2.0.0-d16d95c318-b1abc137d7.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-table-npm-2.0.0-45a74f064b-a043d60d72.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-task-list-item-npm-2.0.0-cb1270a10f-679a3ff09b.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-phrasing-npm-4.1.0-30939ebbcd-3a97533e8a.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-to-markdown-npm-2.1.2-40d984eac3-ab494a32f1.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-to-string-npm-4.0.0-fc8d9714a5-f4a5dbb9ea.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-core-commonmark-npm-2.0.3-5e317c62b2-2b98b9eba1.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-autolink-literal-npm-2.1.0-8fcb271412-933b9b96ca.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-footnote-npm-2.1.0-1cf783dd36-7e019414e3.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-npm-3.0.0-d154ab531f-8493d10417.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-strikethrough-npm-2.1.0-b2aa188eba-eaf2c7b1e3.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-table-npm-2.1.1-7b9f4422c9-0391ead408.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-tagfilter-npm-2.0.0-c5ad486636-c5e3f8cdf2.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-task-list-item-npm-2.1.0-b717607894-c5f72929f0.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-destination-npm-2.0.1-2b4ab89121-9c4baa9ca2.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-label-npm-2.0.1-2ce9fdcfd2-bd03f5a75f.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-space-npm-2.0.1-36b4717310-1bd68a017c.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-title-npm-2.0.1-a5f7a4ac37-b4d2e4850a.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-whitespace-npm-2.0.1-2d7cfaf8ae-67b3944d01.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-npm-4.0.2-99b2e4c11c-1b85e49c8f.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-chunked-npm-2.0.1-27444b1e7b-f8cb2a67bc.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-classify-character-npm-2.0.1-127a4a9c2a-4d8bbe3a6d.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-combine-extensions-npm-2.0.1-9810c0bf8d-5d22fb9ee3.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-decode-numeric-character-reference-npm-2.0.2-c2d481632e-ee11c8bde5.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-decode-string-npm-2.0.1-72716f39ea-2f517e4c61.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-html-tag-name-npm-2.0.1-eb560993c8-dea365f5ad.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-normalize-identifier-npm-2.0.1-336335e80e-1eb9a289d7.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-resolve-all-npm-2.0.1-50f997ec4c-9275f3ddb6.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-subtokenize-npm-2.1.0-2452c9ae9b-5f18c70cb9.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/remark-gfm-npm-4.0.1-f55aaba8ef-86899862cf.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/remark-npm-15.0.1-0f67091876-671eae3a44.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/remark-parse-npm-11.0.0-6484fba69e-59d584be56.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/remark-stringify-npm-11.0.0-b41a557b8d-32b2f6093b.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/unified-npm-11.0.5-ac5333017e-d9e6e88900.zipis excluded by!**/.yarn/**,!**/*.zipyarn.lockis excluded by!**/yarn.lock,!**/*.lock
📒 Files selected for processing (19)
.changeset/chatty-breads-watch.md(1 hunks).pnp.cjs(46 hunks)docs/package.json(1 hunks)docs/pages/api/llms-changelog.txt.ts(1 hunks)docs/pages/api/llms-full.txt.ts(1 hunks)docs/pages/api/llms.txt.ts(1 hunks)docs/pages/docs/_meta.en.json(1 hunks)docs/pages/docs/_meta.ko.json(1 hunks)docs/pages/docs/changelog.en.mdx(1 hunks)docs/pages/docs/changelog.ko.mdx(1 hunks)docs/pages/docs/get-started/_meta.en.json(1 hunks)docs/pages/docs/get-started/_meta.ko.json(1 hunks)docs/pages/docs/get-started/ai-integration.en.mdx(1 hunks)docs/pages/docs/get-started/ai-integration.ko.mdx(1 hunks)docs/tsconfig.json(1 hunks)docs/utils/constants.ts(1 hunks)docs/utils/get-all-pages.ts(1 hunks)package.json(2 hunks)scripts/generate-changelog.ts(1 hunks)
🧰 Additional context used
📓 Path-based instructions (2)
.changeset/*.md
📄 CodeRabbit inference engine (AGENTS.md)
Include a Changeset entry for any user-facing package change
Files:
.changeset/chatty-breads-watch.md
**/*.{ts,tsx}
📄 CodeRabbit inference engine (AGENTS.md)
Write source in TypeScript with strict typing enabled across the codebase
Files:
docs/pages/api/llms-full.txt.tsdocs/pages/api/llms.txt.tsdocs/utils/constants.tsdocs/pages/api/llms-changelog.txt.tsscripts/generate-changelog.tsdocs/utils/get-all-pages.ts
🧬 Code graph analysis (4)
docs/pages/api/llms-full.txt.ts (3)
docs/pages/api/llms-changelog.txt.ts (1)
handler(9-37)docs/pages/api/llms.txt.ts (1)
handler(4-14)docs/utils/get-all-pages.ts (1)
getAllPages(13-39)
docs/pages/api/llms.txt.ts (3)
docs/pages/api/llms-changelog.txt.ts (1)
handler(9-37)docs/pages/api/llms-full.txt.ts (1)
handler(4-15)docs/utils/constants.ts (1)
baseUrl(1-4)
docs/utils/constants.ts (1)
.pnp.cjs (1)
URL(21065-21065)
docs/pages/api/llms-changelog.txt.ts (2)
docs/pages/api/llms-full.txt.ts (1)
handler(4-15)docs/pages/api/llms.txt.ts (1)
handler(4-14)
🪛 ast-grep (0.39.6)
scripts/generate-changelog.ts
[warning] 55-55: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(## ${date}(?: #\\d+)?, "g")
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html
(regexp-from-variable)
🪛 LanguageTool
docs/pages/docs/get-started/ai-integration.ko.mdx
[grammar] ~7-~7: El plural de les sigles no es marca gràficament.
Context: --- title: AI 통합 --- # AI 통합 ## LLMs.txt 대규모 언어 모델(LLM)이 Stackflow를 쉽게 이해할 ...
(SIGLES)
[grammar] ~9-~9: El plural de les sigles no es marca gràficament.
Context: ...대규모 언어 모델(LLM)이 Stackflow를 쉽게 이해할 수 있도록 LLMs.txt를 제공합니다. ### 구조 다음과 같은 LLMs.txt 파일...
(SIGLES)
[grammar] ~13-~13: El plural de les sigles no es marca gràficament.
Context: ... 수 있도록 LLMs.txt를 제공합니다. ### 구조 다음과 같은 LLMs.txt 파일들을 제공합니다: - [llms.txt](https://s...
(SIGLES)
[typographical] ~15-~15: Símbol sense parella: sembla que falta «[».
Context: ...다음과 같은 LLMs.txt 파일들을 제공합니다: - llms.txt: LLM...
(UNPAIRED_BRACKETS)
[grammar] ~15-~15: El plural de les sigles no es marca gràficament.
Context: ...xt](https://stackflow.so/api/llms.txt): LLMs.txt 파일들의 구조를 제공하는 메인 파일입니다. - [llms-ful...
(SIGLES)
[typographical] ~16-~16: Símbol sense parella: sembla que falta «[».
Context: ...파일들의 구조를 제공하는 메인 파일입니다. - llms-full.txt...
(UNPAIRED_BRACKETS)
[typographical] ~17-~17: Símbol sense parella: sembla que falta «[».
Context: ...low의 모든 문서를 포함합니다. - [llms-changelog.txt](https://stackflow.so/api/llms-changelog...
(UNPAIRED_BRACKETS)
[grammar] ~21-~21: El plural de les sigles no es marca gràficament.
Context: ...### Cursor Cursor의 @docs 기능을 사용하여 프로젝트에 LLMs.txt 파일을 포함할 수 있습니다. [**Cursor @docs에 대...
(SIGLES)
[typographical] ~23-~23: Símbol sense parella: sembla que falta «[».
Context: ...함할 수 있습니다. [Cursor @docs에 대해 자세히 알아보기](https://docs.cursor.com/context/@-symbo...
(UNPAIRED_BRACKETS)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (2)
- GitHub Check: Workers Builds: stackflow-docs
- GitHub Check: Cloudflare Pages
🔇 Additional comments (12)
.pnp.cjs (1)
118-130: This is an auto-generated file; review should focus on source files instead.The
.pnp.cjsfile is Yarn's auto-generated Plug'n'Play manifest and should not be manually reviewed for code quality. The changes reflect dependency tree updates from modifications topackage.json.The added dependencies align with the PR objectives (changesets for changelog generation, remark/mdast for markdown processing, gray-matter for frontmatter parsing), but to properly review this PR, we need to examine:
package.jsonchanges and dependency version rationale- New/modified source files for LLMs.txt and Changelog feature implementation
- Build system updates (as mentioned in the AI summary)
- Documentation pages and utility functions for reading docs
Please provide the source files that directly implement the LLMs.txt and Changelog functionality, along with the
package.jsonmodifications.Also applies to: 2539-2766, 6192-6209, 6285-6297, 12790-13074, 13121-13157, 13282-13390, 13400-13545, 13647-13970, 14008-14021, 15932-16055, 17425-17442
.changeset/chatty-breads-watch.md (1)
1-5: Changeset entry follows correct structure.The changeset correctly documents the minor release for @stackflow/docs with an appropriate description of the user-facing changes.
docs/tsconfig.json (1)
1-28: TypeScript configuration looks good.The tsconfig.json follows standard Next.js/React patterns with appropriate settings for a TypeScript documentation site.
docs/pages/docs/get-started/_meta.en.json (1)
1-9: Metadata entry for AI integration documentation is properly added.The new navigation entry follows the existing pattern and maintains valid JSON structure.
package.json (2)
22-28: Ensure generate-changelog script is integrated correctly.The
changeset:versionscript now depends ongenerate:changelogrunning successfully. Any failure in changelog generation will block the release process.Verify that:
scripts/generate-changelog.tsexists and implements the changelog generation logic- The script runs without errors:
yarn generate:changelog- Output is correctly written to
docs/pages/docs/changelog.en.mdx(and.ko.mdxif applicable)
37-43: New changesets dependencies are well-scoped.The added @changesets packages support the automated changelog generation workflow and appear appropriately versioned.
docs/pages/docs/_meta.ko.json (1)
1-5: Korean metadata changelog entry is correctly added.The translation "변경 이력" (Changelog) is appropriate and the JSON structure is valid.
docs/pages/docs/_meta.en.json (1)
1-5: English metadata changelog entry is correctly added.The navigation entry properly introduces the Changelog section to the documentation structure.
docs/pages/docs/changelog.ko.mdx (1)
1-1: The file structure is valid, but the review comment misdiagnosed the issue.The
changelog.ko.mdxfile is a symbolic link pointing tochangelog.en.mdx, not a file containing only the string "changelog.en.mdx". The actual MDX content is valid with proper frontmatter and structure.However, there is a legitimate localization concern: Korean users receive English-language changelog content (title: "Changelog", entries in English) instead of Korean translations. For proper i18n support, the Korean changelog should contain Korean translations rather than linking to the English version.
Likely an incorrect or invalid review comment.
docs/pages/docs/get-started/_meta.ko.json (1)
7-8: LGTM.
Key "ai-integration" matches the new page slug; JSON is valid.docs/package.json (1)
7-15: generate:changelog script already wired in root package.jsonVerification confirms the
generate:changelogscript has been successfully added to the root package.json (line 7). The original concern has been addressed—the generator is now invokable via npm.docs/utils/get-all-pages.ts (1)
1-2: Review comment is based on incorrect premise; however, a separate async/await inconsistency exists.The project is properly configured for Cloudflare Workers deployment: wrangler.jsonc has
compatibility_date: "2025-04-23"andcompatibility_flags: ["nodejs_compat"]. With nodejs_compat enabled, synchronous Node.js fs APIs like readFileSync are available on Cloudflare Workers. The getAllPages() utility's use offs.readFileSync,fs.readdirSync, andfs.statSyncwill function correctly with this configuration.However, fix the async/await inconsistency:
getAllPages()is not an async function but is awaited in the API handler atdocs/pages/api/llms-full.txt.ts:8. Either make the function async or remove the await.Likely an incorrect or invalid review comment.
docs/pages/api/llms-changelog.txt.ts
Outdated
| import fs from "node:fs"; | ||
| import path from "node:path"; | ||
| import matter from "gray-matter"; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧩 Analysis chain
API route will break on Cloudflare Workers (fs/path at runtime)
This route reads the MDX file with fs at request-time. Cloudflare Workers don’t support Node fs/path; the endpoint will 500 in production unless deployed on a Node runtime. Options:
- Build-time: generate a plain-text artifact (or JSON) and import/serve it.
- Static asset: emit the MDX-processed text to public/ and stream it.
- If unavoidable, pin this route to a Node runtime and exclude from Worker deploys.
Also applies to: 15-20
---
🏁 Script executed:
```shell
#!/bin/bash
# View the complete file to understand how fs/path are used
cat docs/pages/api/llms-changelog.txt.ts
Length of output: 1263
🏁 Script executed:
#!/bin/bash
# Check if there's a build configuration or deployment config that clarifies the target
fd -t f "(vercel|next|wrangler|cloudflare|deploy)" --type f | head -20Length of output: 140
🏁 Script executed:
#!/bin/bash
# Search for usage of fs or path in the file to understand runtime vs build-time usage
rg -n "fs\.|path\." docs/pages/api/llms-changelog.txt.tsLength of output: 107
🌐 Web query:
Cloudflare Workers Node.js fs module support runtime
💡 Result:
Short answer: Cloudflare Workers now implements a Node.js-compatible virtual file system exposed via the node:fs module. It's available in Node.js compatibility mode (set compatibility flag nodejs_compat) and is enabled by default for Workers with a compatibility_date of 2025-09-01 or later (it can also be enabled/disabled with the enable_nodejs_fs_module / disable_nodejs_fs_module flags). [1][2]
Key points:
- How to enable: set compatibility_date ≥ 2025-09-01 and add compatibility_flags: ["nodejs_compat"] (or enable the fs flag on earlier dates). [1][2]
- Usage: import using the node: prefix, e.g. import { readFileSync } from "node:fs". [1][2]
- Behavior: the fs is a per-request in-memory virtual file system (ephemeral — not persisted across requests). [1][2]
- Limits & known restrictions: max file size 128 MB, path length and segment limits, timestamps currently always the Unix epoch, no fs.watch/fs.watchFile, some glob and force options not implemented, file permissions/ownership not supported; temporary files count against Worker memory. [1]
- Rationale: implemented natively in the Workers runtime as part of Cloudflare’s Node.js compatibility improvements. [3]
Sources:
[1] Cloudflare Workers docs — fs / Node.js fs info.
[2] Cloudflare changelog post (Aug 15, 2025) announcing node:fs in Workers.
[3] Cloudflare blog post on Node.js compatibility in Workers.
---
🏁 Script executed:
```shell
#!/bin/bash
# Check wrangler config to understand deployment strategy
cat docs/wrangler.jsonc
Length of output: 650
🏁 Script executed:
#!/bin/bash
# Search for changelog-related build or static asset generation
rg -i "changelog" docs/ --type ts --type js --type mjs --type json -B2 -A2Length of output: 27
🏁 Script executed:
#!/bin/bash
# Check if pages/docs/changelog.en.mdx exists and if there's build processing
fd -t f "changelog" docs/Length of output: 87
API route breaks on Cloudflare Workers with current deployment config (fs/path not available)
The route uses fs.readFileSync() at request-time (line 19), but wrangler.jsonc specifies compatibility_date: "2025-04-23", which does not support Node.js fs/path modules. The endpoint will error in production.
Even if upgraded to compatibility_date: "2025-09-01" or later (when nodejs_compat fs became available), the fs module in Workers is an ephemeral per-request virtual filesystem — not disk I/O — so this pattern remains incompatible.
Recommendations:
- Generate the changelog at build-time and import/serve as static content
- Emit processed output to
public/and serve via static asset - If this route must remain dynamic, pin it to a Node.js runtime and exclude from Cloudflare Workers deployment
🤖 Prompt for AI Agents
In docs/pages/api/llms-changelog.txt.ts around lines 1 to 3, the route imports
node fs/path and calls fs.readFileSync at request time which breaks on
Cloudflare Workers (no Node fs/path at the configured compatibility_date and
even newer nodejs_compat is an ephemeral VFS); change the implementation to
produce the changelog at build time and serve static content instead: move file
reading/gray-matter parsing into your build step (or a script) that writes the
processed output into public/ (or generates a module you can import), update
this API route to either import the generated static file or return the static
asset, or alternatively mark this route to run on a Node.js runtime and exclude
it from Workers deployment if it truly must remain dynamic.
package.json
Outdated
| "packages/*", | ||
| "extensions/*" | ||
| ], | ||
| "type": "module", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🧩 Analysis chain
Verify ESM compatibility across the monorepo before merging.
Adding "type": "module" converts the entire monorepo to ES modules, which is a breaking change. Ensure all workspaces, build scripts, and dependencies properly support ESM before merging.
🏁 Script executed:
#!/bin/bash
# Description: Verify generate-changelog.ts exists and check ESM compatibility indicators
# Check if generate-changelog.ts exists
if [ -f scripts/generate-changelog.ts ]; then
echo "✓ scripts/generate-changelog.ts exists"
head -20 scripts/generate-changelog.ts
else
echo "✗ scripts/generate-changelog.ts NOT FOUND"
fi
# Verify the script doesn't use CommonJS requires
if [ -f scripts/generate-changelog.ts ]; then
if grep -q "require(" scripts/generate-changelog.ts; then
echo "⚠ WARNING: Script appears to use CommonJS require() - may not work with type:module"
else
echo "✓ Script appears to use ES imports"
fi
fi
# Check for any .ts config or build files that might conflict
fd -e ts -e mjs -e cjs scripts/ 2>/dev/null | head -10Length of output: 785
🏁 Script executed:
#!/bin/bash
# Description: Verify ESM compatibility across workspaces and build configuration
# Check workspace package.json files for type field
echo "=== Checking workspace configurations ==="
fd -e package.json -path '*/packages/*/package.json' | head -20 | while read -r pkg; do
echo "File: $pkg"
grep -E '"type"|"module"' "$pkg" || echo " (no type field)"
done
# Check root tsconfig.json for module settings
echo -e "\n=== Checking TypeScript module configuration ==="
if [ -f tsconfig.json ]; then
echo "Root tsconfig.json:"
grep -A2 -B2 '"module"' tsconfig.json || echo " (no module field)"
else
echo "tsconfig.json not found"
fi
# Look for any build/test scripts that might use CommonJS syntax
echo -e "\n=== Checking for CommonJS patterns in build context ==="
grep -r "require\.resolve\|module\.exports\|CommonJS" . --include="*.ts" --include="*.js" -l 2>/dev/null | grep -E "(build|test|scripts)" | head -10 || echo " (no obvious CommonJS patterns in build scripts)"
# Check if .mocharc or similar test config exists and uses ESM
echo -e "\n=== Checking test configuration ==="
fd -E node_modules '.mocharc*' -o '.babelrc*' -o 'jest.config*' | head -5Length of output: 679
🏁 Script executed:
#!/bin/bash
# Check if there are documented ESM breaking changes or migration notes
echo "=== Checking for ESM migration documentation ==="
fd -e md -e txt -E node_modules | xargs grep -l "ESM\|module.*type\|CommonJS" 2>/dev/null | head -5Length of output: 100
🏁 Script executed:
#!/bin/bash
# Description: Verify ESM compatibility across workspaces and build configuration
# Check workspace package.json files for type field
echo "=== Checking workspace configurations ==="
fd -e package.json -path '*/packages/*/package.json' | head -20 | while read -r pkg; do
echo "File: $pkg"
grep -E '"type"' "$pkg" || echo " (no type field)"
done
# Check root tsconfig.json for module settings
echo -e "\n=== Checking TypeScript module configuration ==="
if [ -f tsconfig.json ]; then
echo "Root tsconfig.json:"
grep -A2 -B2 '"module"' tsconfig.json || echo " (no module field)"
fi
# Check for .mts files or explicit ESM markers
echo -e "\n=== Checking for ESM file extensions in scripts ==="
fd -e mts -o -e mjs scripts/ 2>/dev/null || echo " (no .mts or .mjs files in scripts)"
# Look for common ESM incompatibilities in scripts directory
echo -e "\n=== Checking script files for ESM compatibility ==="
fd -type f scripts/ 2>/dev/null | while read -r script; do
if file "$script" | grep -q "JavaScript"; then
if grep -l "module.exports\|require(" "$script" 2>/dev/null; then
echo "⚠ POTENTIAL ISSUE: $script uses CommonJS"
fi
fi
doneLength of output: 555
🏁 Script executed:
#!/bin/bash
# Description: Check esbuild-config usage and build process compatibility
# Verify how esbuild-config is imported/used
echo "=== Searching for esbuild-config imports ==="
rg -n "esbuild-config" --type ts --type js -B2 -A2 | head -30
# Check package.json to see if esbuild-config is a package or internal config
echo -e "\n=== Checking esbuild-config package structure ==="
if [ -f packages/esbuild-config/package.json ]; then
echo "esbuild-config package.json:"
cat packages/esbuild-config/package.json | head -15
fi
# Check root package.json build scripts more closely
echo -e "\n=== Build and script commands from root package.json ==="
grep -E '"(build|dev|test|prepare|postinstall)"' package.json | head -10Length of output: 2698
🏁 Script executed:
#!/bin/bash
# Description: Verify if esbuild configs have been migrated to ESM or .mjs/.mts
# Check for .mjs or .mts versions of esbuild config files
echo "=== Checking for ESM versions of esbuild config ==="
fd -e mjs -e mts | grep esbuild || echo " (no .mjs or .mts esbuild configs found)"
# Check if any esbuild.config.js files have been converted to import syntax
echo -e "\n=== Checking if any esbuild.config.js use import syntax ==="
fd -name "esbuild.config.js" | while read -r file; do
if head -5 "$file" | grep -q "^import\|^export"; then
echo "✓ ESM: $file"
else
echo "✗ CommonJS: $file"
fi
done
# Check if git shows these files as modified in this PR
echo -e "\n=== Checking git status of esbuild config files ==="
git diff HEAD --name-only 2>/dev/null | grep -i esbuild || echo " (no esbuild files modified in this PR)"Length of output: 479
Migrate esbuild.config.js files to ESM before setting "type": "module".
Adding "type": "module" at the root converts all .js files to ESM. However, multiple esbuild.config.js files throughout the monorepo (extensions/react-ui-core/, extensions/plugin-basic-ui/, extensions/plugin-stack-depth-change/, extensions/plugin-map-initial-activity/, extensions/plugin-history-sync/, extensions/plugin-preload/, and others) still use CommonJS require() syntax. These will fail when parsed as ESM.
Either migrate these build config files to ESM (.mjs or import syntax) or add "type": "commonjs" to their respective package.json files to override the root setting.
🤖 Prompt for AI Agents
In package.json around line 14, adding "type": "module" will make all .js files
ESM and will break existing esbuild.config.js files that still use CommonJS
require() in the listed extension packages (extensions/react-ui-core,
extensions/plugin-basic-ui, extensions/plugin-stack-depth-change,
extensions/plugin-map-initial-activity, extensions/plugin-history-sync,
extensions/plugin-preload, etc.); fix by either (A) migrating each
esbuild.config.js to ESM: rename to .mjs or convert require()/module.exports to
import/export syntax and adjust any synchronous require usage to ESM-compatible
patterns, or (B) add a package.json in each extension folder with "type":
"commonjs" to keep those configs as CommonJS; pick one approach per package and
apply consistently so the root "type": "module" does not break their build
configs.
scripts/generate-changelog.ts
Outdated
| const existingContent = await readFile(changelogPath, "utf-8"); | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion | 🟠 Major
Handle first-run when changelog doesn’t exist
readFile will throw if docs/pages/docs/changelog.en.mdx is missing. Default to empty and start fresh.
- const existingContent = await readFile(changelogPath, "utf-8");
+ let existingContent = "";
+ try {
+ existingContent = await readFile(changelogPath, "utf-8");
+ } catch {
+ console.log("🆕 No existing changelog; starting fresh");
+ }🤖 Prompt for AI Agents
In scripts/generate-changelog.ts around lines 445 to 446, reading the changelog
with readFile will throw if docs/pages/docs/changelog.en.mdx is missing; wrap
the readFile call in a try/catch, on ENOENT set existingContent = "" (start
fresh) and for any other error rethrow it so real failures surface; ensure
subsequent logic uses the default empty string when the file doesn't exist.
0c3cf2b to
2ce34d1
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 4
♻️ Duplicate comments (3)
scripts/generate-changelog.ts (3)
441-452: Handle first‑run when changelog doesn’t exist (EN)readFile will throw if the file is missing.
- const existingContent = await readFile(changelogEnPath, "utf-8"); + let existingContent = ""; + try { + existingContent = await readFile(changelogEnPath, "utf-8"); + } catch (e: any) { + if (e?.code !== "ENOENT") throw e; + console.log("🆕 No existing changelog.en.mdx; starting fresh"); + }
120-168: Don’t cap to 10 and avoid Unix‑only pipeline; derive from release plan IDsThe find|grep|head|cut chain is non‑portable and silently drops after 10 files. Build from releasePlan.changesets IDs and filter “Version Packages” in JS.
-async function getChangesetCommits(): Promise<Record<string, string>> { +async function getChangesetCommits(ids: string[]): Promise<Record<string, string>> { try { - // .changeset 폴더의 .md 파일들 찾기 (README.md 제외) - const files = await execCommand( - "find .changeset -name '*.md' -not -name 'README.md' | head -10", - ); - - if (!files) { - console.log("📝 No changeset files found in .changeset folder"); - - return {}; - } - - const fileList = files.split("\n").filter((file) => file.trim()); - console.log(`📊 Found ${fileList.length} changeset files:`, fileList); - - // 각 파일별로 main 브랜치에 머지된 commit 찾기 + const fileList = ids.map((id) => `.changeset/${id}.md`); + console.log(`📊 Resolving ${fileList.length} changeset files from release plan`); const commitMap: Record<string, string> = {}; - for (const file of fileList) { - // changeset ID 추출 (파일명에서 .md 제거) - const changesetId = file.split("/").pop()?.replace(".md", "") || ""; - - // Version Packages 커밋을 제외하고 main 브랜치에 머지된 커밋 찾기 - const commit = await execCommand( - `git log --oneline --first-parent main -- "${file}" | grep -v "Version Packages" | head -1 | cut -d' ' -f1`, - ); - if (commit) { - // 전체 커밋 해시 가져오기 - const fullCommit = await execCommand(`git rev-parse ${commit}`); - if (fullCommit) { - commitMap[changesetId] = fullCommit; - console.log(` 📄 ${changesetId} → ${fullCommit.slice(0, 7)}`); - } - } - } + for (const id of ids) { + const file = `.changeset/${id}.md`; + // Hash<TAB>Subject on first-parent main for the file + const log = await execCommand( + `git log --first-parent main --pretty=format:%H%x09%s -- "${file}"` + ); + if (!log) continue; + const line = log.split("\n").find((l) => !l.includes("Version Packages")); + if (!line) continue; + const hash = line.split("\t")[0]; + const fullCommit = await execCommand(`git rev-parse ${hash}`); + if (fullCommit) { + commitMap[id] = fullCommit; + console.log(` 📄 ${id} → ${fullCommit.slice(0, 7)}`); + } + }
219-239: Pass changeset IDs to the new helper; keep filtering out “Version Packages” in JSAligns with the portable helper above.
- const commitMap = await getChangesetCommits(); + const commitMap = await getChangesetCommits( + releasePlan.changesets.map((c) => c.id), + );
🧹 Nitpick comments (4)
scripts/generate-changelog.ts (4)
52-59: Anchor the date regex; reduce backtracking riskUse start-of-line anchor and multiline flag; simpler and safer matching.
- const dateRegex = new RegExp(`## ${date}(?: #\\d+)?`, "g"); + const dateRegex = new RegExp(`^## ${date}(?: #\\d+)?$`, "gm");
97-101: Avoid hard‑coding repo; read from env with fallbackHelps forks/CI and local clones.
-function createCommitLink(commitHash: string): string { - const repo = "daangn/stackflow"; +function createCommitLink(commitHash: string): string { + const repo = process.env.GITHUB_REPOSITORY || "daangn/stackflow"; const shortHash = commitHash.slice(0, 7); return `[\`${shortHash}\`](https://github.com/${repo}/commit/${commitHash})`; }
106-114: Harden git exec: set timeout and larger bufferPrevents hanging and buffer overflows on large logs.
- try { - const { stdout } = await execAsync(command); + try { + const { stdout } = await execAsync(command, { + timeout: 30000, + maxBuffer: 10 * 1024 * 1024, + }); return stdout.trim();
287-323: Inject manual content blocks into the markdownPreserve curated notes per date.
for (const entry of sortedEntries) { markdown += `## ${entry.date}\n\n`; + + // Optional manual content block + if (entry.manualContent && entry.manualContent.trim()) { + markdown += `<!-- MANUAL_CONTENT_START -->\n${entry.manualContent}\n<!-- MANUAL_CONTENT_END -->\n\n`; + }
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Jira integration is disabled by default for public repositories
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
📒 Files selected for processing (2)
docs/next.config.mjs(1 hunks)scripts/generate-changelog.ts(1 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx}
📄 CodeRabbit inference engine (AGENTS.md)
Write source in TypeScript with strict typing enabled across the codebase
Files:
scripts/generate-changelog.ts
🪛 ast-grep (0.39.6)
scripts/generate-changelog.ts
[warning] 55-55: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(## ${date}(?: #\\d+)?, "g")
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html
(regexp-from-variable)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
- GitHub Check: Workers Builds: stackflow-docs
| date: dateKey, | ||
| changesets: changesetEntries, | ||
| manualContent: manualContents[dateKey], | ||
| }); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Collected manualContent is never rendered
You store manualContent but generateChangelogMarkdown doesn’t inject it, so it’s dropped.
Add rendering in generateChangelogMarkdown (see suggestion below).
🤖 Prompt for AI Agents
In scripts/generate-changelog.ts around lines 241–244, the collected
manualContent is added to the per-date payload but generateChangelogMarkdown
never uses it, so manual notes are dropped; update generateChangelogMarkdown (or
the template it uses) to accept a manualContent field and render its markdown
for each date entry (preferably immediately after the changesets list for that
date), skipping if empty; ensure the function signature and callers are updated
to pass the manualContent and that the rendered output preserves raw markdown
(no double-escaping) and is included in the final changelog output.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Jira integration is disabled by default for public repositories
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
📒 Files selected for processing (1)
docs/pages/docs/changelog.ko.mdx(1 hunks)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
- GitHub Check: Workers Builds: stackflow-docs
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
🧹 Nitpick comments (4)
docs/scripts/generate-llms-txt.ts (4)
10-19: Consider making file operations async or removingasynckeyword.The function is declared as
asyncbut uses synchronous file operations (writeFileSync). For consistency and better I/O performance, consider using the asyncfs.promisesAPI. Alternatively, if synchronous operations are preferred, remove theasynckeyword since noawaitis used.Apply this diff to use async file operations:
-async function generateLlmsFull() { +async function generateLlmsFull(): Promise<void> { const pages = getAllPages(); const content = pages .map((page) => `# ${page.title}\n\n${page.content}`) .join("\n\n"); const outputPath = path.join(process.cwd(), "public/llms-full.txt"); - fs.writeFileSync(outputPath, content); + await fs.promises.writeFile(outputPath, content, "utf-8"); console.log(`Generated ${outputPath}`); }As per coding guidelines, TypeScript with strict typing should be used across the codebase.
21-36: Add return type annotation for strict typing.The function correctly uses
async/awaitfor the remark processing, but lacks an explicit return type annotation.Apply this diff:
-async function generateLlmsChangelog() { +async function generateLlmsChangelog(): Promise<void> { const changelogPath = path.join(process.cwd(), "pages/docs/changelog.en.mdx"); const fileContent = fs.readFileSync(changelogPath, "utf-8"); const { content } = matter(fileContent);As per coding guidelines, strict typing should be enabled across the codebase.
38-51: Consider making file operations async or removingasynckeyword.Similar to
generateLlmsFull, this function is declared asasyncbut uses synchronous operations. Apply the same consistency improvement here.Apply this diff:
-async function generateLlmsIndex() { +async function generateLlmsIndex(): Promise<void> { const content = ` # Stackflow Documentation for LLMs ## Documentation Sets - [llms-full.txt](${new URL("/llms-full.txt", baseUrl)}): Complete documentation of Stackflow - [llms-changelog.txt](${new URL("/llms-changelog.txt", baseUrl)}): Latest updates and version history `.trim(); const outputPath = path.join(process.cwd(), "public/llms.txt"); - fs.writeFileSync(outputPath, content); + await fs.promises.writeFile(outputPath, content, "utf-8"); console.log(`Generated ${outputPath}`); }As per coding guidelines, strict typing should be applied.
53-70: Good error handling and directory management.The main function properly ensures the output directory exists and includes appropriate error handling with logging and exit code. The sequential execution of generators is clear and correct.
For consistency with strict typing guidelines, consider adding a return type annotation:
-async function main() { +async function main(): Promise<void> { try {
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Jira integration is disabled by default for public repositories
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
⛔ Files ignored due to path filters (10)
.yarn/cache/@esbuild-darwin-arm64-npm-0.25.12-2a5a9f9710-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-darwin-x64-npm-0.25.12-157b2f4f8a-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-linux-arm64-npm-0.25.12-a5aaa0e70e-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-linux-ia32-npm-0.25.12-3b5addbfbb-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-linux-x64-npm-0.25.12-07c7c22cce-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/esbuild-npm-0.25.12-352393c4bd-bc9c03d64e.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/get-tsconfig-npm-4.13.0-009b232bdd-3603c6da30.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/resolve-pkg-maps-npm-1.0.0-135b70c854-0763150adf.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/tsx-npm-4.20.6-78231068b5-16396df25c.zipis excluded by!**/.yarn/**,!**/*.zipyarn.lockis excluded by!**/yarn.lock,!**/*.lock
📒 Files selected for processing (4)
.pnp.cjs(76 hunks)docs/.gitignore(1 hunks)docs/package.json(3 hunks)docs/scripts/generate-llms-txt.ts(1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
- docs/package.json
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx}
📄 CodeRabbit inference engine (AGENTS.md)
Write source in TypeScript with strict typing enabled across the codebase
Files:
docs/scripts/generate-llms-txt.ts
🧬 Code graph analysis (1)
docs/scripts/generate-llms-txt.ts (2)
docs/utils/get-all-pages.ts (1)
getAllPages(13-39)docs/utils/constants.ts (1)
baseUrl(1-4)
🪛 GitHub Actions: Integration
docs/scripts/generate-llms-txt.ts
[error] 1-1: Command tsx failed with Error: spawn tsx ENOENT. Is the command on your path?
🪛 GitHub Actions: Release
docs/scripts/generate-llms-txt.ts
[error] 1-1: Command 'tsx scripts/generate-llms-txt.ts' failed. spawn ENOENT: 'tsx' not found on PATH. Install 'tsx' or adjust build to use an available runner (e.g., node).
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (2)
- GitHub Check: Workers Builds: stackflow-docs
- GitHub Check: Cloudflare Pages
🔇 Additional comments (4)
docs/.gitignore (1)
3-6: LGTM! Appropriate ignore patterns for generated LLMS artifacts.The gitignore entries correctly exclude the generated LLMS documentation files (llms-full.txt, llms-changelog.txt, llms.txt) that are created by the new build script.
docs/scripts/generate-llms-txt.ts (2)
1-8: Imports are well-organized and appropriate.The use of the
node:protocol prefix for built-in modules is a modern best practice, and the dependencies align with the script's markdown processing requirements.
1-1: ****The original concern about a missing
tsxcommand is not valid. Verification confirms:
tsxis already declared as a devDependency indocs/package.jsonat version^4.20.6- All GitHub Actions workflows (
build.yml,integration.yml,release.yml) runyarn install --immutablebefore executing any build steps- The script is correctly invoked via
yarn build:llms, which resolvestsxfromnode_modules/.bin/- The hardcoded path to
pages/docs/changelog.en.mdxis correct for the execution context (resolves todocs/pages/docs/changelog.en.mdxwhen the script runs from the docs folder)No pipeline failures related to the missing
tsxcommand should occur with the current configuration.Likely an incorrect or invalid review comment.
.pnp.cjs (1)
118-130: Auto-generated dependency manifest—verify package.json changes instead.This file is auto-generated by Yarn and reflects the current lock state. The hunks show legitimate dependency additions (e.g.,
@changesets/*for changelog generation,remark/mdast/micromarkfor markdown processing) and version bumps (esbuildto 0.25.12) that align with the PR's documentation infrastructure goals.However, reviewing this file directly is not actionable. To verify these changes are correct:
- Review the corresponding
package.jsonchanges to see which dependencies were explicitly added and which versions were specified.- Confirm that
@changesets/*,remark, and related markdown packages are pinned to intentional versions (e.g., are they dev-only dependencies?).- Verify no breaking version jumps in transitive dependencies.
Also applies to: 2541-2555, 10163-10195, 16160-16283, 17506-17517
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
♻️ Duplicate comments (5)
scripts/generate-changelog.ts (4)
120-168: Don't cap to 10 changesets; use release plan IDs and avoid Unix-only commands.The pipeline
find .changeset -name '*.md' -not -name 'README.md' | head -10silently limits processing to 10 changesets and relies on Unix-specific tools (find, grep, head, cut). Instead, derive the list of changeset files fromreleasePlan.changesets.map(c => c.id)and use only Git commands for portability.Based on past review comments, this is a known issue that remains unresolved.
Apply the suggested fix from the previous review to pass changeset IDs to the function and build paths programmatically:
-async function getChangesetCommits(): Promise<Record<string, string>> { +async function getChangesetCommits(ids: string[]): Promise<Record<string, string>> { try { - // .changeset 폴더의 .md 파일들 찾기 (README.md 제외) - const files = await execCommand( - "find .changeset -name '*.md' -not -name 'README.md' | head -10", - ); - - if (!files) { - console.log("📝 No changeset files found in .changeset folder"); - - return {}; - } - - const fileList = files.split("\n").filter((file) => file.trim()); - console.log(`📊 Found ${fileList.length} changeset files:`, fileList); - - // 각 파일별로 main 브랜치에 머지된 commit 찾기 + // Release plan에 등장하는 changeset ID들만 처리 + const fileList = ids.map((id) => `.changeset/${id}.md`); + console.log(`📊 Resolving ${fileList.length} changeset files from release plan`); + const commitMap: Record<string, string> = {}; for (const file of fileList) { - // changeset ID 추출 (파일명에서 .md 제거) const changesetId = file.split("/").pop()?.replace(".md", "") || ""; - - // Version Packages 커밋을 제외하고 main 브랜치에 머지된 커밋 찾기 + // main 브랜치 첫 머지 커밋 (Version Packages 제외) const commit = await execCommand( `git log --oneline --first-parent main -- "${file}" | grep -v "Version Packages" | head -1 | awk '{print $1}'`, );Then update the call site at line 221:
- const commitMap = await getChangesetCommits(); + const commitMap = await getChangesetCommits(releasePlan.changesets.map((c) => c.id));
241-244: Render manualContent in the generated changelog.The
manualContentis collected from existing changelogs butgenerateChangelogMarkdownnever outputs it, so manual notes are silently dropped.Based on past review comments, this is a known issue that remains unresolved. Update
generateChangelogMarkdownto render themanualContentfield for each entry (preferably after the changesets list), ensuring it's included in the final output.
451-451: Handle first-run when changelog file doesn't exist.
readFilewill throw ifdocs/pages/docs/changelog.en.mdxis missing. Wrap in try-catch and default to empty string for initial runs.Based on past review comments, this is a known issue that remains unresolved.
- const existingContent = await readFile(changelogEnPath, "utf-8"); + let existingContent = ""; + try { + existingContent = await readFile(changelogEnPath, "utf-8"); + } catch (e: any) { + if (e?.code !== "ENOENT") throw e; + console.log("🆕 No existing changelog; starting fresh"); + }
469-473: Read Korean changelog separately to preserve KO content.Currently,
markdownKois built using EnglishexistingContent, which overwrites Korean frontmatter and manual blocks.Based on past review comments, this issue was marked as addressed but the code still uses
existingContent(English) for both EN and KO generation. Read the Korean file separately:+ // Read KO content and manual blocks + let existingContentKo = ""; + try { + existingContentKo = await readFile(changelogKoPath, "utf-8"); + } catch (e: any) { + if (e?.code !== "ENOENT") throw e; + console.log("🆕 No existing changelog.ko.mdx; starting fresh"); + } + const manualContentsKo = await extractManualContent(changelogKoPath); + + // Build entries separately so KO manual content for today's date is preserved + const entriesKo = await organizeChangelogEntries( + releasePlan, + manualContentsKo, + existingContentKo, + ); + const markdownKo = generateChangelogMarkdown( - entries, - existingContent, + entriesKo, + existingContentKo, "변경 이력", );package.json (1)
14-14: Migrate esbuild configs or add per-package type overrides before setting"type": "module".Adding
"type": "module"converts all.jsfiles to ESM, but multipleesbuild.config.jsfiles across the monorepo still use CommonJSrequire()syntax and will fail when parsed as ESM.Based on past review comments, this is a known issue that remains unresolved. Either:
- Migrate each
esbuild.config.jsto.mjsor use ESMimport/exportsyntax, or- Add
"type": "commonjs"to each extension'spackage.jsonto override the root settingVerify all affected packages before merging.
🧹 Nitpick comments (1)
docs/tsconfig.json (1)
10-10: Consider enabling TypeScript strict mode.The configuration disables strict mode (
"strict": false), which reduces type safety during compilation. While this is pragmatic for documentation-only build scripts, enabling strict mode would catch more potential issues early.Apply this diff to enable strict mode:
- "strict": false, + "strict": true,Alternatively, if you prefer a phased approach, you can keep the current setting for now and enable it incrementally as the docs tooling matures.
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Jira integration is disabled by default for public repositories
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
⛔ Files ignored due to path filters (52)
.yarn/cache/@changesets-assemble-release-plan-npm-6.0.9-e01af97ef4-f84656eabb.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@changesets-git-npm-3.0.4-c1d351b2f6-4f5a1f3354.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@changesets-read-npm-0.6.5-fc55502eb7-fec0ac2880.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-darwin-arm64-npm-0.25.12-2a5a9f9710-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-darwin-x64-npm-0.25.12-157b2f4f8a-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-linux-arm64-npm-0.25.12-a5aaa0e70e-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-linux-ia32-npm-0.25.12-3b5addbfbb-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/@esbuild-linux-x64-npm-0.25.12-07c7c22cce-10.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/esbuild-npm-0.25.12-352393c4bd-bc9c03d64e.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/get-tsconfig-npm-4.13.0-009b232bdd-3603c6da30.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-find-and-replace-npm-3.0.2-700884f061-446561aa95.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-from-markdown-npm-2.0.2-b327f875e3-69b207913f.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-autolink-literal-npm-2.0.1-dd870d9308-d933b42feb.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-footnote-npm-2.1.0-d8da32ba7c-5fac0f64d1.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-npm-3.1.0-933de2cdb5-d66809a070.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-strikethrough-npm-2.0.0-d16d95c318-b1abc137d7.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-table-npm-2.0.0-45a74f064b-a043d60d72.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-gfm-task-list-item-npm-2.0.0-cb1270a10f-679a3ff09b.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-phrasing-npm-4.1.0-30939ebbcd-3a97533e8a.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-to-markdown-npm-2.1.2-40d984eac3-ab494a32f1.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/mdast-util-to-string-npm-4.0.0-fc8d9714a5-f4a5dbb9ea.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-core-commonmark-npm-2.0.3-5e317c62b2-2b98b9eba1.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-autolink-literal-npm-2.1.0-8fcb271412-933b9b96ca.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-footnote-npm-2.1.0-1cf783dd36-7e019414e3.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-npm-3.0.0-d154ab531f-8493d10417.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-strikethrough-npm-2.1.0-b2aa188eba-eaf2c7b1e3.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-table-npm-2.1.1-7b9f4422c9-0391ead408.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-tagfilter-npm-2.0.0-c5ad486636-c5e3f8cdf2.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-extension-gfm-task-list-item-npm-2.1.0-b717607894-c5f72929f0.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-destination-npm-2.0.1-2b4ab89121-9c4baa9ca2.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-label-npm-2.0.1-2ce9fdcfd2-bd03f5a75f.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-space-npm-2.0.1-36b4717310-1bd68a017c.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-title-npm-2.0.1-a5f7a4ac37-b4d2e4850a.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-factory-whitespace-npm-2.0.1-2d7cfaf8ae-67b3944d01.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-npm-4.0.2-99b2e4c11c-1b85e49c8f.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-chunked-npm-2.0.1-27444b1e7b-f8cb2a67bc.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-classify-character-npm-2.0.1-127a4a9c2a-4d8bbe3a6d.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-combine-extensions-npm-2.0.1-9810c0bf8d-5d22fb9ee3.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-decode-numeric-character-reference-npm-2.0.2-c2d481632e-ee11c8bde5.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-decode-string-npm-2.0.1-72716f39ea-2f517e4c61.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-html-tag-name-npm-2.0.1-eb560993c8-dea365f5ad.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-normalize-identifier-npm-2.0.1-336335e80e-1eb9a289d7.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-resolve-all-npm-2.0.1-50f997ec4c-9275f3ddb6.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/micromark-util-subtokenize-npm-2.1.0-2452c9ae9b-5f18c70cb9.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/remark-gfm-npm-4.0.1-f55aaba8ef-86899862cf.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/remark-npm-15.0.1-0f67091876-671eae3a44.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/remark-parse-npm-11.0.0-6484fba69e-59d584be56.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/remark-stringify-npm-11.0.0-b41a557b8d-32b2f6093b.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/resolve-pkg-maps-npm-1.0.0-135b70c854-0763150adf.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/tsx-npm-4.20.6-78231068b5-16396df25c.zipis excluded by!**/.yarn/**,!**/*.zip.yarn/cache/unified-npm-11.0.5-ac5333017e-d9e6e88900.zipis excluded by!**/.yarn/**,!**/*.zipyarn.lockis excluded by!**/yarn.lock,!**/*.lock
📒 Files selected for processing (21)
.changeset/chatty-breads-watch.md(1 hunks).pnp.cjs(76 hunks)docs/.gitignore(1 hunks)docs/next.config.mjs(1 hunks)docs/package.json(3 hunks)docs/pages/docs/_meta.en.json(1 hunks)docs/pages/docs/_meta.ko.json(1 hunks)docs/pages/docs/ai-integration/_meta.en.json(1 hunks)docs/pages/docs/ai-integration/_meta.ko.json(1 hunks)docs/pages/docs/ai-integration/llms-txt.en.mdx(1 hunks)docs/pages/docs/ai-integration/llms-txt.ko.mdx(1 hunks)docs/pages/docs/changelog.en.mdx(1 hunks)docs/pages/docs/changelog.ko.mdx(1 hunks)docs/pages/docs/get-started/_meta.en.json(1 hunks)docs/pages/docs/get-started/_meta.ko.json(1 hunks)docs/scripts/generate-llms-txt.ts(1 hunks)docs/tsconfig.json(1 hunks)docs/utils/constants.ts(1 hunks)docs/utils/get-all-pages.ts(1 hunks)package.json(2 hunks)scripts/generate-changelog.ts(1 hunks)
✅ Files skipped from review due to trivial changes (1)
- docs/pages/docs/ai-integration/_meta.ko.json
🚧 Files skipped from review as they are similar to previous changes (6)
- docs/scripts/generate-llms-txt.ts
- docs/pages/docs/changelog.ko.mdx
- docs/pages/docs/get-started/_meta.en.json
- docs/utils/get-all-pages.ts
- docs/pages/docs/changelog.en.mdx
- docs/next.config.mjs
🧰 Additional context used
📓 Path-based instructions (2)
**/*.{ts,tsx}
📄 CodeRabbit inference engine (AGENTS.md)
Write source in TypeScript with strict typing enabled across the codebase
Files:
docs/utils/constants.tsscripts/generate-changelog.ts
.changeset/*.md
📄 CodeRabbit inference engine (AGENTS.md)
Include a Changeset entry for any user-facing package change
Files:
.changeset/chatty-breads-watch.md
🧬 Code graph analysis (1)
docs/utils/constants.ts (1)
.pnp.cjs (1)
URL(21314-21314)
🪛 ast-grep (0.40.0)
scripts/generate-changelog.ts
[warning] 55-55: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(## ${date}(?: #\\d+)?, "g")
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html
(regexp-from-variable)
🪛 LanguageTool
docs/pages/docs/ai-integration/llms-txt.ko.mdx
[grammar] ~5-~5: El plural de les sigles no es marca gràficament.
Context: --- title: LLMs.txt --- # LLMs.txt 대규모 언어 모델(LLM)이 Stackflow를 쉽게 이해할 ...
(SIGLES)
[grammar] ~7-~7: El plural de les sigles no es marca gràficament.
Context: ...대규모 언어 모델(LLM)이 Stackflow를 쉽게 이해할 수 있도록 LLMs.txt를 제공합니다. ### 구조 다음과 같은 LLMs.txt 파일...
(SIGLES)
[grammar] ~11-~11: El plural de les sigles no es marca gràficament.
Context: ... 수 있도록 LLMs.txt를 제공합니다. ### 구조 다음과 같은 LLMs.txt 파일들을 제공합니다: - [llms.txt](https://s...
(SIGLES)
[typographical] ~13-~13: Símbol sense parella: sembla que falta «[».
Context: ...다음과 같은 LLMs.txt 파일들을 제공합니다: - llms.txt: LLMs.tx...
(UNPAIRED_BRACKETS)
[grammar] ~13-~13: El plural de les sigles no es marca gràficament.
Context: ...ms.txt](https://stackflow.so/llms.txt): LLMs.txt 파일들의 구조를 제공하는 메인 파일입니다. - [llms-ful...
(SIGLES)
[typographical] ~14-~14: Símbol sense parella: sembla que falta «[».
Context: ...파일들의 구조를 제공하는 메인 파일입니다. - llms-full.txt: St...
(UNPAIRED_BRACKETS)
[typographical] ~15-~15: Símbol sense parella: sembla que falta «[».
Context: ...low의 모든 문서를 포함합니다. - [llms-changelog.txt](https://stackflow.so/llms-changelog.txt...
(UNPAIRED_BRACKETS)
[grammar] ~19-~19: El plural de les sigles no es marca gràficament.
Context: ...### Cursor Cursor의 @docs 기능을 사용하여 프로젝트에 LLMs.txt 파일을 포함할 수 있습니다. [**Cursor @docs에 대...
(SIGLES)
[typographical] ~21-~21: Símbol sense parella: sembla que falta «[».
Context: ...함할 수 있습니다. [Cursor @docs에 대해 자세히 알아보기](https://docs.cursor.com/context/@-symbo...
(UNPAIRED_BRACKETS)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (2)
- GitHub Check: Workers Builds: stackflow-docs
- GitHub Check: Cloudflare Pages
🔇 Additional comments (13)
.pnp.cjs (1)
118-130: This is an auto-generated file; verify dependency updates align with PR objectives.The
.pnp.cjsfile is auto-generated by Yarn and reflects package dependency updates. The changes include:
- Changesets packages (assemble-release-plan, cli, config, pre, read, types): Used for changelog automation, supporting the PR goal of adding changelog functionality.
- Remark/markdown packages (remark, remark-gfm, remark-parse, remark-stringify, mdast-util-, micromark-): Required for markdown processing, supporting LLMs.txt and documentation generation.
- Build tooling (esbuild 0.25.12, tsx 4.20.6, get-tsconfig 4.13.0): Updated versions with appropriate dependency resolution.
- New packages (resolve-pkg-maps, gray-matter): gray-matter enables YAML/frontmatter parsing, useful for documentation headers.
These updates appear intentional and aligned with the PR's documentation infrastructure goals. However, ensure that:
- Any major version bumps (especially in changesets and remark) don't introduce breaking changes to your tooling.
- This file is regenerated as part of your CI/build process rather than manually maintained.
Also applies to: 2541-2555, 6373-6397, 10160-10195, 16160-16283, 17506-17517
docs/.gitignore (1)
5-6: LGTM!The ignore patterns correctly exclude generated LLMs.txt files from version control.
docs/pages/docs/get-started/_meta.ko.json (1)
7-8: LGTM!The Korean translation metadata is correctly added with proper JSON formatting.
docs/pages/docs/_meta.en.json (1)
4-5: LGTM!The English metadata entries are correctly added for the new AI Integration and Changelog sections.
docs/pages/docs/ai-integration/llms-txt.ko.mdx (1)
1-21: LGTM!The Korean documentation correctly describes the LLMs.txt structure and usage with AI tools. The static analysis warnings are false positives (Catalan grammar rules incorrectly applied to Korean text).
docs/utils/constants.ts (1)
1-4: LGTM!The baseUrl constant correctly handles development and production environments with appropriate fallback. The localhost port 6006 aligns with the dev script configuration.
docs/package.json (2)
8-9: LGTM!The build workflow correctly chains LLMs generation before the Next.js build, and tsx is properly added as a devDependency to execute the TypeScript generation script.
31-41: LGTM!The added dependencies (gray-matter for frontmatter parsing, remark ecosystem for Markdown processing, and tsx for TypeScript execution) appropriately support the LLMs text generation workflow.
package.json (1)
33-33: Patch is compatible with version 6.0.9—no action needed.There are no breaking changes between version 6.0.6 and 6.0.9; these were patch releases only. The patch file targets the compiled dist code, which remains stable across patch releases. The resolution selector
@changesets/assemble-release-plan@npm:^6.0.6correctly matches version 6.0.9, and the patch will apply cleanly without issues.docs/pages/docs/_meta.ko.json (1)
1-6: Korean metadata keys added correctly.The translations for the new AI integration and changelog sections are semantically accurate and follow the existing metadata structure.
.changeset/chatty-breads-watch.md (1)
1-5: Changeset entry correctly formatted and required.The changeset properly documents a user-facing documentation package change with an appropriate "minor" version bump. The description is clear and concise. This satisfies the coding guideline for user-facing package changes.
docs/pages/docs/ai-integration/_meta.en.json (1)
1-3: AI integration metadata added correctly.The metadata properly maps the LLMs.txt documentation route to its display name. Structure is consistent with framework conventions.
docs/pages/docs/ai-integration/llms-txt.en.mdx (1)
1-21: Documentation page is well-structured and clearly written.The content effectively explains the LLMs.txt setup with clear sections for structure and usage. The three file variants are well-differentiated, and the Cursor integration example provides practical value to users.
Please verify during deployment testing that the three LLMs.txt files (
llms.txt,llms-full.txt,llms-changelog.txt) will be generated and available at the URLs referenced in lines 13-15. Also confirm the external Cursor documentation link remains valid.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 0
♻️ Duplicate comments (4)
package.json (1)
14-14: Verify ESM migration is complete before merging.This change converts the entire monorepo to ES modules. As flagged in previous reviews, multiple
esbuild.config.jsfiles throughout the codebase still use CommonJSrequire()syntax and will fail when parsed as ESM. Ensure all affected build configuration files have been migrated to ESM syntax or have local"type": "commonjs"overrides in their package.json files.docs/scripts/generate-changelog.ts (3)
123-171: Remove 10-entry cap and use cross-platform approach to derive changeset commits.The current implementation has two critical issues:
head -10on line 127 silently limits processing to 10 changesets, potentially dropping entries- The Unix pipeline (
find,grep,head,cut) won't work on WindowsAs previously suggested, derive the changeset file list from
releasePlan.changesetsby mapping IDs to.changeset/<id>.mdpaths, then use git commands directly without shell pipelines. This ensures all changesets are processed and improves cross-platform compatibility.
243-247: Manual content is collected but never rendered in the output.The
manualContentfield is added to entries butgenerateChangelogMarkdown(lines 260-329) doesn't render it. Manual notes from MANUAL_CONTENT_START/END blocks will be silently dropped.Update
generateChangelogMarkdownto renderentry.manualContent(if present) within each date section, preferably after the changesets list.
466-470: Korean changelog may lose locale-specific front-matter and manual content.Lines 466-470 generate
markdownKousing the sameexistingContent(from English file, line 448) andmanualContents(from English file, lines 450-451). This means Korean-specific front-matter and manual content blocks will be overwritten with English content.Read
changelogKoPathseparately and extract its manual content to preserve Korean locale-specific information.+ console.log("📖 Reading existing Korean changelog..."); + let existingContentKo = ""; + try { + existingContentKo = await readFile(changelogKoPath, "utf-8"); + } catch (e: any) { + if (e?.code !== "ENOENT") throw e; + console.log("🆕 No existing Korean changelog; starting fresh"); + } + + console.log("📖 Extracting Korean manual content..."); + const manualContentsKo = await extractManualContent(changelogKoPath); + + console.log("🗂️ Organizing Korean changelog entries..."); + const entriesKo = await organizeChangelogEntries( + releasePlan, + manualContentsKo, + existingContentKo, + ); + console.log("📝 Generating changelog markdown..."); const markdownEn = generateChangelogMarkdown( entries, existingContent, "Changelog", ); const markdownKo = generateChangelogMarkdown( - entries, - existingContent, + entriesKo, + existingContentKo, "변경 이력", );
🧹 Nitpick comments (1)
.pnp.cjs (1)
118-127: This is an auto-generated lock file—verify updates came from package.json changes.The
.pnp.cjsfile is Yarn's auto-generated Plug'n'Play runtime manifest and should not be manually edited. All changes shown here should result from updates topackage.jsonand runningyarn installor similar commands.The hunks indicate significant dependency additions and version bumps that align with the PR objectives:
- @changesets/ packages* (v6.0.9, v3.1.1, v2.0.2, v0.6.5, v6.1.0, v3.0.4) — for automated changelog generation
- remark ecosystem ([email protected], [email protected], [email protected], mdast-util-, micromark-) — for markdown processing and LLMs.txt generation
- [email protected] with platform binaries — build tooling update
- [email protected] — TypeScript execution tool
Verify that these dependency updates (especially version bumps) have been intentionally made in
package.jsonand thatyarn.lockwas regenerated to produce this.pnp.cjsmanifest.Also applies to: 2539-2767, 2974-10201, 10976-10985, 13024-14209, 16166-16289, 17512-17523, 17684-17697
📜 Review details
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Disabled knowledge base sources:
- Jira integration is disabled by default for public repositories
- Linear integration is disabled by default for public repositories
You can enable these sources in your CodeRabbit configuration.
⛔ Files ignored due to path filters (1)
yarn.lockis excluded by!**/yarn.lock,!**/*.lock
📒 Files selected for processing (4)
.pnp.cjs(77 hunks)docs/package.json(2 hunks)docs/scripts/generate-changelog.ts(1 hunks)package.json(1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
- docs/package.json
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx}
📄 CodeRabbit inference engine (AGENTS.md)
Write source in TypeScript with strict typing enabled across the codebase
Files:
docs/scripts/generate-changelog.ts
🪛 ast-grep (0.40.0)
docs/scripts/generate-changelog.ts
[warning] 58-58: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(## ${date}(?: #\\d+)?, "g")
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html
(regexp-from-variable)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (2)
- GitHub Check: Workers Builds: stackflow-docs
- GitHub Check: Cloudflare Pages
🔇 Additional comments (1)
package.json (1)
22-22: LGTM! Changelog generation properly integrated into version workflow.The script correctly prepends changelog generation before version bumping, ensuring the changelog is updated as part of the versioning process.
No description provided.