Другое событие NullPointerException
возникает, когда объявляется массив объектов, а затем сразу же пытается разыменовать его внутри.
String[] phrases = new String[10];
String keyPhrase = "Bird";
for(String phrase : phrases) {
System.out.println(phrase.equals(keyPhrase));
}
Этот конкретный NPE можно избежать, если порядок сравнения отменяется ; а именно, использовать .equals
для гарантированного непустого объекта.
Все элементы внутри массива инициализируются их общим начальным значением ; для любого типа массива объектов, это означает, что все элементы null
.
Вы должны инициализировать элементы в массиве перед доступом или разыменованием их.
String[] phrases = new String[] {"The bird", "A bird", "My bird", "Bird"};
String keyPhrase = "Bird";
for(String phrase : phrases) {
System.out.println(phrase.equals(keyPhrase));
}
Вот как я это делаю с современным синтаксисом, основанным на примере go-oleg.
Я добавил несколько комментариев в код.
./ db / mongodb.js
blockquote>< blockquote>const MongoClient = require('mongodb').MongoClient const uri = 'mongodb://user:password@localhost:27017/dbName' let _db const connectDB = async (callback) => { try { MongoClient.connect(uri, (err, db) => { _db = db return callback(err) }) } catch (e) { throw e } } const getDB = () => _db const disconnectDB = () => _db.close() module.exports = { connectDB, getDB, disconnectDB }
./ index.js
blockquote>// Load MongoDB utils const MongoDB = require('./db/mongodb') // Load queries & mutations const Users = require('./users') // Improve debugging process.on('unhandledRejection', (reason, p) => { console.log('Unhandled Rejection at:', p, 'reason:', reason) }) const seedUser = { name: 'Bob Alice', email: 'test@dev.null', bonusSetting: true } // Connect to MongoDB and put server instantiation code inside // because we start the connection first MongoDB.connectDB(async (err) => { if (err) throw err // Load db & collections const db = MongoDB.getDB() const users = db.collection('users') try { // Run some sample operations // and pass users collection into models const newUser = await Users.createUser(users, seedUser) const listUsers = await Users.getUsers(users) const findUser = await Users.findUserById(users, newUser._id) console.log('CREATE USER') console.log(newUser) console.log('GET ALL USERS') console.log(listUsers) console.log('FIND USER') console.log(findUser) } catch (e) { throw e } const desired = true if (desired) { // Use disconnectDB for clean driver disconnect MongoDB.disconnectDB() process.exit(0) } // Server code anywhere above here inside connectDB() })
./ users / index.js
blockquote>const ObjectID = require('mongodb').ObjectID // Notice how the users collection is passed into the models const createUser = async (users, user) => { try { const results = await users.insertOne(user) return results.ops[0] } catch (e) { throw e } } const getUsers = async (users) => { try { const results = await users.find().toArray() return results } catch (e) { throw e } } const findUserById = async (users, id) => { try { if (!ObjectID.isValid(id)) throw 'Invalid MongoDB ID.' const results = await users.findOne(ObjectID(id)) return results } catch (e) { throw e } } // Export garbage as methods on the Users object module.exports = { createUser, getUsers, findUserById }
Вы можете создать модуль mongoUtil.js
, который имеет функции как для подключения к mongo, так и для возврата экземпляра mongo db:
var MongoClient = require( 'mongodb' ).MongoClient;
var _db;
module.exports = {
connectToServer: function( callback ) {
MongoClient.connect( "mongodb://localhost:27017/marankings", function( err, db ) {
_db = db;
return callback( err );
} );
},
getDb: function() {
return _db;
}
};
Чтобы использовать его, вы сделаете это в своем app.js
:
var mongoUtil = require( 'mongoUtil' );
mongoUtil.connectToServer( function( err ) {
// start the rest of your app here
} );
И тогда, когда вам нужен доступ к mongo где-нибудь, вы можете сделать это:
var mongoUtil = require( 'mongoUtil' );
var db = mongoUtil.getDb();
db.collection( 'users' ).find();
Причина этого в том, что в узле, когда модули require
'd, они только загружаются / получаются один раз, так что вы только когда-нибудь закончите с одним экземпляром _db
, а mongoUtil.getDb()
всегда вернет тот же самый экземпляр.
Примечание, код не проверен.
app.js
в функции обратного вызова из connectToServer
. Если вы require
их в app.js
до _db
установлены, то вы получите неопределенные ошибки в других модулях.
– Mike
17 February 2018 в 22:40
go-oleg в принципе прав, но в эти дни вы (вероятно) не хотите использовать «mongodb» самостоятельно, скорее используйте некоторую фреймворк, которая сделает для вас много «грязной работы».
Например, мангуст является одним из самых распространенных. Это то, что мы имеем в нашем исходном файле server.js
:
const mongoose = require('mongoose');
const options = {server: {socketOptions: {keepAlive: 1}}};
mongoose.connect(config.db, options);
Это все, что необходимо для его настройки. Теперь используйте это в любом месте вашего кода
const mongoose = require('mongoose');
И вы получите тот экземпляр, который вы установили с помощью mongoose.connect
Если вы используете Express, то вы можете использовать модуль express-mongo-db , который позволяет вам получить соединение db в объекте запроса.
Установить
npm install --save express-mongo-db
server.js
var app = require('express')();
var expressMongoDb = require('express-mongo-db');
app.use(expressMongoDb('mongodb://localhost/test'));
routes / users.js
app.get('/', function (req, res, next) {
req.db // => Db object
});
Проверенное решение на основе принятого ответа:
mongodbutil.js:
var MongoClient = require( 'mongodb' ).MongoClient;
var _db;
module.exports = {
connectToServer: function( callback ) {
MongoClient.connect( "<connection string>", function( err, client ) {
_db = client.db("<collection name>");
return callback( err );
} );
},
getDb: function() {
return _db;
}
};
app.js :
var createError = require('http-errors');
var express = require('express');
var path = require('path');
var cookieParser = require('cookie-parser');
var logger = require('morgan');
var app = express();
app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'ejs');
app.use(logger('dev'));
app.use(express.json());
app.use(express.urlencoded({ extended: false }));
app.use(cookieParser());
app.use(express.static(path.join(__dirname, 'public')));
var mongodbutil = require( './mongodbutil' );
mongodbutil.connectToServer( function( err ) {
//app goes online once this callback occurs
var indexRouter = require('./routes/index');
var usersRouter = require('./routes/users');
var companiesRouter = require('./routes/companies');
var activitiesRouter = require('./routes/activities');
var registerRouter = require('./routes/register');
app.use('/', indexRouter);
app.use('/users', usersRouter);
app.use('/companies', companiesRouter);
app.use('/activities', activitiesRouter);
app.use('/register', registerRouter);
// catch 404 and forward to error handler
app.use(function(req, res, next) {
next(createError(404));
});
// error handler
app.use(function(err, req, res, next) {
res.locals.message = err.message;
res.locals.error = req.app.get('env') === 'development' ? err : {};
res.status(err.status || 500);
res.render('error');
});
//end of calback
});
module.exports = app;
activities.js - маршрут:
var express = require('express');
var router = express.Router();
var mongodbutil = require( '../mongodbutil' );
var db = mongodbutil.getDb();
router.get('/', (req, res, next) => {
db.collection('activities').find().toArray((err, results) => {
if (err) return console.log(err)
res.render('activities', {activities: results, title: "Activities"})
});
});
router.post('/', (req, res) => {
db.collection('activities').save(req.body, (err, result) => {
if (err) return console.log(err)
res.redirect('/activities')
})
});
module.exports = router;