В Java все переменные, которые вы объявляете, на самом деле являются «ссылками» на объекты (или примитивы), а не самими объектами.
При попытке выполнить один метод объекта , ссылка просит живой объект выполнить этот метод. Но если ссылка ссылается на NULL (ничего, нуль, void, nada), то нет способа, которым метод будет выполнен. Тогда runtime сообщит вам об этом, выбросив исключение NullPointerException.
Ваша ссылка «указывает» на нуль, таким образом, «Null -> Pointer».
Объект живет в памяти виртуальной машины пространство и единственный способ доступа к нему - использовать ссылки this
. Возьмем этот пример:
public class Some {
private int id;
public int getId(){
return this.id;
}
public setId( int newId ) {
this.id = newId;
}
}
И в другом месте вашего кода:
Some reference = new Some(); // Point to a new object of type Some()
Some otherReference = null; // Initiallly this points to NULL
reference.setId( 1 ); // Execute setId method, now private var id is 1
System.out.println( reference.getId() ); // Prints 1 to the console
otherReference = reference // Now they both point to the only object.
reference = null; // "reference" now point to null.
// But "otherReference" still point to the "real" object so this print 1 too...
System.out.println( otherReference.getId() );
// Guess what will happen
System.out.println( reference.getId() ); // :S Throws NullPointerException because "reference" is pointing to NULL remember...
Это важно знать - когда больше нет ссылок на объект (в пример выше, когда reference
и otherReference
оба указывают на null), тогда объект «недоступен». Мы не можем работать с ним, поэтому этот объект готов к сбору мусора, и в какой-то момент VM освободит память, используемую этим объектом, и выделит другую.
Хорошо, поэтому моя основная проблема заключалась в том, что я не смог получить _id документа, который я вставил, не будучи в состоянии проверить, был ли он обновлен / найден или вставлен. Однако я узнал, что вы можете создать свой собственный идентификатор.
id = mongoose.Types.ObjectId();
Chatrooms.findOneAndUpdate({Roomname: room.Roomname},{ $setOnInsert: {_id: id, status: true, userNum: 1}}, {new: true, upsert: true}, function(err, doc) {
if(err) console.log(err);
if(doc === null) {
// inserted document logic
// _id available for inserted document via id
} else if(doc.status) {
// found document logic
}
});
Обновить
API Mongoose v4.4.8
passRawResult: если true, передает исходный результат от драйвера MongoDB в качестве третьего параметра обратного вызова.
Я не знаю, как это полностью отключилось, но так же, как всегда, был «третий» аргумент для всех методов .XXupdate()
, который в основном является сырым ответом от драйвера. Это всегда говорит вам, будет ли документ «вставлен» или нет:
Chatrooms.findOneAndUpdate(
{ "Roomname": room.Roomname },
{ "$setOnInsert": {
"status": true, "userNum": 1
}},
{ "new": true, "upsert": true },
function(err, doc,raw) {
if(err) console.log(err);
// Check if upserted
if ( raw.lasErrorObject.n == 1 && !raw.lastErrorObject.updatedExisting ) {
console.log("upserted: %s", raw.lastErrorObject.upserted);
}
console.log("DOC " + doc)
if (doc.status) {
// FOUND ROOM SATTUS IS TRUE LOGIC
console.log(doc);
// return callback(true)
}
});
Что скажет вам _id
документа, который был только что поднят.
От чего-то вроде это в «сыром» ответе:
{ lastErrorObject:
{ updatedExisting: false,
n: 1,
upserted: 55e12c65f6044f57c8e09a46 },
value: { _id: 55e12c65f6044f57c8e09a46,
status: true,
userNum: 1
__v: 0 },
ok: 1 }
Полный воспроизводимый список:
var async = require('async'),
mongoose = require('mongoose'),
Schema = mongoose.Schema;
mongoose.connect('mongodb://localhost/test');
var testSchema = new Schema({
name: String
});
var Test = mongoose.model('Test', testSchema, 'test');
async.series(
[
function(callback) {
Test.remove({},callback);
},
function(callback) {
async.eachSeries(
["first","second"],
function(it,callback) {
console.log(it);
Test.findOneAndUpdate(
{ "name": "Bill" },
{ "$set": { "name": "Bill" } },
{ "new": true, "upsert": true },
function(err,doc,raw) {
console.log(raw),
console.log(doc),
callback(err);
}
);
},
callback
);
}
],
function(err) {
if (err) throw err;
mongoose.disconnect();
}
);
Какие выходы:
first
{ lastErrorObject:
{ updatedExisting: false,
n: 1,
upserted: 55e2a92328f7d03a06a2dd6b },
value: { _id: 55e2a92328f7d03a06a2dd6b, name: 'Bill', __v: 0 },
ok: 1 }
{ _id: 55e2a92328f7d03a06a2dd6b, name: 'Bill', __v: 0 }
second
{ lastErrorObject: { updatedExisting: true, n: 1 },
value: { _id: 55e2a92328f7d03a06a2dd6b, name: 'Bill', __v: 0 },
ok: 1 }
{ _id: 55e2a92328f7d03a06a2dd6b, name: 'Bill', __v: 0 }
upsert:true
всегда есть ответ. Это связано с тем, что в этом случае мангуст получает ответ от него в первую очередь. Вы делаете что-то неправильно / другое.
– Blakes Seven
30 August 2015 в 06:31
Chatrooms.findOneAndUpdate({Roomname: RoomHash.roomhash},{ $setOnInsert: { userNum: 1, status: true}}, {new: true,upsert: true}, function(err, doc, raw) { console.log("DOC: %j" , doc); console.log("RAW: %j", raw); if(err) console.log(err);
– Sarodh Uggalla
30 August 2015 в 06:34
Версия 4.1.10 Mongoose имеет опцию, называемую passRawResult
, которая, если установлена в true
, вызывает передачу параметра raw
. Если оставить этот параметр, по умолчанию он равен false
и вызывать raw
всегда undefined
:
passRawResult: если true, передает исходный результат от драйвера MongoDB в качестве третьего обратного вызова параметр
blockquote>http://mongoosejs.com/docs/api.html#query_Query-findOneAndUpdate
Боюсь, что использование FindOneAndUpdate не может делать то, что вы хотите, потому что у него нет промежуточного программного обеспечения и сеттера, и он упоминает об этом docs:
. Хотя значения передаются в соответствующие типы при использовании findAndModify, следующие не применяются:
http://mongoosejs.com/docs/api.html найти его в findOneAndUpdate, если вы хотите получить документы перед обновлением, а документы после обновления вы можете сделать это таким образом :
Model.findOne({ name: 'borne' }, function (err, doc) {
if (doc){
console.log(doc);//this is ur document before update
doc.name = 'jason borne';
doc.save(callback); // you can use your own callback to get the udpated doc
}
})
надеюсь, что это поможет вам
findOneAndUpdate
– Sarodh Uggalla
29 August 2015 в 00:08