You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React/Node项目部署Replit/Heroku后页面空白问题求助

问题描述

我正在开发基于React和NodeJS/Express的电商服务,部署到Replit后仅本地服务器能正常运行,其他设备打开页面显示空白。推测是服务器配置存在问题,已查阅StackOverflow相关话题但未找到解决方案,希望获得配置修正的相关建议。


服务器index.js代码

const express = require('express');
const mongoose = require('mongoose');
const dotenv = require('dotenv');
const cors = require('cors');
const session = require('express-session');
const MongoStore = require('connect-mongo');
const path = require('path');

// set dotenv
dotenv.config();

// set app 
const app = express();
app.listen(process.env.PORT || 8000, () => {
  console.log('Server is running on port 8000', process.env.PORT)
});

// mongoDB connection 
mongoose
  .connect(process.env.MONGO_URL, {
    useNewUrlParser: true, 
    useUnifiedTopology: true 
  })
  .then(() => {console.log('DB connection succesfull')})
  .catch((err) => {console.log('DB error is', err)});

// middleware
app.use(cors({
  origin: ["http://localhost:3000", "http://localhost:8000"],
  methods: ['POST', 'PUT', 'GET', 'OPTIONS', 'HEAD', 'DELETE'],
  credentials: true
}))
if(process.env.NODE_ENV !== 'production') {
  app.use(
    cors({
      origin: ['http://localhost:3000'],
      credentials: true,
    })
  );
} 
app.use(express.json());
app.use(express.urlencoded({ extended: false}));
app.use(session({ 
  secret: process.env.SECRET,
  store: MongoStore.create(mongoose.connection),
  resave: false,
  saveUninitialized: false,
  /* This cause error in creating user session - no login available
  cookie: {
    secure: process.env.NODE_ENV == 'production',
  },*/
}));

// access to storage folder
app.use(express.static(path.join(__dirname, '/client/build')));

// import routes
const userRoute = require('./routes/user.routes');
const authRoute = require('./routes/auth.routes');
const productRoute = require('./routes/products.routes');
const orderRoute = require('./routes/order.routes');

// use routes
app.use('/api', userRoute);
app.use('/auth', authRoute);
app.use('/products', productRoute);
app.use('/orders', orderRoute);

app.get('*', (req, res) => {
  res.sendFile(path.join(__dirname, '/client/build/index.html'));
});

.env文件

MONGO_URL = mongodb+srv://user:pass@cluster0.hpidkxl.mongodb.net/prospero?retryWrites=true&w=majority
SECRET = pass
NODE_ENV = production
PASS_SEC = marc

配置文件

export const API_URL = (process.env.NODE_ENV === 'production')
? '/'
: 'http://localhost:8000/';

.gitignore文件

# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.

# dependencies
/node_modules
/.pnp
.pnp.js

# testing
/coverage

# production


# misc
.DS_Store
.env.local
.env.development.local
.env.test.local
.env.production.local

npm-debug.log*
yarn-debug.log*
yarn-error.log*

package.json文件

{
  "name": "04-prosperostore",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1",
    "start": "nodemon index.js"
  },
  "repository": {
    "type": "git",
    "url": "git+https://github.com/MarcinBieniek/ProsperoStore.git"
  },
  "keywords": [],
  "author": "",
  "license": "ISC",
  "bugs": {
    "url": "https://github.com/MarcinBieniek/ProsperoStore/issues"
  },
  "homepage": "https://github.com/MarcinBieniek/ProsperoStore#readme",
  "dependencies": {
    "@mui/x-data-grid": "^6.0.2",
    "axios": "^1.3.4",
    "bcryptjs": "^2.4.3",
    "connect-mongo": "^4.6.0",
    "cors": "^2.8.5",
    "crypto-js": "^4.1.1",
    "dotenv": "^16.0.3",
    "express": "^4.18.2",
    "express-session": "^1.17.3",
    "mongoose": "^7.0.1",
    "multer": "1.4.4",
    "nodemon": "^2.0.21",
    "path": "^0.12.7",
    "redux-thunk": "^2.4.2"
  }
}

配置修正建议

1. 修复CORS配置问题

当前代码重复调用app.use(cors()),生产环境下仅允许localhost来源,导致外部设备无法访问。调整方案:

  • 删除重复的CORS中间件
  • 生产环境指定Replit分配的应用域名作为允许来源,可通过环境变量注入
  • 修改后的CORS配置示例:
const allowedOrigins = process.env.NODE_ENV === 'production' 
  ? [process.env.REPLIT_APP_URL] // 替换为你的Replit公开域名,如https://xxx.replit.app
  : ["http://localhost:3000", "http://localhost:8000"];

app.use(cors({
  origin: allowedOrigins,
  methods: ['POST', 'PUT', 'GET', 'OPTIONS', 'HEAD', 'DELETE'],
  credentials: true
}));

注意:在Replit的环境变量面板中添加REPLIT_APP_URL,值为应用的公开访问域名。

2. 调整服务器监听逻辑

将服务器启动逻辑移至MongoDB连接成功后,避免服务启动但数据库未就绪的情况,同时修正端口打印信息:

// 替换原有的数据库连接和服务器启动代码
mongoose.connect(process.env.MONGO_URL, {
  useNewUrlParser: true, 
  useUnifiedTopology: true 
})
.then(() => {
  console.log('DB connection successful');
  const PORT = process.env.PORT || 8000;
  app.listen(PORT, () => {
    console.log(`Server is running on port ${PORT}`);
  });
})
.catch((err) => {console.log('DB error is', err)});

3. 静态文件路径验证

确认Replit中client/build目录存在且路径正确,可添加日志打印验证:

const buildPath = path.join(__dirname, '/client/build');
console.log('Static files path:', buildPath);
app.use(express.static(buildPath));

4. 修正启动脚本

生产环境使用nodemon不合适,替换为node直接启动,保留dev脚本用于开发:

"scripts": {
  "test": "echo \"Error: no test specified\" && exit 1",
  "start": "node index.js",
  "dev": "nodemon index.js"
}

5. 完善会话Cookie配置

取消注释Cookie配置,添加sameSite属性适配生产环境HTTPS:

app.use(session({ 
  secret: process.env.SECRET,
  store: MongoStore.create(mongoose.connection),
  resave: false,
  saveUninitialized: false,
  cookie: {
    secure: process.env.NODE_ENV === 'production',
    sameSite: process.env.NODE_ENV === 'production' ? 'none' : 'lax',
    maxAge: 24 * 60 * 60 * 1000 // 可选,设置Cookie有效期为1天
  },
}));

注:sameSite: 'none'必须配合secure: true使用,Replit公开域名默认使用HTTPS,符合要求。

6. 确认环境变量加载

Replit不会自动加载本地.env文件,需在Replit的环境变量面板中手动添加所有.env中的变量(如MONGO_URL、SECRET等)。

内容的提问来源于stack exchange,提问作者MarcinB

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.27 00:35:21