quarto preview of a document outside website output-dir publishes Browse at .../../file.html and 404s
Nobody has claimed this yet.
Assessment
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Newbie friendliness
- 76/100
- Issue type
- Bug
- Clarity
- Clearly specified
- Activity status
- Quiet
- Tech stack
- typescript
- Domain
- cli
Research direction
Start in src/command/preview/preview.ts, focusing on previewInitialPath() and the handler-selection logic. Run the supplied website project reproduction with an omitted document, then trace how a path outside projectOutputDir is handled. Done means the draft is served successfully at the root URL instead of producing a ../ URL and a 404.
Written by the indexing model from the issue text.
Description
I have:
- searched the issue tracker for similar issues
- installed the latest version of Quarto CLI
- formatted my issue following the Bug Reports guide
Bug description
Bug description
In a website project with output-dir, previewing a document that is not written into that output directory still uses the website preview server (rooted at output-dir). The browse URL becomes something like:
Browse at http://localhost:PORT/../_draft.html
The browser/IDE normalizes that to /_draft.html, which is not served from output-dir, so the preview pane gets 404. The HTML file itself is rendered successfully next to the source.
This looks related to the #13804 / #14298 / #14300 preview-path work: #14300 fixed the single-file (isSingleFile) case, but not the case where a real website project renders a file outside projectOutputDir.
Steps to reproduce
Steps to reproduce
mkdir -p repro && cd repro
cat > _quarto.yml <<'EOF'
project:
type: website
output-dir: _output
render:
- index.qmd
EOF
cat > index.qmd <<'EOF'
---
title: Site
---
Hello site
EOF
cat > _draft.qmd <<'EOF'
---
title: Draft
format: html
---
Hello draft
EOF
# Build the site once so _output/ exists
quarto render
# Preview the draft (not in render list; HTML lands next to source)
quarto preview _draft.qmd --no-browser --no-watch-inputs --port 5678
Observe:
Output created: _draft.html
Browse at http://localhost:5678/../_draft.html
Then:
curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:5678/ # 200 (index)
curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:5678/_draft.html # 404
ls _draft.html _output/_draft.html
# _draft.html exists; _output/_draft.html does not
Same failure happens for a non-underscore file that is also omitted from project.render (so output is still written beside the source, not into _output).
Actual behavior
- Browse URL includes
../filename.html - Preview server is still
projectHtmlFileRequestHandlerrooted at_output - Requested path 404s
- VS Code / Cursor Quarto preview is unusable for these docs even though render succeeded
Suggested fix direction
In previewInitialPath() / handler selection in src/command/preview/preview.ts, when
relative(projectOutputDir(project), outputFile)
escapes the output dir (starts with ..), treat it like single-file preview (htmlFileRequestHandler + empty initial path) instead of the website handler.
Expected behavior
Preview should serve the rendered document successfully. For outputs outside projectOutputDir, it should fall back to the single-file handler / root URL behavior (as #14300 did for isSingleFile), e.g.:
Browse at http://localhost:PORT/GET /→ 200 with the draft HTML
Workarounds
quarto render draft.qmdand open the.htmldirectly- Temporarily move/rename
_quarto.ymlso preview runs in single-file mode - Add the file to the website
render:list so output lands underoutput-dir
Your environment
- IDE: Cursor / VS Code Quarto preview (
quarto preview … --no-browser --no-watch-inputs) - OS: macOS (darwin 25)
Quarto check output
Quarto 1.10.18
[✓] Checking versions of quarto binary dependencies...
Pandoc version 3.10.0: OK
Dart Sass version 1.101.0: OK
Deno version 2.7.14: OK
Typst version 0.15.1: OK
[✓] Checking Quarto installation......OK
Version: 1.10.18
Path: /Applications/quarto/bin
- Dominant language
- JavaScript
- Stars
- 6k
- Forks
- 458
- Avg merge
- 1d 8h
- Merged PRs (30d)
- 42
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
More from quarto-dev/quarto-cli
-
documentation
Difficulty 2/5 1-3 hours Newbie friendliness 86/100
quarto-dev/quarto-cli#14915 ·
-
binder bug
Difficulty 1/5 Under an hour Newbie friendliness 92/100
quarto-dev/quarto-cli#14907 · 3 comments · 1 reaction ·
-
brand bug
Difficulty 2/5 1-3 hours Newbie friendliness 68/100
quarto-dev/quarto-cli#14891 ·
-
brand bug html revealjs
Difficulty 2/5 1-3 hours Newbie friendliness 84/100
quarto-dev/quarto-cli#14882 ·
-
bug
Difficulty 2/5 1-3 hours Newbie friendliness 85/100
quarto-dev/quarto-cli#14875 ·
All issues in quarto-dev/quarto-cli
Similar issues
-
curation good first issue
Difficulty 2/5 1-3 hours Newbie friendliness 88/100
amponce/archive-movie-browser#186 ·
-
Difficulty 2/5 1-3 hours Newbie friendliness 86/100
clerk/javascript#9852 ·
-
bug p1 tools
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
-
Difficulty 2/5 1-3 hours Newbie friendliness 88/100
HarperFast/skills#96 ·
-
factory-active factory-automatic task-bug-reproduction-cannot-reproduce task-identify-harness-labels-done task-identify-issue-type-done
Difficulty 2/5 1-3 hours Newbie friendliness 84/100