Я начинаю новый проект. В настоящее время у меня есть такая структура из корневой папки:
/app (CRA frontend app)
/server (Node.js Express app)
Dockerfile
docker-compose.yml
Мои требования следующие:
Разработка
Производство
То, где я сейчас нахожусь, где-то посередине. Я не знаю, как правильно настроить Docker, чтобы все это работало, и я действительно не знаю, как структурировать мое приложение React и приложение Express во время разработки. Производственная часть кажется проще, когда я знаю, как структурировать часть разработки ... + Nginx в качестве прокси для приложения Express?
В настоящее время я создаю контейнер Docker, который запускает контейнер, в котором работает горячая перезагрузка и т. д., Но я не знаю, как настроить часть Express, чтобы они хорошо работали вместе ...?
Любая помощь очень ценится.
Спасибо





Очень широкий вопрос. Возможно, лучше разбить его на более прямые вопросы. В любом случае, я не думаю, что настройка вашего разработчика в Docker идеальна. Вместо этого создайте свое приложение с помощью CRA. Затем разверните в Docker.
В моих собственных проектах у меня есть контейнер докеров, на котором запущен сервер узла, который обслуживает приложение реакции с помощью SSR.
Вот часть докера. Обратите внимание, что ваш package.json должен иметь сценарий с именем start:prod, чтобы это работало. Затем этот сценарий запускает ваше приложение в производстве.
// --- Dockerfile
# Pulled from docker hub and has everything
# needed to run a node project
FROM node:alpine
ENV PORT 3000
# Navigate (cd) to the app folder in the docker container
WORKDIR /usr/src/app
# Copy all package.json / package-lock.json etc. to the root folder
# Executed on build: docker build .
COPY ./package*.json ./
RUN npm i
# copy entire project into docker container
COPY . .
# build front-end with react build scripts and store them in the build folder
RUN npm run build
EXPOSE 3000
CMD ["npm", "run", "start:prod"]
Вот экспресс-сервер, который запустит сервер.
// -- server.js
import express from "express";
import router from "./controller/index";
const app = express();
const port = 4000;
// Tell the app to use the routes above
app.use(router);
// start the app
app.listen(port, () => {
console.info(`express running on port ${port}`);
});
Вот файл controller/index.js, который вам понадобится для запуска
// -- controller/index.js
import express from "express";
import path from "path";
import serverRenderer from '../middleware/renderer';
const router = express.Router();
// root (/) should always serve our server rendered page
router.use('^/$', serverRenderer());
// other static resources should just be served as they are
router.use(express.static(
path.resolve(__dirname, '..', '..', 'build'),
{ maxAge: '30d' },
));
export default router;
И, наконец, средство визуализации, которое отображает приложение на сервере.
// -- renderer.js
import React from "react";
import { renderToString } from "react-dom/server";
import App from "../../src/App";
const path = require("path");
const fs = require("fs");
export default () => (req, res) => {
// point to html file created by CRA's build tool
const filePath = path.resolve(__dirname, "..", "..", "build", "index.html");
fs.readFile(filePath, "utf8", (error, htmlData) => {
if (error) {
console.error("error", error);
return response.status(404).end();
}
// render the app as string
const html = renderToString(<App />);
// inject rendered app into final html and send
return res.send(
htmlData
.replace('<div id = "root"></div>', `<div id = "root">${html}</div>`)
);
})
}
Вам понадобится bootstrap.js для поддержки определенных пакетов.
// -- bootstrap.js
require('ignore-styles');
require('url-loader');
require('file-loader');
require('babel-register')({
ignore: [/(node_modules)/],
presets: ['es2015', 'react-app'],
plugins: [
'syntax-dynamic-import',
'dynamic-import-node'
]
});
require("./index");
Вы можете найти подробности здесь: https://blog.mytoori.com/react-served-by-express-running-in-docker-container
Спасибо, попробую! Извините за расплывчатый вопрос :) Дам вам знать, работает ли это для меня.
Я получаю сообщение об ошибке const html = renderToString (<App />) синтаксическая ошибка неожиданный токен
нужно ли нам ядро babel или babel cli, когда я проверяю наличие ошибки, это показывает, что любая идея по этому поводу
ваша команда должна быть npm run prod: start или npm run build?
в файле index.js папки / server должны ли мы автоматически запрашивать bootstrap.js ??
@DILEEPTHOMAS, я подозреваю, что вы могли использовать server / index.js, когда вам нужно импортировать bootstrap.js. Моя лучшая рекомендация - проверить исходный исходный код на github: github.com/Giwan/fe-docker-dynamic-be/blob/ssr/server/server .js (обратите внимание, что имена файлов там немного отличаются)
Ваш вопрос очень расплывчатый. Было бы лучше разбить ваш проект на более прямые вопросы. В любом случае, я не думаю, что рекомендуется запускать настройку разработчика в Docker (если вы не знаете, что делаете), вместо этого было бы лучше построить ваше приложение в обычном режиме с CRA. Затем разверните в Docker.