MEAN Stack 应用程序:切换布尔值
MEAN Stack application: Toggle boolean value
我正在使用 mlab 和 mongojs 以及 Angular。当我尝试切换布尔值 (onStatus) 时,视图中的按钮从关闭切换到打开,但它使应用程序崩溃。当我签入数据库时,属性 已从文档中删除。下面的代码片段:
device.service.ts
toggleDevice(updatedStatus){
var headers = new Headers();
headers.append('Content-Type', 'application/json');
return this.http.put('/api/device/'+updatedStatus._id, JSON.stringify(updatedStatus), {headers: headers})
.map(res => res.json());
}
devices.component.ts
toggleDevice(device){
var currentStatus = device.onStatus;
var updatedStatus = {
_id: device._id,
name: device.name,
onStatus: !currentStatus
};
this.deviceService.toggleDevice(updatedStatus)
.subscribe(data => {
device.onStatus = !device.onStatus
});
}
devices.compoonents.html
<button class="btn" (click)="toggleDevice(device)" type="button">{{ device.onStatus ? 'Switch Off' : 'Switch On' }}</button>
API路由
var express = require('express');
var router = express.Router();
var database = require('../config/database');
var mongojs = require('mongojs');
var db = mongojs(database.url, ['devices'])
// GET : All devices
router.get('/devices', function(req, res, next){
db.devices.find(function(err, devices){
if(err) {
res.send(err);
}
res.json(devices);
});
});
// GET : Single device
router.get('/device/:id', function(req, res, next){
db.devices.findOne({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
});
// POST : Save a device
router.post('/device', function(req, res, next){
var device = req.body;
device.onStatus = false;
if(!device.name) {
res.status(400);
res.json({
"error": "Please add a name."
});
} else {
db.devices.save(device, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
}
});
// DELETE : A device
router.delete('/device/:id', function(req, res, next){
db.devices.remove({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
});
// PUT : Update a device
router.put('/device/:id', function(req, res, next){
var device = req.body;
var updatedDevice = {};
if(device.name) {
updatedDevice.name = device.name;
}
if(!updatedDevice){
res.status(400);
res.json({'Error': 'Name not specified'});
} else {
db.devices.update({_id: mongojs.ObjectId(req.params.id)}, updatedDevice, {}, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
}
db.devices.findOne({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
});
module.exports = router;
错误
/home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/lib/utils.js:98
process.nextTick(function() { throw err; });
^
Error: Can't set headers after they are sent.
at ServerResponse.OutgoingMessage.setHeader (_http_outgoing.js:344:11)
at ServerResponse.header (/home/chopin/Development/homeautomation/node_modules/express/lib/response.js:719:10)
at ServerResponse.send (/home/chopin/Development/homeautomation/node_modules/express/lib/response.js:164:12)
at ServerResponse.json (/home/chopin/Development/homeautomation/node_modules/express/lib/response.js:250:15)
at /home/chopin/Development/homeautomation/routes/devices.js:80:9
at /home/chopin/Development/homeautomation/node_modules/mongojs/lib/collection.js:50:5
at handleCallback (/home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/lib/utils.js:95:56)
at /home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/lib/cursor.js:674:5
at handleCallback (/home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/node_modules/mongodb-core/lib/cursor.js:171:5)
at nextFunction (/home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/node_modules/mongodb-core/lib/cursor.js:682:5)
[nodemon] app crashed - waiting for file changes before starting...
感谢您的帮助。
编辑:我应该提到错误只发生在我第二次切换按钮时。我假设因为某些原因这已从数据库中删除。名称和 ID 保留,但 onStatus 不保留。
在您的 /device/:id
PUT
端点上,您正在进行 update
和 findOne
异步调用,彼此独立,因此调用 res.json()
两次。尝试将 findOne
函数移动到 update
回调中。
即使已经发送,您仍在尝试发送响应。您所要做的就是在您的回复发送后添加 return
语句。
var express = require('express');
var router = express.Router();
var database = require('../config/database');
var mongojs = require('mongojs');
var db = mongojs(database.url, ['devices'])
// GET : All devices
router.get('/devices', function(req, res, next){
db.devices.find(function(err, devices){
if(err) {
res.send(err);
return;
}
res.json(devices);
});
});
// GET : Single device
router.get('/device/:id', function(req, res, next){
db.devices.findOne({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
return;
}
res.json(device);
});
});
// POST : Save a device
router.post('/device', function(req, res, next){
var device = req.body;
device.onStatus = false;
if(!device.name) {
res.status(400);
res.json({"error": "Please add a name."});
} else {
db.devices.save(device, function(err, device){
if(err) {
res.send(err);
return;
}
res.json(device);
});
}
});
// DELETE : A device
router.delete('/device/:id', function(req, res, next){
db.devices.remove({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
return;
}
res.json(device);
});
});
// PUT : Update a device
router.put('/device/:id', function(req, res, next){
var device = req.body;
var updatedDevice = {};
if(device.name) {
updatedDevice.name = device.name;
}
if(!updatedDevice){
res.status(400);
res.json({'Error': 'Name not specified'});
} else {
db.devices.update({_id: mongojs.ObjectId(req.params.id)}, updatedDevice, {}, function(err, device){
if(err) {
res.send(err);
return;
}
/*
* Commenting following line because
* you are sending a response in `findOne`
*/
// res.json(device);
db.devices.findOne({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
return;
}
res.json(device);
});
});
}
});
module.exports = router;
我正在使用 mlab 和 mongojs 以及 Angular。当我尝试切换布尔值 (onStatus) 时,视图中的按钮从关闭切换到打开,但它使应用程序崩溃。当我签入数据库时,属性 已从文档中删除。下面的代码片段:
device.service.ts
toggleDevice(updatedStatus){
var headers = new Headers();
headers.append('Content-Type', 'application/json');
return this.http.put('/api/device/'+updatedStatus._id, JSON.stringify(updatedStatus), {headers: headers})
.map(res => res.json());
}
devices.component.ts
toggleDevice(device){
var currentStatus = device.onStatus;
var updatedStatus = {
_id: device._id,
name: device.name,
onStatus: !currentStatus
};
this.deviceService.toggleDevice(updatedStatus)
.subscribe(data => {
device.onStatus = !device.onStatus
});
}
devices.compoonents.html
<button class="btn" (click)="toggleDevice(device)" type="button">{{ device.onStatus ? 'Switch Off' : 'Switch On' }}</button>
API路由
var express = require('express');
var router = express.Router();
var database = require('../config/database');
var mongojs = require('mongojs');
var db = mongojs(database.url, ['devices'])
// GET : All devices
router.get('/devices', function(req, res, next){
db.devices.find(function(err, devices){
if(err) {
res.send(err);
}
res.json(devices);
});
});
// GET : Single device
router.get('/device/:id', function(req, res, next){
db.devices.findOne({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
});
// POST : Save a device
router.post('/device', function(req, res, next){
var device = req.body;
device.onStatus = false;
if(!device.name) {
res.status(400);
res.json({
"error": "Please add a name."
});
} else {
db.devices.save(device, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
}
});
// DELETE : A device
router.delete('/device/:id', function(req, res, next){
db.devices.remove({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
});
// PUT : Update a device
router.put('/device/:id', function(req, res, next){
var device = req.body;
var updatedDevice = {};
if(device.name) {
updatedDevice.name = device.name;
}
if(!updatedDevice){
res.status(400);
res.json({'Error': 'Name not specified'});
} else {
db.devices.update({_id: mongojs.ObjectId(req.params.id)}, updatedDevice, {}, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
}
db.devices.findOne({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
}
res.json(device);
});
});
module.exports = router;
错误
/home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/lib/utils.js:98
process.nextTick(function() { throw err; });
^
Error: Can't set headers after they are sent.
at ServerResponse.OutgoingMessage.setHeader (_http_outgoing.js:344:11)
at ServerResponse.header (/home/chopin/Development/homeautomation/node_modules/express/lib/response.js:719:10)
at ServerResponse.send (/home/chopin/Development/homeautomation/node_modules/express/lib/response.js:164:12)
at ServerResponse.json (/home/chopin/Development/homeautomation/node_modules/express/lib/response.js:250:15)
at /home/chopin/Development/homeautomation/routes/devices.js:80:9
at /home/chopin/Development/homeautomation/node_modules/mongojs/lib/collection.js:50:5
at handleCallback (/home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/lib/utils.js:95:56)
at /home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/lib/cursor.js:674:5
at handleCallback (/home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/node_modules/mongodb-core/lib/cursor.js:171:5)
at nextFunction (/home/chopin/Development/homeautomation/node_modules/mongojs/node_modules/mongodb/node_modules/mongodb-core/lib/cursor.js:682:5)
[nodemon] app crashed - waiting for file changes before starting...
感谢您的帮助。
编辑:我应该提到错误只发生在我第二次切换按钮时。我假设因为某些原因这已从数据库中删除。名称和 ID 保留,但 onStatus 不保留。
在您的 /device/:id
PUT
端点上,您正在进行 update
和 findOne
异步调用,彼此独立,因此调用 res.json()
两次。尝试将 findOne
函数移动到 update
回调中。
即使已经发送,您仍在尝试发送响应。您所要做的就是在您的回复发送后添加 return
语句。
var express = require('express');
var router = express.Router();
var database = require('../config/database');
var mongojs = require('mongojs');
var db = mongojs(database.url, ['devices'])
// GET : All devices
router.get('/devices', function(req, res, next){
db.devices.find(function(err, devices){
if(err) {
res.send(err);
return;
}
res.json(devices);
});
});
// GET : Single device
router.get('/device/:id', function(req, res, next){
db.devices.findOne({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
return;
}
res.json(device);
});
});
// POST : Save a device
router.post('/device', function(req, res, next){
var device = req.body;
device.onStatus = false;
if(!device.name) {
res.status(400);
res.json({"error": "Please add a name."});
} else {
db.devices.save(device, function(err, device){
if(err) {
res.send(err);
return;
}
res.json(device);
});
}
});
// DELETE : A device
router.delete('/device/:id', function(req, res, next){
db.devices.remove({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
return;
}
res.json(device);
});
});
// PUT : Update a device
router.put('/device/:id', function(req, res, next){
var device = req.body;
var updatedDevice = {};
if(device.name) {
updatedDevice.name = device.name;
}
if(!updatedDevice){
res.status(400);
res.json({'Error': 'Name not specified'});
} else {
db.devices.update({_id: mongojs.ObjectId(req.params.id)}, updatedDevice, {}, function(err, device){
if(err) {
res.send(err);
return;
}
/*
* Commenting following line because
* you are sending a response in `findOne`
*/
// res.json(device);
db.devices.findOne({_id: mongojs.ObjectId(req.params.id)}, function(err, device){
if(err) {
res.send(err);
return;
}
res.json(device);
});
});
}
});
module.exports = router;