在微博小系统的调试过程中:

(1)登入登出可以正常显示,就是在注册的时候网络连接突然停止,但是用户名和密码已经存入数据库中,报错为:undefined is not a function

错误主要指向Use.js中的一句话:mongodb.close();

解决方案:因为mongodb版本高于1.3.0,所以认为mongodb.close()这个函数未定义而当做函数来用,直接把mongodb.close()这句话注释掉则系统可以正常注册运行;

(2)注释掉mongodb.close()以后系统又出现mongodb经常会出现的错误db object already connecting, open cannot be called multiple times’

nodejs是异步线程,无论如何,都要用到db.open(),但是每次打开数据库访问完毕后还得对应关闭书裤裤db.close();

在上一步调试中注释掉关闭数据库,则数据库一直是处于打开状态,数据库还未关闭就在此打开则会出现db object already connecting, open cannot be called multiple times’的错误

此时的解决方案:

a:在数据库在此打开之前直接在前面加上一个mongodb.close()以确保每次数据库打开之前已经关闭数据库,经调试系统正常运行;

b.从open and close 行为改为 open once and reuse anywhere。程序启动的时候db.open一次,每次http请求直接访问数据库,扔掉db.open/db.close这2个多余的操作

原始的open + close方法:

var server_options={};
var db_options={w:-1}; var mongodb = require("mongodb"),
mongoserver = new mongodb.Server('localhost', 27017,server_options ),
db = new mongodb.Db('test', mongoserver, db_options); var http=require('http'); var server=http.createServer(function(req,res){
db.open(function(err,db){
if(err)return console.error(err);
console.log('* mongodb connected');
db.collection('foo').save({test:1},function(err,result){
res.end(JSON.stringify(result,null,2));
db.close();
});
}) });
server.listen(8080,function(){
console.log('server listen to %d',this.address().port);
});
setTimeout(function(){
//http.get('http://localhost:8080',function(res){console.log('request ok')});
//http.get('http://localhost:8080',function(res){console.log('request ok')});
},2000);

  扔掉db.open/db.close这2个循环对应操作的方法,让其最开始就一直处于打开状态

var server_options={'auto_reconnect':true,poolSize:5};
var db_options={w:-1}; var mongodb = require("mongodb"),
mongoserver = new mongodb.Server('localhost', 27017,server_options ),
db = new mongodb.Db('test', mongoserver, db_options); db.open(function(err,db){
if(err)throw err;
console.info('mongodb connected');
});
var http=require('http'); var server=http.createServer(function(req,res){
db.collection('foo').save({test:1},function(err,result){
res.end(JSON.stringify(result,null,2));
}); });
server.listen(8080,function(){
console.log('server listen to %d',this.address().port);
});
setTimeout(function(){
http.get('http://localhost:8080',function(res){console.log('request ok')});
http.get('http://localhost:8080',function(res){console.log('request ok')});
},2000); 

这样改会引入潜在问题:当并发访问>5时,因为同时可用的底层数据库连接只有5,从而导致了阻塞。

实际应用场景中,直接引用db对象并不是一个好主意。默认情况下,db的poolSize=5,意味着并发只有5, 要提高并发的话,把poolSize拉到10? 20? 50? 100? NO,我们需要的是能动态调整连接数的连接池,既能满足高峰期的连接数要求,也能在空闲期释放闲置的连接,而不是象mongodb的内置连接池那样保持固定连接数。怎么办?重新发明轮子吗?不,重用已有的连接池模块generic_pool,代码如下

var http=require('http'),
mongodb = require("mongodb"),
poolModule = require('generic-pool'); var pool = poolModule.Pool({
name : 'mongodb',
create : function(callback) {
var server_options={'auto_reconnect':false,poolSize:1};
var db_options={w:-1};
var mongoserver = new mongodb.Server('localhost', 27017,server_options );
var db=new mongodb.Db('test', mongoserver, db_options);
db.open(function(err,db){
if(err)return callback(err);
callback(null,db);
});
},
destroy : function(db) { db.close(); },
max : 10,//根据应用的可能最高并发数设置
idleTimeoutMillis : 30000,
log : false
}); var server=http.createServer(function(req,res){
pool.acquire(function(err, db) {
if (err) {
res.statusCode=500;
res.end(JSON.stringify(err,null,2));
} else {
db.collection('foo').save({test:1},function(err,result){
res.end(JSON.stringify(result,null,2));
pool.release(db);
});
}
});
});
server.listen(8080,function(){
console.log('server listen to %d',this.address().port);
});
setTimeout(function(){
http.get('http://localhost:8080',function(res){console.log('request ok')});
http.get('http://localhost:8080',function(res){console.log('request ok')});
},2000);

  c.对于mongodb数据库有一个问题:刷新得太快,或者多个用户同时访问数据库,数据库没来得及关闭,db object already connecting, open cannot be called multiple times这个错误就会出现

我们如果换成使用mongoose就不会出现这错误,因为对于mongoose而言,一旦连接好数据库,db就会处于open状态,不存在访问时要打开,然后又要关闭的规则,

这是用mongodb的操作方法:

User.get = function get(username, callback) {
mongodb.open(function(err, db) {
if (err) {
return callback(err);
}
//读取 users 集合
db.collection('users', function(err, collection) {
if (err) {
mongodb.close();
return callback(err);
}
//查找 name 属性为 username 的文档
collection.findOne({name: username}, function(err, doc) {
mongodb.close();
if (doc) callback (err, doc);
else callback (err, null);
});
});
});
};

  这是用mongoose的操作方法

User.get = function get(username, callback) {
users.findOne({name:username}, function(err, doc){
if (err) {
return callback(err, null);
}
return callback(err, doc);
});
};

  

以上a.b.c则为解决db object already connecting, open cannot be called multiple times’问题的三种方案总结

mongodb数据库调试问题:‘db object already connecting, open cannot be called multiple times’的更多相关文章

  1. nodejs:注册登录session出错以及连接Mongodb数据库时Error connecting to database解决方案

    (1)nodejs:注册登录session出错 解决办法: 在app.js 中将var MongoStore =  require(connect-mongo')改为var MongoStore =  ...

  2. mongoDB数据库插入数据时报错:db.collection is not a function

    nodejs连接mongodb插入数据时,发现mongoDB报错:db.collection is not a function.解决方法: 1.npm下载mongodb2.x.x版本替换3.x.x ...

  3. node.js连接MongoDB数据库,db.collection is not a function完美解决

    解决方法一. mongodb数据库版本回退: 这个错误是出在mongodb的库中,在nodejs里的写法和命令行中的写法不一样,3.0的api已经更新和以前的版本不不一样,我们在npm中没指定版本号的 ...

  4. MongoDB数据库(一):基本操作

    1.NoSQL的概念 "NoSQL"一词最早于1998年被用于一个轻量级的关系数据库的名字 随着web2.0的快速发展,NoSQL概念在2009年被提了出来 NoSQL最常见的解释 ...

  5. python学习笔记——mongodb数据库

    1 概述 1.1 文件管理阶段 优点:可以长期保存 能存储大量数据 缺点:没有结构化的组织 查找不方便 数据容易冗余 1.2 数据库管理阶段 有文件存储的优点,同时解决了文件存储的问题 缺点 : 操作 ...

  6. Python全栈 MongoDB 数据库(概念、安装、创建数据)

    什么是关系型数据库?           是建立在关系数据库模型基础上的数据库,借助于集合代数等概念和方法来处理数据库中的数据,             同时也是一个被组织成一组拥有正式描述性的表格( ...

  7. MongoDB 数据库的学习与使用

    MongoDB 数据库 一.MongoDB 简介(了解) ​ MongoDB 数据库是一种 NOSQL 数据库,NOSQL 数据库不是这几年才有的,从数据库的初期发展就以及存在了 NOSQL 数据库. ...

  8. python操作mongodb数据库

    一.MongoDB 数据库操作 连接数据库 import pymongo conn = pymongo.Connection() # 连接本机数据库 conn = pymongo.Connection ...

  9. mongoDB数据库

    1.mongoDB简介:mongoDB 为非关系数据库,集合(collection)关系数据库中的表,中存储的为json结构的文档,集合中的每一条记录都可以结构不同, 但必须都有_id字段(mongo ...

随机推荐

  1. win10系统 Visual Studio 2013 Color Theme Editor插件 安装出错

    下载这个版本,用vs2013打开安装即可:http://pan.baidu.com/s/1hrcfY1A

  2. 关于js中的类型内容总结(类型识别)

    JS 有7种数据类型: 6种原始类型:Boollean    String   Number    Null    Underfined   Symbol 引用类型:Object 类型识别主要有以下四 ...

  3. C语言-进制

    本文目录 • 一.十进制 • 二.二进制 • 三.八进制 • 四.十六进制 • 五.进制总结 • 六.变量与进制 • 七.printf的简单使用上一讲简单介绍了常量和变量,这讲补充一点计算机的基础知识 ...

  4. Java web 基础

  5. Global.asax 文件说明

    引用 来自  http://www.cnblogs.com/jianshao810/archive/2011/02/03/1948912.htm 在网上找了N多相关的东西总说的不够细,现在终于找到了. ...

  6. QF——关于iOS的强引用,弱引用及strong,retain,copy,weak,assignd的关系

    强引用和弱引用: 我们已经知道OC中的内存管理是通过“引用计数器”来实现的.一个对象的生命周期取决于它是否还被其他对象引用(是否retainCount=0).但在有些情况下,我们并不希望对象的销毁时间 ...

  7. selenium_python学习

    虫师selenium_python 学习:原文档 下载:http://download.csdn.net/detail/fnngj/6041329 具体参看selenium_python API : ...

  8. MyEclipse数据库反向生成实体类

    MyEclipse数据库反向生成实体类 “计应134(实验班) 凌豪” 当我们在开发项目涉及到的表太多时,一个一个的写JAVA实体类很是费事.然而强大的MyEclipse为我们提供简便的方法:数据库反 ...

  9. 解密电子书之四:MCU(freescale)

    谈完国产的君正,让我们再看看呛了君正财路的freescale iMX51. 这是freescale近期的主打产品,用的是ARM Cortex A8架构,主频在消费电子领域最高可达800MHz,在工业领 ...

  10. 一些User-Agent

    "Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.0)", "Mozilla/4.0 (compatible; MSIE ...