2

I just launched my first working Back4App application. This application is a React app with the React Router. To make it work, I did a npm run build and uploaded all the files under the 'public' folder (found at Cloud Code).

Now everything is in place, I can go to the index page, that is https://[myapp].b4a.app, and everything works well. But when I go to a subpage and do a refresh, I stumble upon a 403 - {"error":"unauthorized"} error.

I do understand this happens because the user tries to go where my app is not served. Normally I would put Nginx or something similar in the middle; so I could catch those requests and redirect them to the SPA.

But now, as I don't have control on the backend side at all, how can I make this work?

Jacob van Lingen
  • 8,989
  • 7
  • 48
  • 78
  • 1
    Please take a look at this link: https://help.back4app.com/hc/en-us/articles/360031634031-Routing-Single-Page-Application- – Davi Macêdo Dec 27 '21 at 04:20
  • @DaviMacêdo Awesome, I totally missed that piece of documentation. Please rewrite your comments as an answer! – Jacob van Lingen Dec 27 '21 at 07:18
  • I was looking for the solution but I can't find it in the docs, can you answer so that I have a solution that works for other people too. – Franj Jan 26 '22 at 11:46
  • @Franj I didn't want to take Davi Macêdo's place, but as time did pass I recon it's ok! So, check the answer below. – Jacob van Lingen Jan 27 '22 at 08:18

1 Answers1

1

Back4App uses Express, a Node.js web application framework, as a backend. Luckily for us, we can add a routing file ourselves. Just go to your Cloud Code section and add an app.js file in the cloud folder:

enter image description here

The Routing & Single Page Application FAQ states:

To configure the routing to your SPA in Express, you should use the GET HTTP method to include an HTML file and in the response, we are going to deliver the index.html file to the browser.

It means you have the route all possible GET request to your index.html, except of the Back4App reserved paths (like 'login' and 'logout' for instance). A working basic file can also be found from the documentation:

const path = require('path');
const unRoutedPaths = ['apps','batch','requestPasswordReset','files','login','logout','user','users','Roles','parse','schemas','functions','classes','aggregate','cloud_code','config','hooks','push_audiences','installations','push','sessions','events','jobs','export_progress','export_data','graphql','import_data'];

app.use((req, res, next) => {
    const pathParts = req.path.split('/').filter((p) => p !== '');
    if (req.path.indexOf('.') > 0 || unRoutedPaths.includes(pathParts[0])) {
        next();
    } else {
        res.sendFile(path.join(`${__dirname}/public/index.html`));
    }
});
Jacob van Lingen
  • 8,989
  • 7
  • 48
  • 78
  • This code no longer works with ionic v6 and angular v13 in Parse Server 4.5.0 – Franj Apr 11 '23 at 22:29
  • I don't think it matters which frontend framework you are running, as long a you put your files in the public folder. But I updated the unRoutePaths with 'graphql' and 'import_data', as the documentation did this as well. To be sure you could go to [documentation](https://help.back4app.com/hc/en-us/articles/360031634031-Routing-Single-Page-Application-) yourself! – Jacob van Lingen Apr 12 '23 at 12:34