Skip to content

πŸ—„οΈ feat: Archive Docs Snapshots Automatically For Each LibreChat Release - #933

Open
berry-13 wants to merge 4 commits into
mainfrom
berry-13/feat-auto-archive-docs
Open

berry-13 wants to merge 4 commits into
mainfrom
berry-13/feat-auto-archive-docs

Conversation

@berry-13

@berry-13 berry-13 commented Nov 14, 2026 •

Copy link
Copy Markdown
Collaborator

Summary

Archiving docs for a LibreChat release was a manual pnpm docs:archive run, and v0.8.9-rc1 (published Oct 26) still has no snapshot. This adds pnpm docs:archive:sync and a daily Sync docs archive workflow that does it automatically and opens a PR for review.

Each new release and release candidate is archived from the last commit on main (first-parent) before it was published, so a snapshot matches its release day. Candidate snapshots stay while a release is in testing and show a "Release candidate" banner instead of the "no longer maintained" warning; the PR that archives the final release removes them. Final releases are compared with the newest archived final, so overlapping release lines work. The run changes nothing when the releases API fails, when there is no release snapshot to start from, or when the archive would reach the 17 snapshots webpack cannot bundle.

Change Type

  • New feature (non-breaking change which adds functionality)

Testing

  • pnpm exec vitest run scripts/sync-docs-archive.test.ts lib/docs-version-order.test.ts scripts/archive-docs-version.test.ts: all pass (planner rules, pagination, first-parent pick, banner kind)
  • e2e/docs-archive-sync.spec.ts: 5 scenarios run the real script against a git fixture and a local releases API stand-in
  • e2e/docs-archive-versions.spec.ts against next start on a production build that included a generated v0.8.9-rc1 snapshot: every snapshot is listed in the switcher and shows the banner for its status; light and dark screenshots checked
  • pnpm docs:archive:sync --dry-run against the live releases plans v0.8.9-rc1 from 2426cdc7, committed 30 seconds before the release. The snapshot is not committed here; the workflow opens it after merge.
  • pnpm typecheck, ESLint and Prettier clean

Checklist

  • My code adheres to this project's style guidelines
  • I have performed a self-review of my own code
  • I have commented in any complex areas of my code
  • I have made pertinent documentation changes
  • My changes do not introduce new warnings
  • I have written tests demonstrating that my changes are effective or that my feature works
  • Local unit tests pass with my changes

Add pnpm docs:archive:sync and a daily workflow that archives every LibreChat
release and release candidate newer than the newest snapshot, each from the
last docs commit before it was published, and opens a PR. Candidate snapshots
stay until their final release is archived and are removed in that PR.
@berry-13 berry-13 added the enhancement New feature or request label Nov 14, 2026
@vercel

vercel Bot commented Nov 14, 2026 •

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
librechat-ai Ready Ready Preview Nov 14, 2026 1:02am UTC

Request Review

@chatgpt-codex-connector

chatgpt-codex-connector Bot commented Nov 14, 2026 •

Copy link
Copy Markdown
Codex Review Summary: βœ… Completed

This comment shows the latest Codex review activity on this pull request.

Review Status Commit Review trigger
πŸ“ Code Review βœ… Completed 2026-11-14T00:53:23.567213Z ba9d8ee New commits
πŸ”’ Security Review βœ… Completed 2026-11-14T00:35:09.532646Z 80200df PR opened
ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review" or "@codex security review".

Codex reacts with πŸ‘€ while any review is running, comments if it has suggestions, and reacts with πŸ‘ once all reviews finish with no findings.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

πŸ’‘ Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 80200df157

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with πŸ‘.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread scripts/sync-docs-archive.ts Outdated
const pending = releases
.filter((release) => RELEASE_TAG_PATTERN.test(release.tag))
.filter((release) => !existing.includes(release.tag))
.filter((release) => !newestArchived || isNewer(release.tag, newestArchived))

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Allow final releases to replace candidates below the newest snapshot

When release streams overlap, an archived candidate for a higher version prevents a lower version's final release from ever being archived. For example, with v0.8.9-rc1 and v0.9.0-rc1 already archived, publishing v0.8.9 produces { archive: [], remove: [] }: this filter excludes the final release before stableIds can recognize it. Consequently, its candidate remains indefinitely and the latest stable docs remain outdated. Allow missing final releases that supersede existing candidate snapshots even when they sort below the newest archived version.

Useful? React with πŸ‘Β / πŸ‘Ž.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 7881ef3 (pushed head ba9d8ee). Final releases are now compared with the newest archived final release, not the newest snapshot of any kind, so with v0.8.8, v0.8.9-rc1 and v0.9.0-rc1 archived, publishing v0.8.9 archives it and removes v0.8.9-rc1 while v0.9.0-rc1 stays. Unit test 'archives a final release below a newer archived candidate' is your example; the final-release-replaces-its-candidate-snapshots scenario runs the planner through the real script.

Comment thread scripts/sync-docs-archive.ts Outdated

/** The last commit on `ref` at or before `timestamp`, so a snapshot matches its release day. */
export async function commitAt(timestamp: string, cwd: string, ref = 'HEAD'): Promise<string> {
const { stdout } = await execFile('git', ['rev-list', '-1', `--before=${timestamp}`, ref], {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Restrict historical snapshot selection to first-parent history

If a branch contains commits dated before a release but is merged into main afterward, this unrestricted traversal can select a commit from that branch rather than the tree that was actually on main at release time. The resulting archive can therefore include unpublished changes and omit other main-branch changes. Git's rev-list documentation specifies that --first-parent will β€œfollow only the first parent commit upon seeing a merge commit”; use that restriction when resolving the historical main-branch snapshot.

Useful? React with πŸ‘Β / πŸ‘Ž.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 7881ef3 (pushed head ba9d8ee): commitAt runs git rev-list -1 --first-parent --before=<published_at>. 6819aea adds a unit test with a branch committed before the release and merged after it; removing --first-parent makes it pick the branch commit and fail.

Comment thread scripts/sync-docs-archive.ts Outdated
}

async function fetchReleases(repository: string, token?: string): Promise<Release[]> {
const response = await fetch(`https://github.com/proxy/api.github.com/repos/${repository}/releases?per_page=50`, {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Paginate releases before calculating the archive plan

If an unarchived release falls beyond the first 50 API resultsβ€”for example, after an extended interruption in syncingβ€”this function silently omits it. GitHub documents per_page as the number of results per page and defaults page to 1, so this request does not retrieve the complete release list. Once the returned newer releases are archived, the planner's newest-snapshot cutoff permanently excludes the omitted releases on subsequent runs. Follow pagination until all potentially pending releases have been fetched rather than treating the first page as complete. See the List releases parameters.

Useful? React with πŸ‘Β / πŸ‘Ž.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 7881ef3 (pushed head ba9d8ee): fetchReleases follows page= at 100 per page until a short page, and fails after 20 full pages instead of treating a partial list as complete. Unit test 'follows pagination to the last page and skips drafts' (6819aea) checks two requests and the release on page 2.

@github-actions

Copy link
Copy Markdown
Contributor

πŸ“¦ Next.js Bundle Analysis for librechat.ai

This analysis was generated by the Next.js Bundle Analysis action. πŸ€–

This PR introduced no changes to the JavaScript bundle! πŸ™Œ

Compare final releases with the newest archived final release, so an
archived candidate of a newer version no longer holds back the final release
of an older one. Pick the release-day commit from main's first-parent
history, read every page of releases, refuse to start without a final
release snapshot, and stop before the archive outgrows what the build can
bundle.

Archived release candidates newer than the latest release now get a release
candidate banner instead of the no longer maintained warning, and the sync
and the archived versions each get scenario specs.
@github-actions

Copy link
Copy Markdown
Contributor

πŸ“¦ Next.js Bundle Analysis for librechat.ai

This analysis was generated by the Next.js Bundle Analysis action. πŸ€–

This PR introduced no changes to the JavaScript bundle! πŸ™Œ

This branch was successfully deployed

1 active deployment
Preview β€” ba9d8ee7 Deployed Nov 14, 2026 by vercel[bot]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant