Node + Ts + Mongodb 增删改查封装
俗言有道,自奉必减几分方好,处世能退一步为高。
之前有很多的前后端开发,数据库其实是一个项目运行的必须的一环,也是很重要的一环。
数据库千千万,合适的到底有哪些?
数据库有哪些
- 关系型数据库
- Oracle
- MySQL
- 非关系型数据库
- NoSQL
- 键值存储数据库(key-value)
- Memcached
- Redis
- MemcacheDB
- 列存储(Column-oriented)数据库
- Cassandra
- HBase
- 面向文档(Document-Oriented)数据库
- MongoDB
- CouchDB
- 图形数据库
- Neo4J
- InforGrid
MongoDB
几句话。
不管是kv的内存型redies,还是文档型的mongodb,上手都很都很简单,而且,文档型数据库跟json很像啊,那就更容易理解了,再加上性能还凑合,就他了呗,而且还有mongoose这种玩意,写着毫无压力,个把小时就上手了
敲黑板!时间就是金钱啊,先上了再说玩会了这个流程,是什么数据库不重要,都是store,根据配置切不同实现就完事。至于后面要考虑的存和取的性能和场景,不需要一开始就过度考虑。
妄论一下。
1.Node在io并发处理比较擅长,mongodb也是擅长读写的,两者这方面很契合,mongodb在大数据方面也比较擅长。
2.mongodb是文档数据,数据结构是bson,也可以说是json,而众所周知json是来源于JavaScript object,nodejs又是以js为编程语言。
Js为底层语言
很直观的体现了,在进入Mongo时,执行1 + 1
会返回2
,dddd
看到这里,其实也跃跃欲试了,如何像博主一样花费30分钟就可以玩得转它?
我知道你很急,但是你先别急。
安装流程
很保姆级了,往下看。
下载。
安装。
无需配置环境变量。
能理解到这一步,其实对shell这类,还有系统这类有一定认识了,mongo.exe其实就是一个cmd程序。
我的bin文件夹
打开目录下的终端,这里不管是cmd还是terminal都可以
先别急着一步步操作,看教程是为了学会,请耐心通读本段落
mongod.exe是创建mongodb的进程,也就是打开数据库的程序
我在D:/创建了文件夹Databases/Mongodb
刚创建文件夹肯定不会像我一样有文件。。。
mongod.exe --dbpath "D:/Databases/Mongodb/"
执行完后,你会发现你的文件夹里面生成了文件。
然后,
打开数据库。。。
mongosh.exe是一个可以操作mongodb的命令行程序
mongosh.exe
到这里,你拥有了一个Mongodb数据库。
使用方法
创建数据库
尝试使用一个自定义的数据库:
> use test_db
switched to db test_db
> db
test_db
>
> show dbs
admin 40.00 KiB
config 72.00 KiB
local 72.00 KiB
test_db 8.00 KiB
>
“为什么我use的test_db不在里面?”
> db.test_db.insert({"name":"测试"})
DeprecationWarning: Collection.insert() is deprecated. Use insertOne, insertMany, or bulkWrite.
{
acknowledged: true,
insertedIds: { '0': ObjectId("63917571c6696a553b3fc68c") }
}
> show dbs
admin 40.00 KiB
config 72.00 KiB
local 72.00 KiB
test_db 8.00 KiB
>
出现了。
在这一步,Mongodb会在你插入数据的时候自动创建数据库。(很方便)
删除数据库
> db.dropDatabase()
{ ok: 1, dropped: 'test_db' }
>
集合
列出
show collections
创建
db.createCollection(name, options)
options
字段 | 类型 | 描述 |
---|---|---|
capped | 布尔 | (可选)如果为 true,则创建固定集合。固定集合是指有着固定大小的集合,当达到最大值时,它会自动覆盖最早的文档。当该值为 true 时,必须指定 size 参数。 |
autoIndexId | 布尔 | 3.2 之后不再支持该参数。(可选)如为 true,自动在 _id 字段创建索引。默认为 false。 |
size | 数值 | (可选)为固定集合指定一个最大值,即字节数。如果 capped 为 true,也需要指定该字段。 |
max | 数值 | (可选)指定固定集合中包含文档的最大数量。 |
删除
db.collection.drop()
文档
于集合下的一个子函数,可以理解为集合的下一级,而文档内存储的就是业务逻辑中的主要内容
插入
{% codeblock lang:js %}
db.COLLECTION_NAME.insert(document)
或
db.COLLECTION_NAME.save(document)
{% endcodeblock %}
更新
{% codeblock lang:js %}
db.collection.update(
{
upsert:
multi:
writeConcern:
}
)
{% endcodeblock %}
DB类封装
{% codeblock lang:ts %}
import * as mongodb from 'mongodb';
import { DBI } from './interfaces';
export class Db implements DBI {
public client: mongodb.MongoClient | undefined;
public db: mongodb.Db | undefined;
static instance: Db | null;
static getInstance() {
if (!Db.instance) throw "No Event!"
return this.instance;
}
constructor(DB_CONN_STRING: string, DB_NAME: string) {
this.connection(DB_CONN_STRING, DB_NAME);
}
/**
* 插入数据
* @param collectionName 集合名称
* @param doc 内容
* @returns
*/
public insert<T = mongodb.Document>(collectionName: string, doc: mongodb.OptionalId<T>): Promise<mongodb.InsertOneResult<mongodb.Document>> {
return new Promise<mongodb.InsertOneResult<mongodb.Document>>(async (resolve, reject) => {
try {
this.db?.collection(collectionName).insertOne(doc).then(resolve).catch(err => {
throw err;
});
} catch (err) {
reject(false);
}
});
}
/**
* 插入多数据
* @param collectionName 集合名称
* @param docs[] 内容数组
* @returns
*/
public insertMany<T = mongodb.Document>(collectionName: string, docs: mongodb.OptionalId<T>[]): Promise<mongodb.InsertManyResult<mongodb.Document>> {
return new Promise<mongodb.InsertManyResult<mongodb.Document>>(async (resolve, reject) => {
try {
this.db?.collection(collectionName).insertMany(docs).then(resolve).catch(err => {
throw err;
});
} catch (err) {
reject(false);
}
});
}
public delete<T = mongodb.Document>(collectionName: string, filter: mongodb.Filter<T>): Promise<mongodb.DeleteResult> {
return new Promise<mongodb.DeleteResult>(async (resolve, reject) => {
try {
this.db?.collection(collectionName).deleteOne(filter).then(resolve).catch(err => {
throw err;
});
} catch (err) {
reject(false);
}
}).catch(err => {
return err;
});
}
public deleteMany<T = mongodb.Document>(collectionName: string, filter: mongodb.Filter<T>): Promise<mongodb.DeleteResult> {
return new Promise<mongodb.DeleteResult>(async (resolve, reject) => {
try {
this.db?.collection(collectionName).deleteMany(filter).then(resolve).catch(err => {
throw err;
});
} catch (err) {
reject(false);
}
}).catch(err => {
return err;
});
}
public update<T = mongodb.Document>(collectionName: string, filter: mongodb.Filter<T>, update: mongodb.UpdateFilter<T>): Promise<mongodb.UpdateResult> {
return new Promise<mongodb.UpdateResult>(async (resolve, reject) => {
try {
this.db?.collection(collectionName).updateOne(filter, update).then(resolve).catch(err => {
throw err;
});
} catch (err) {
reject(false);
}
}).catch(err => {
return err;
});
}
public find<T = mongodb.Document>(collectionName: string, filter: mongodb.Filter<T>): Promise<any[]> {
return new Promise<any>(async (resolve, reject) => {
try {
resolve(this.db?.collection(collectionName).find(filter));
} catch (err) {
reject(false);
}
}).catch(err => {
return err;
});
}
public aggregate(_collectionName: string, _pipeline: object[]): Promise<any[]> {
throw new Error('Method not implemented.');
}
private connection(DB_CONN_STRING: string, DB_NAME: string): Promise<mongodb.MongoClient> {
return new Promise<mongodb.MongoClient>(async (resolve, reject) => {
try {
if (!this.client) {
const client: mongodb.MongoClient = new mongodb.MongoClient(DB_CONN_STRING);
await client.connect();
this.db = client.db(DB_NAME);
this.client = client;
console.log("[Mongodb] class inited.");
}
resolve(this.client);
} catch (err) {
reject(err);
}
});
}
}
{% endcodeblock %}
JS-SDK引入
emmmmmm内心复杂。
照理来说微信不该对组件编程陌生,这里居然还用半嵌入式页面开发。
既来之,则安之,我把它转为对象引入到项目,这部分有很多大佬都做了,因为没什么技术门槛。