0

Note: I'm focused on a Web build right now, so this question is focused on solving some very specific to web usage.

I'm building a React Native application where the underlying infrastructure is reliant on cookie auth for normal users. I'm using Expo as the framework. To make the cookie stuff as smooth as possible I run all the relevant services locally, a self-signed cert that the system trusts, and use an nginx reverse proxy to keep the routes matching.

Thus, all requests are made to routes like: https://portal.company.com https://api.company.com/billing

and nginx is doing a proxy_pass to http://localhost:5000, http://localhost:5001, and so forth.

I made a previous Vite app that had no issue responding to requests on subpaths with this configuration:

    server {
        listen 443 ssl;
        server_name portal.company.com;
        ssl_certificate "cert-path//portal-cert.pem";
        ssl_certificate_key "cert-path//portal-private.pem";
        ssl_session_cache    shared:SSL:1m;
        ssl_protocols       TLSv1.3;
        ssl_session_timeout  5m;

        ssl_ciphers  HIGH:!aNULL:!MD5;
        ssl_prefer_server_ciphers  on;

        proxy_set_header Host $host; # MAGIC
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";

        location / {
            include includes/cors;
            proxy_pass https://localhost:5173;
        }
    }

However, when I reused that for the Expo app, subpaths kept throwing up a "Not found" page with a 404, and it was pretty clear my code wasn't running. It was clearly the classic "running a SPA app" issue where it's only technically responding to requests at the app's root, but I didn't see a clear way of getting the request to the root.

1 Answer 1

0

See comments, but this solution is a bit hacky - I still want to make it visible because it helped me with running locally on a defined URL instead of just localhost, but I don't want people to think this is the proper way to do things.

At first I started to think the answer was to try something other than proxy_pass, becuase I needed Expo to 'see' the request where the code was actually executing. I think my instinct was right, but what I was wrong about was that proxy_pass is still the right tool for the job. Instead of messing with the subpaths via the location flag, you instead have it handle static files one way, and everything else with the $request_uri appended to the route:

location ~* \.(?:ico|css|js|map|png|jpg|jpeg|gif|svg|woff2|mp3?)$ {
    proxy_pass http://localhost:8081;
}

location = / {
    proxy_pass http://localhost:8081/;
}

location / {
    # hack
    proxy_pass http://localhost:8081/$request_uri;
}

Source

With that, Expo started reacting to subpaths as expected. To be clear, this is a bit of a hack - the source does not include the / before $request_uri and for good reason - that introduces a double-slash. However, I've found said double-slash is what makes Expo actually process the request instead of ignoring it and throwing a 404 at me.

Hope this helps someone else. I did some furious searching and failed to get an answer until I started digging into nginx documentation.

Sign up to request clarification or add additional context in comments.

2 Comments

There's no point in making the configuration that complicated, especially with regular expressions. It does make sense to serve requests for static files directly with nginx without involving the backend app, but that's not what you're doing here. The configuration you've provided is functionally equivalent to location / { proxy_pass http://localhost:8081; }. The only difference is that in the third location you end up doubling the leading slash in the request URI.
So quick preface, this is only for local dev. That extra slash was what makes Expo process the request - without it, I'm back to getting 404s from Expo. Clearly this is related to the fix to get SPAs to work on GitHub pages, using hash routes. If there was a clear way to specify your URL that you're running on, I'd take it; I've only found things that are kind of close to it but not quite the fit, or entail altering @expo/cli code. I'll update my Q/A to explain that what I'm offering is a hack at least, now that I know the extra slash was what 'fixed' it. Thanks for catching th

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.