I am currently trying to connect a frontend (React) to a backend (Express/nodejs) within Azure App Services. I am using Windows, since "Virtual applications and directories" are currently not available for Linux. However, according to my research, that is necessary in this case.
Backend sample: server.js
const express = require('express');
const app = express();
const port = 3003;
require("dotenv").config(); // For process.env
[...]
app.get("/api/getBooks", async (req, res) => {
const books = await Books.find();
res.send(books);
});
Frontend sample: App.js
const getBooks = () => {
axios.get('/api/getBooks')
.then(res => {
setBooks(res.data);
console.log("Got books: ")
console.log(res.data);
})
.catch(err => {
console.log(err);
})
}
Azure: Folder structure
site/server/server.js (Express)
site/wwwroot/index.html (React)
I successfully executed "npm install" via "Development Tools/Console".
The two are already connected via Virtual applications in Azure by using the following configuration.
The app generally loads succesfully. However, the connection to the backend is not working.
How can I start the node.js server now on Azure and make the proxy working?
I tried to start the server via "node server" on the console. But this does not seem to be working.
CodePudding user response:
I discovered two possible ways to solve this issue.
Assuming you have a client (client/App.js) and a server (server/server.js).
Serve the React App via node.js/Express
Based on the above architecture, a little bit of structure needs to be changed here. Because the React app is no longer output through its own server, but directly through Express.
In server/server.js, the following function must be called after express is declared.
app.use(express.static("../client/build"));
After defining some endpoints to the APIs, the last API node to define is the default route - the static output of the React build.
app.get("/", (res) => {
res.sendFile(path.resolve(__dirname, "client", "build", "index.html"));
});
Using an FTP client, you can now create the /client/build directory that will contain the built React app. Of course, another directory structure can be used.
The client files from the built React app are then simply uploaded there.
The deployment from the server is best done via Visual Studio Code and the Azure plugin.
In the above structure, /server would then be deployed to your in the Azure extension (Azure/App Services --> Right click on "myapp" --> Deploy to Web App ...)
Create two App Services
For example: myapp.azurewebsites.net & myapp-api.azurewebsites.net
myapp must simply contain the built React app (/build) in the wwwroot directory. This can be achieved via FTP.
The deployment from the /server to *myapp-api is best done via Visual Studio Code and the Azure plugin.
In the above structure, /server would then be deployed to myapp-api in the Azure extension (Azure/App Services --> Right click on "myapp-api" --> Deploy to Web App ...)
Also worth mentioning is that CORS should be configured, so that API calls can only be made from myapp.azurewebsites.net. This can be configured in the Azure Portal.
Occasionally the node dependencies have to be installed afterwards via the SSH console in the Azure Portal. For me it sometimes worked automatically and sometimes not.
To do this, simply change to the wwwroot directory (of the /server) and execute the following command.
npm cache clean --force && npm install
Combine this with React Router
React Router is usually used with React. This can be easily combined with a static-served web app from Express.
https://create-react-app.dev/docs/deployment/#other-solutions
How to handle React Router with Node Express routing
https://dev.to/nburgess/creating-a-react-app-with-react-router-and-an-express-backend-33l3