问题
At first everything works, and I can successfully store data by posting to the /upload route. But after 120 seconds of inactivity, the timeout event fires, and future attempts to store data fail. However the callback isn't called, so there is no "Unable to insert..."
message at the log.
var express = require('express');
var bodyParser = require('body-parser');
var winston = require('winston');
var config = require('./config');
var MongoClient = require('mongodb').MongoClient;
var app = express();
app.use(bodyParser.json());
app.post('/upload', function (req, res) {
req.json({status: 'recieved'});
req.app.locals.db.collection('data').insertOne(req.body, function(err, result) {
if (err === null) {
winston.info('Successfully inserted', {data: req.body});
} else {
winston.warn('Unable to insert', {cause: err});
}
});
});
const options = {
server: {
socketOptions: {
keepAlive: 1,
autoReconnect: true,
connectTimeoutMS: 5000
}
}
};
MongoClient.connect(config.databaseURI, function(err, db) {
if (err !== null) {
winston.error('Could not connect to database', {cause: err});
return;
}
db.on('timeout', function (err) {
winston.error('Mongo timed out', {cause: err});
});
app.locals.db = db;
app.listen(config.port, function() {
winston.info('Listening on port %d', config.port);
});
});
I based my code loosely off of this example. It has been suggested to me that I open a new connection to the DB after every request, but this is not best practice since internally, MongoClient.connect
is managing a pool. I also tried changing some of the options according to this. Still no luck.
回答1:
This solved the problem for me:
var options = {
server: {
socketOptions: {
keepAlive: 300000, connectTimeoutMS: 30000
}
},
replset: {
socketOptions: {
keepAlive: 300000,
connectTimeoutMS : 30000
}
}
};
Then put it in here:
if(process.env.MONGODB_URI) {
mongoose.connect(process.env.MONGODB_URI, options);
} else {
// Connect to local database
}
来源:https://stackoverflow.com/questions/38486384/mongodb-connection-to-mongolab-timing-out-in-nodejs-on-heroku