Caddy, jwt, login and Go templates/variables

(Ted Jangius) #1

I’m trying to setup a one page proxy Caddy site of sorts with jwt and login (oauth with Google) while using go variables and templates to show different html code sections depending of if you’re logged in or out, but I’m not getting the results I want.
So the page code I have is a basic js file with some code and a html file (index.html) including some {{define foo}} sections (like a navbar, a few different divs, and a toast). I’m using bootstrap 4(.3.1) with jquery (3.3.1), popper (1.14.7) and fontawesome (5.8.1).
When I initially visit the sites root it seems that the defined templates and such work, but as soon as I’ve authenticated, all template references seem to be ignored.
I’m unsure of how to properly set this entire thing up and I might’ve done basic stuff wrong.
What’s required to have the site working all the time? Should the web server have Go installed to properly parse the template and variable definitions (it’s not installed now, only Caddy is) or am I missing some other dependency?

This is my (probably wrongly) configured Caddyfile:

(g-auth) {
    jwt {
        path /
        except /images/favicon.ico
        allow domain domain.tld
        allow domain localhost
        redirect /login

localhost {
    tls off
    import g-auth
    root .
    log stdout
    errors stdout
    login {
        google client_id={$GOOGLE_CLIENT_ID},client_secret={$GOOGLE_CLIENT_SECRET}
        success_url /
        logout_url /
        cookie_domain domain.tld
        cookie_domain localhost
        cookie_secure false
        template index.html

Please, excuse my noobish ways. :slight_smile:

(Matthew Fay) #2

Howdy @adlib!

I don’t use Caddy templates myself, but I’ve got a hunch what’s going on from your Caddyfile.

    login {
        # ...stuff
        template index.html

You’ve actually got the login middleware rendering your index page for you!

The template subdirective of the login middleware is intended to render the login page (i.e. a login form).

Once you’re logged in, the login middleware doesn’t need to render any pages anymore, so it passes it off to Caddy. But you don’t have a standalone templates directive in your Caddyfile, so Caddy just passes the whole document up as-is without executing the templates.

So I think you want to change it so the login directive has template login.html (if there’s a login page, otherwise remove the subdirective) and you want to add templates somewhere in your site definition.

P.S.: It hurts me to see root . - would you indulge me by changing that to an absolute path? :stuck_out_tongue:

(Ted Jangius) #3

@Whitestrake, thanks a bunch for your answer!
Your reasoning seems logical and describes what’s happening more or less entirely.

Let me explain this setup of mine (which is a pure test setup), which I have running on my own Windows desktop. The finished site will be hosted on my FreeBSD server when I feel everything is working the way I want. Therefore this Caddyfile is just thrown together to get my test site working (also the reason for me turning tls off, logging to stdout and serving the site with root . I know it’s hardly best practice. Thanks for the pointer though!

Right now have a specific part of my index.html that’s rendered when I’m unauthenticated, and I want other parts to be rendered when I’ve logged in. But perhaps it’s a better practice to have a specific login page, and be redirected back to the index page upon login.

I’m trying to use the templates function with Caddy now, but I’m not sure I’m using them correctly. Since I’m using jwt I want to use information from the jwt cookie on the index page, but I’m not sure how to achieve that. Do templates only contain {{}} sections or should they contain entire go code definitions (such as the default login template for the login plugin,
How do I reach the logged in jwt data that the login page/template has, like {{.Authenticated}}, {{.Sub}} and {{.Name}}?

Thanks for your time and effort, by the way!

(Ted Jangius) #4

OK, so I’ve just made what I think is the world’s ugliest and worst workaround I can think of. Surely there’s a better way.
When returning to the index page after authenticating, I have a script tag with this:

    var jwt_token = '{{.Cookie "jwt_token"}}';

and then I parse the info in the variable with this js code:
var userinfo = JSON.parse(atob(jwt_token.split('.')[1])); and then I’m able to reach the relevant data with userinfo.sub, etc, so that I can populate html tags with this info.
This surely isn’t a good way to solve this … and there must be a better way.