Need help making a "source code viewer" with the browse directive

I’m trying to give users of my website a way to view some of the source files in my web server. (find it here) The way I’ve done this is by creating a directory called “open” and then symlinking folders or files I want to share inside. The relevant part of my caddy file looks like this: {
	root open/
	ext .html .htm .php
	browse / raspbi_assets/styles/browse.tpl
	errors {
		404 ../error_pages/404.html

The problem is, when you click on a file that can be rendered into a webpage, like a html file, the browser usually renders the webpage instead of just displaying the raw text, like I want it to do. Even with php files, it just renders the parts it can! is there a way to stop the browser rendering the wepbages? I’ve tried in chrome, opera, vivaldi, firefox, and IE.

The user’s browser doesn’t see a difference between a HTML formatted file served conventionally and one served via browse middleware.

To tell the browser not to render it as HTML, you’ll need to force the Content-Type header via Caddy’s header directive. You’ll want text/plain.

You will run into an issue, however, when it comes to distinguishing between files you don’t want to set this header for, and the actual browse pages (which you definitely want rendering properly).

I’m repeating myself from another recent suggestion I made, but… The only way I can think of right now to do that would be to set up a subdomain (e.g. and set that header globally. This lets you take advantage of the redir directive’s if statements (which are actually documented better in the rewrite docs instead) to target requests for files that end in HTML-renderable extensions (e.g. if {file} ends_with ".html") and issue a redirect to the plaintext subdomain so they can be delivered non-renderable.

You’ll need to remove the ext directive from the block, though, or you won’t be able to rely on that trick because the browsers won’t be requesting them with the extension included. I’d probably leave the browse directive out of the plaintext block too, use it just to show the files themselves.

This works fine for me, thanks a lot :slight_smile:

1 Like

Actually, I’m kind of stuck. I’m trying

	redir {
		if {file} ends_with ".html"

But nothing seems to be happening. Is there anything I’m doing wrong?

Are there any rewrites in place that are changing the URI?

No. Also, if I browse to a folder that has a file called index.html in it, it still loads the webpage from the folder. I don’t think it’s possible to fix that with redid?


redir {
	if {file} ends_with ".html"

With just to{path}, I think Caddy is trying to redirect from the literal url {host}to, which isn’t going to occur. With a /, it’ll redirect from any path.

See this example from the Caddy redir docs:

redir 301 {
    if {>X-Forwarded-Proto} is http
    /  https://{host}{uri}
1 Like

Thanks, this works. However, if I browse to a folder that has a file inside called “index.html”, browsers still render the webpage.

That seems like odd behaviour to me, does it also occur if you have a .html file called something other than “index”?

Could be worth trying if {uri} instead of if {file}, too.

Doesn’t matter, I’ve got a proper github repo set up now. Thanks for the help

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.