Skip to content

Commit 2dd33dd

Browse files
Keep install choices across methods and stop hiding commands on metadata errors
1 parent 5a62ac3 commit 2dd33dd

5 files changed

Lines changed: 63 additions & 32 deletions

File tree

‎app/docs/[section]/[[...slug]]/page.tsx‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -306,7 +306,7 @@ export default async function ArticlePage({ params }: PageProps) {
306306
<div className="mt-4">
307307
<Link
308308
href="/packages?method=packages"
309-
className={primerPrimaryLinkClass}
309+
className={primerSecondaryLinkClass}
310310
>
311311
Linux packages installation
312312
</Link>

‎app/lib/installSelection.ts‎

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -99,9 +99,13 @@ export function installSelectionQuery(selection: InstallSelection): string {
9999
return new URLSearchParams({ method: selection.method, family, target, pg, arch }).toString();
100100
}
101101

102-
// The shareable URL: package choices only matter, and are only written, for packages.
102+
// Docker links stay short, but keep non-default package choices so switching back restores them.
103103
export function installSelectionUrlQuery(selection: InstallSelection): string {
104-
return selection.method === "docker" ? "method=docker" : installSelectionQuery(selection);
104+
const { family, target, pg, arch } = selection.packages;
105+
const defaults = defaultInstallSelection.packages;
106+
const packagesChanged = family !== defaults.family || target !== defaults.target
107+
|| pg !== defaults.pg || arch !== defaults.arch;
108+
return selection.method === "docker" && !packagesChanged ? "method=docker" : installSelectionQuery(selection);
105109
}
106110

107111
export function selectInstallTarget(selection: InstallSelection, target: string): SelectionResult {

‎app/packages/page.tsx‎

Lines changed: 44 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -33,8 +33,11 @@ const dockerCommand = `docker run -dt --name documentdb \\
3333
--username '<YOUR_USERNAME>' \\
3434
--password '<YOUR_PASSWORD>'`;
3535

36-
const firstQuery = `db.starter.insertOne({ message: "Hello, DocumentDB!" })
37-
db.starter.findOne({ message: "Hello, DocumentDB!" })`;
36+
const dockerReadyCommand = `until docker logs documentdb 2>&1 | grep -q "=== DocumentDB is ready ==="; do sleep 2; done`;
37+
38+
const firstQuery = `use quickstart
39+
db.orders.insertOne({ item: "widget", qty: 5 })
40+
db.orders.find({ item: "widget" })`;
3841

3942
const nextGuides = [
4043
{ title: "Python", description: "Connect with PyMongo.", href: "/docs/getting-started/python-setup" },
@@ -79,17 +82,19 @@ export default function PackagesPage() {
7982
const { method, packages } = selection;
8083
const { family, target, pg, arch } = packages;
8184
const selectionReady = state !== null && state.error === null;
82-
const packagesAvailable = releaseStatus === "live" && releaseHasPackages(release, packages);
83-
const canInstall = selectionReady && packagesAvailable;
85+
// The commands install from the package repository, so only a confirmed gap in the release withholds them.
86+
const packagesMissing = releaseStatus === "live" && !releaseHasPackages(release, packages);
87+
const canInstall = selectionReady && !packagesMissing;
8488
const targetLabel = packages.family === "apt" ? aptTargetLabels[packages.target] : rpmTargetLabels[packages.target];
8589
const selectedPackageNames = `documentdb-${pg}`;
8690
const packagingGuideUrl = `https://github.com/documentdb/documentdb/blob/${release.tagName}/packaging/README.md`;
8791
const setupCommand = buildSetupCommand(pg);
8892
const installCommand = packages.family === "apt"
8993
? buildAptInstallCommand(packages.target, packages.arch, packages.pg)
9094
: buildRpmInstallCommand(packages.target, packages.arch, packages.pg);
91-
const connectionCommand = `mongosh 'mongodb://127.0.0.1:10260/mydb?authSource=admin&tls=true&tlsAllowInvalidCertificates=true' \\
92-
--username ${method === "packages" ? "admin" : "'<YOUR_USERNAME>'"} --password`;
95+
// Same form as the getting-started guides.
96+
const connectionCommand = `mongosh localhost:10260 -u ${method === "packages" ? "admin" : "'<YOUR_USERNAME>'"} -p \\
97+
--authenticationMechanism SCRAM-SHA-256 --tls --tlsAllowInvalidCertificates`;
9398

9499
function choose(result: SelectionResult) {
95100
setState(result);
@@ -99,7 +104,7 @@ export default function PackagesPage() {
99104
for (const [key, value] of new URLSearchParams(installSelectionUrlQuery(result.selection))) {
100105
url.searchParams.set(key, value);
101106
}
102-
window.history.pushState(null, "", url);
107+
window.history.replaceState(null, "", url);
103108
}
104109

105110
function changeChoice(key: "method" | "pg" | "arch", value: string) {
@@ -120,7 +125,10 @@ export default function PackagesPage() {
120125
Use Docker to evaluate and develop on Linux, macOS, or Windows. On a supported Linux
121126
host, Linux packages give you control over PostgreSQL, services, and configuration.
122127
</p>
123-
<a href="#downloads" className={`mt-4 inline-block text-sm ${linkClass}`}>Looking for individual package downloads?</a>
128+
<p className="mt-4 text-sm text-gray-300">
129+
<a href="https://github.com/documentdb/documentdb/releases" className={linkClass}>Download release assets</a>
130+
{" · "}<a href="#downloads" className={linkClass}>Package details</a>
131+
</p>
124132
</header>
125133

126134
<section aria-label="Installation method" className="grid gap-3 sm:grid-cols-2">
@@ -131,10 +139,10 @@ export default function PackagesPage() {
131139
<button
132140
key={item.value}
133141
type="button"
134-
aria-pressed={method === item.value}
142+
aria-pressed={state !== null && method === item.value}
135143
onClick={() => changeChoice("method", item.value)}
136144
className={`rounded-xl border p-5 text-left transition-colors focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-blue-400 ${
137-
method === item.value ? "border-blue-400 bg-blue-500/15" : "border-neutral-700 bg-neutral-800/60 hover:bg-neutral-800"
145+
state !== null && method === item.value ? "border-blue-400 bg-blue-500/15" : "border-neutral-700 bg-neutral-800/60 hover:bg-neutral-800"
138146
}`}
139147
>
140148
<span className="block text-xl font-semibold text-white">{item.title}</span>
@@ -165,10 +173,13 @@ export default function PackagesPage() {
165173
</div>
166174
)}
167175

168-
{method === "packages" ? (
176+
{/* The static page can't see the query string, so show no flow until it is read. */}
177+
{state === null ? (
178+
<p className="text-center text-sm text-gray-400">Loading installation steps...</p>
179+
) : method === "packages" ? (
169180
<>
170181
<section className={panelClass} aria-labelledby="linux-settings">
171-
<h2 id="linux-settings" className="text-xl font-bold text-white">One complete stack. No package decisions.</h2>
182+
<h2 id="linux-settings" className="text-xl font-bold text-white">Choose your Linux host</h2>
172183
<p className="mt-2 text-sm leading-6 text-gray-300">
173184
The selected <code>{selectedPackageNames}</code> package brings PostgreSQL, the extension,
174185
gateway, setup tools, and services together. The number {pg} is the PostgreSQL major,
@@ -216,28 +227,28 @@ export default function PackagesPage() {
216227
</p>
217228
</aside>
218229

219-
<div aria-live="polite">
230+
<div>
220231
{releaseStatus === "loading" ? (
221-
<p className="text-sm text-gray-300">Checking the published package release...</p>
232+
<p role="status" className="text-sm text-gray-300">Checking the published package release...</p>
222233
) : releaseStatus === "fallback" ? (
223234
<div role="alert" className="rounded-lg border border-amber-400/40 p-4 text-sm text-amber-100">
224235
<p>Cannot confirm the current repository release. {releaseError}</p>
225236
<p className="mt-2">
226-
Reference release: {release.tagName}, not confirmed current. Installation commands are
227-
withheld until availability can be confirmed.{" "}
237+
The commands below install the latest packages from the repository. Last known
238+
release: {release.tagName}.{" "}
228239
<a href="https://github.com/documentdb/documentdb/releases" className={linkClass}>Browse release assets</a>{" "}
229240
or <button type="button" onClick={() => window.location.reload()} className={linkClass}>retry the lookup</button>.
230241
</p>
231242
</div>
232243
) : (
233-
<p className="text-sm text-gray-300">
244+
<p role="status" className="text-sm text-gray-300">
234245
Published repository release:{" "}
235246
<a href={release.releaseUrl} className={linkClass}>{release.tagName}</a>
236247
{" · "}{targetLabel}{" · "}{arch === "auto" ? "AMD64 / ARM64" : arch}
237248
</p>
238249
)}
239250
</div>
240-
{selectionReady && releaseStatus === "live" && !packagesAvailable && (
251+
{selectionReady && packagesMissing && (
241252
<p role="alert" className="rounded-lg border border-amber-400/40 p-4 text-sm text-amber-100">
242253
The complete package set for this selection is not present in the published release.
243254
Choose another target or a specific available architecture, or{" "}
@@ -253,7 +264,7 @@ export default function PackagesPage() {
253264
stack. Review the command before running it. Installation does not start a usable DocumentDB endpoint.
254265
</p>
255266
{canInstall ? <CommandSnippet command={installCommand} label={`${family.toUpperCase()} installation`} /> : (
256-
<p className="text-sm text-gray-400">Commands will appear after your selection and the published package set are confirmed.</p>
267+
<p className="text-sm text-gray-400">No command is shown for this selection.</p>
257268
)}
258269
</section>
259270

@@ -328,7 +339,15 @@ export default function PackagesPage() {
328339
Install and start Docker first. Replace both credential placeholders before running the
329340
command. This local example exposes port 10260 only on your machine&apos;s loopback interface.
330341
</p>
331-
{selectionReady && <CommandSnippet command={dockerCommand} label="Docker" />}
342+
{selectionReady && (
343+
<>
344+
<CommandSnippet command={dockerCommand} label="Docker" />
345+
<p className="mb-4 mt-4 text-sm leading-6 text-gray-300">
346+
The container is up before DocumentDB accepts connections. Wait for the readiness banner:
347+
</p>
348+
<CommandSnippet command={dockerReadyCommand} label="Wait until ready" />
349+
</>
350+
)}
332351
<p className="mt-4 text-sm leading-6 text-gray-400">
333352
The container initializes the database; do not run the Linux package setup wizard inside it.
334353
For persistent volumes and a versioned image, follow the{" "}
@@ -339,15 +358,15 @@ export default function PackagesPage() {
339358
</>
340359
)}
341360

342-
{!(method === "docker" && dockerSetup === "guided") && (
361+
{state !== null && !(method === "docker" && dockerSetup === "guided") && (
343362
<section id="connect" className={panelClass}>
344363
<h2 className="text-2xl font-bold text-white">{method === "packages" ? "3" : "2"}. Connect and run your first query</h2>
345364
<p className="mb-4 mt-3 text-sm leading-6 text-gray-300">
346365
Install{" "}
347366
<a href="https://www.mongodb.com/docs/mongodb-shell/install/" className={linkClass}>mongosh</a>{" "}
348367
separately, then connect from the same host as DocumentDB.{" "}
349368
{method === "packages" ? "Use the admin password you chose during setup." : "Use the username and password you chose for Docker."}{" "}
350-
The shell prompts for the password; it is not included in the connection URI.
369+
The shell prompts for the password, so it stays out of your shell history.
351370
</p>
352371
{selectionReady && (method === "docker" || canInstall) && (
353372
<>
@@ -357,8 +376,8 @@ export default function PackagesPage() {
357376
</>
358377
)}
359378
<p className="mt-3 text-sm leading-6 text-gray-400">
360-
Expect an acknowledged insert and a document containing &quot;Hello, DocumentDB!&quot;.
361-
The example uses the <code>mydb</code> database. The self-signed certificate bypass is
379+
Expect an acknowledged insert and the widget document back.
380+
The example uses the <code>quickstart</code> database. The self-signed certificate bypass is
362381
for local development only; use trusted certificates and remove the bypass for other deployments.
363382
</p>
364383
<div className="mt-6 grid gap-3 sm:grid-cols-3">
@@ -372,7 +391,7 @@ export default function PackagesPage() {
372391
</section>
373392
)}
374393

375-
{method === "packages" && (
394+
{state !== null && method === "packages" && (
376395
<section className={panelClass} aria-labelledby="keep-control">
377396
<h2 id="keep-control" className="text-2xl font-bold text-white">Keep control after the first query</h2>
378397
<p className="mb-4 mt-3 text-sm leading-6 text-gray-300">

‎blogs/_posts/2026-09-10-linux-packages.md‎

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,12 +37,12 @@ This is a guided installation, not a one-command path from an unprepared machine
3737
After setup and an authenticated connection in `mongosh`, insert a document and read it back:
3838

3939
```javascript
40-
use linux_packages_demo
40+
use quickstart
4141
db.notes.insertOne({ message: "Start simple. Keep control." })
4242
db.notes.findOne({ message: "Start simple. Keep control." })
4343
```
4444

45-
The query should return the inserted document, including its `_id`. On a systemd host, follow [Services and paths]({{ site_root }}/docs/linux-packages/#services-and-paths) to restart the complete-stack target for your selected PostgreSQL major. Reconnect, select `linux_packages_demo`, and repeat the query to check that the same data remains. A service restart is not a data reset.
45+
The query should return the inserted document, including its `_id`. On a systemd host, follow [Services and paths]({{ site_root }}/docs/linux-packages/#services-and-paths) to restart the complete-stack target for your selected PostgreSQL major. Reconnect, select `quickstart`, and repeat the query to check that the same data remains. A service restart is not a data reset.
4646

4747
The [operations guide]({{ site_root }}/docs/linux-packages/) keeps service commands, storage paths, troubleshooting, and removal guidance in one place.
4848

@@ -56,7 +56,7 @@ The complete stack is the starting point, not the only option.
5656

5757
## Supported platforms and release boundaries
5858

59-
These details describe [v0.117-0](https://github.com/documentdb/documentdb/releases/tag/v0.117-0), the current release as of September 10, 2026. Linux packages are not new to this release.
59+
These details describe [v0.117-0](https://github.com/documentdb/documentdb/releases/tag/v0.117-0), the current release as of September 10, 2026.
6060

6161
The shipped package matrix covers Ubuntu 24.04 with APT and RHEL/Rocky Linux 9 with RPM/dnf, on PostgreSQL 17 or 18 and amd64 or arm64. RPM names those architectures x86_64 and aarch64. RHEL requires registration and the documented repository prerequisites. PostgreSQL 18 is the default: `documentdb` selects it, while `documentdb-17` and `documentdb-18` select a specific major.
6262

‎tests/installSelection.test.ts‎

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -80,12 +80,20 @@ describe("install selection links", () => {
8080
expect(parseInstallSelection("family=rpm&target=rocky9").selection?.method).toBe("packages");
8181
});
8282

83-
it("writes package choices to the URL only for packages", () => {
83+
it("keeps Docker links short unless package choices were changed", () => {
8484
expect(installSelectionUrlQuery(defaultInstallSelection)).toBe("method=docker");
8585
const packages = { ...defaultInstallSelection, method: "packages" as const };
8686
expect(installSelectionUrlQuery(packages)).toBe(installSelectionQuery(packages));
8787
});
8888

89+
it("restores package choices after switching to Docker and back", () => {
90+
const chosen = parseInstallSelection("method=packages&family=rpm&target=rhel9&pg=17&arch=aarch64").selection!;
91+
const docker = parseInstallSelection(installSelectionUrlQuery({ ...chosen, method: "docker" })).selection!;
92+
expect(docker.method).toBe("docker");
93+
const back = parseInstallSelection(installSelectionUrlQuery({ ...docker, method: "packages" })).selection;
94+
expect(back).toEqual(chosen);
95+
});
96+
8997
it("allows campaign parameters without treating them as install choices", () => {
9098
expect(parseInstallSelection("?utm_source=blog&method=docker").selection).toEqual(defaultInstallSelection);
9199
});

0 commit comments

Comments
 (0)