MongoDB入门实践#

简单介绍MongoDB,包括MongoDB的使用场景、和MySQL的对比、安装部署、Java客户端访问及总结

MongoDB?#

我们遵循需求驱动技术的原则,通过一个场景来引入MongoDB,在现行业务需求下考虑下面三个问题:

  • 为什么要使用MongoDB?
  • MongoDB是一个什么样的产品?
  • 它能做什么?

Situation(场景)##

以公司站点报告业务场景(当前其实已换成hdfs):

业务流程###

  • 从Server获取站点日志;
  • 日志分析后入MySQL库(8~9个字段,日期和多个维度字段和多个指标字段),每天数据量大约50w;
  • 依照维度字段、指标字段、日期(一般是每天)聚合查询,查询到的结果集(前1000条)存入Redis供前端展现;
  • 目前每天展示的报告实际是当天凌晨通过离线计算(相对时间较长)得到的结果。

运行状态###

  • 数月时间运行后,MySQL库当中的数据量倍增,整个数据库的查询效率大大下降;
  • Redis的内存占用逐渐上升,并大量占用虚拟内存,导致服务器崩溃。
  • 并且由于Redis本身并不支持类似关系数据库的分页动作,只能存储少量数据作为前端展现,而不能一页一页展示整个结果集查询的结果。

Problem(问题)##

原有的解决方案(MySQL+Redis)

  • MySQL存储的数据量太大导致查询效率太低;
  • 把Redis当作存储使用,导致对虚拟内存占用太高;
  • Redis本身不支持关系型数据库的分页,实际展现数据并不完整。

MongoDB特性

  • 大数据量存储,单实例TB级别
  • 高性能持久化数据:支持内存数据模型(减少IO),支持索引;
  • 高可用性(副本集):自动故障切换(automatic failover),数据备份(data redundancy);
  • 自动扩容:自动分片,副本集保证最终一致性、低延迟高流量。

如此看来,MongoDB太强大了,似乎一种招招要了MySQL命的感觉,不过千万别这么想,毕竟术业有专攻!

那现在就让我们来看看MongoDB的庐山真面目。

先睹为快#

插播一段广告,这里引用官方网站上MongoDB的查询示例比较下MySQL和MongoDB。

MongoDB & MySQL查询比较

  • MySQL查询(SELECT _id,name,address FROM users WHERE age>18 LIMIT 5)

  • MongoDB查询(db.users.find( { age: { $gt: 18 } }, { name: 1, address: 1 } ).limit(5))

有没有一种他们俩长的真像的感觉,没错你答对了,MongoDB被称作是最像关系型数据库的NOSQL数据库。

How To Use#

温馨提示

  • MongoDB存在企业版和社区版,企业版是收费版本(咱是穷人,自然不用收费版了)
  • 推荐安装64位
  • 推荐Linux下安装
  • Windows版本可用于调试

官方网站##

官网

官网ORG

下载##

  • 选择Current,Previous,Development
  • 选择Windows,Linux,Max OS X,Solaris
  • 选择下载格式

文档##

  • 选择下载在线
  • 选择文档版本(2.6)
  • 选择文档格式

安装&启动&关闭##

Linux

以Linux ReadHat为例

安装

  • 创建文件mongdb.repo,路径:/etc/yum.repos.d/mongodb.repo
  • 配置mongdb.repo:

    64位:
[mongodb]
name=MongoDB Repository
baseurl=http://downloads-distro.mongodb.org/repo/redhat/os/x86_64/
gpgcheck=0
enabled=1

32位:

name=MongoDB Repository
baseurl=http://downloads-distro.mongodb.org/repo/redhat/os/i686/
gpgcheck=0
enabled=1
  • yum安装完整版: sudo yum install -y mongodb-org

启动

  • selinux开启MongoDB tcp端口: semanage port -a -t mongod_port_t -p tcp 27017
  • 关闭SELINUX: SELINUX=disabled
  • 启动:sudo service mongod start
  • client: 执行mongo命令即可

关闭

  • sudo service mongod stop
  • 进入mongo的窗口:use admin; db.shutdownServer()

Windows 64位

安装

  • 查看windows版本:wmic os get osarchitecture**
  • windows msi或zip(解压即可,比如目录:D:\Program Files\mongodb)
  • 将bin目录加入到classpath

启动

  • 解压目录下创建两级目录:data\db,data\log
  • 启动server(mongod,mongos(分片集群客户端))

    mongod.exe --dbpath "D:\Program Files\mongodb\data"(如果路径中存在空格,请使用""引用路径)
  • client(* driver,mongo)

    mongo

关闭

  • Ctrl+C
  • 进入mongo的窗口:use admin; db.shutdownServer()

一般情况下,对于开发人员,我们更加关心MongoDB的Driver,和Mysql一样,它自然是多语言版的,作为Java开发人员,我们介绍MongoDB Java Driver。

MongoDB Java Driver#

获取Driver(pom)##

        <dependency>
<groupId>org.mongodb</groupId>
<artifactId>mongo-java-driver</artifactId>
<version>2.13.0</version>
</dependency>

CRUD##

我们以java代码方式操作MongoDB,然后用图形化的工具查看结果.

insert###

  • 插入文档记录:{"name" : "someone" , "age" : 18 , "gender" : 1 , "address" : { "country" : "china" , "city" : "shanghai"}}
    @Test
public void insert() throws Exception {
// 新建客户端.
MongoClient client = new MongoClient("127.0.0.1", 27017);
// 获取DB.
DB db = client.getDB("testDB");
// 获取文档集.
DBCollection collection = db.getCollection("demo");
// 一行记录.
// json: {"name" : "someone" , "age" : 18 , "gender" : 1 , "address" : { "country" : "china" , "city" : "shanghai"}}
BasicDBObject user = new BasicDBObject("name", "someone")
.append("age", 18)
.append("gender", 1)
.append("address", new BasicDBObject("country", "china").append("city", "shanghai")); System.out.println(collection.insert(user));
// 关闭客户端
client.close();
}

query###

  • 查询 条件:{ "name" : "someone"}的结果集
    @Test
public void query() throws Exception {
// 新建客户端.
MongoClient client = new MongoClient("127.0.0.1", 27017);
// 获取DB.
DB db = client.getDB("testDB");
// 获取文档集.
DBCollection collection = db.getCollection("demo");
// 条件: { "name" : "someone"}
BasicDBObject match = new BasicDBObject("name", "someone");
// 执行查询并打印结果集列表.
System.out.println(collection.find(match).toArray());
// 关闭客户端
client.close();
}

update###

  • 更新 条件: {"name" : "someone"} set: {"age": 28}
    @Test
public void update() throws Exception {
// 新建客户端.
MongoClient client = new MongoClient("127.0.0.1", 27017);
// 获取DB.
DB db = client.getDB("testDB");
// 获取文档集.
DBCollection collection = db.getCollection("demo");
// 条件.
// json: {"name" : "someone"}
BasicDBObject match = new BasicDBObject("name", "someone"); // set:{"age": 28}
BasicDBObject updatedValue = new BasicDBObject();
updatedValue.put("age", 28);
DBObject updateSetValue = new BasicDBObject("$set", updatedValue); // 执行更新并打印.
//update api: DBObject q, DBObject o, boolean upsert, boolean multi.
//upsert:若为true,没有找到匹配的记录时会执行新增一条记录,false则不做任何处理.
//multi:若为false,表示只更新查询到的一条记录,true则表示更新所有匹配记录.
System.out.println(collection.update(match, updateSetValue, false, true));
// 关闭客户端
client.close();
}

delete###

  • 删除 条件:{"name" : "someone"}
    @Test
public void delete() throws Exception {
// 新建客户端.
MongoClient client = new MongoClient("127.0.0.1", 27017);
// 获取DB.
DB db = client.getDB("testDB");
// 获取文档集.
DBCollection collection = db.getCollection("demo");
// 条件.
// json: {"name" : "someone"}
BasicDBObject match = new BasicDBObject("name", "someone");
// 删除匹配记录.
System.out.println(collection.remove(match));
// 关闭客户端
client.close();
}

常用Api##

常用类###

  • MongoClient 客户端连接抽象
  • DB 文档库
  • DBCollection 文档集
  • DBObject 文档对象基类
  • BasicDBObject 基础文档对象
  • BasicDBList 基础文档列表对象

常用方法###

  • DBCollection: find(),update(),insert(),remove(), MongoDB大部分操作数据有关的Api都是基于此类.
  • MongoClient: getDB(), close()
  • DB: getCollection()
  • DBObject: put()
  • BasicDBObject: append()
  • BasicDBList: add()

第三方封装(Third Party Frameworks and Libraries)##

基于MongoDB的driver,有很多第三方封装的包,比如:

  • Spring MongoDB

  • Jongo

大多数框架都支持以POJO的方式开发基于MongoDB的应用!

MongoDB & MySQL#

Indicator MongoDB MySQL
大数据支持 较强 一般
ACID 部分支持 全部
SQL特性 非结构化,支持部分SQL语言特性 完全支持SQL语言规范,标准化,交互性强
扩展 自动扩展 有一定的硬件成本,需要第三方程序
应用灵活性 一般

MongoDB与MySQL是互补的关系

MongoDB没有全面的ACID支持,因此不能将有事务场景的业务底层存储从MySQL改为NOSQL

MongoDB最佳实践(不全)#

  • 版本更新
  • 采用Replicaton Sets(副本集)部署
  • 采用64位系统部署
  • 默认开启journaling日志
  • 谨慎分片sharding
  • 不要当做Sql数据库使用
  • 明确数据需要的一致性和可靠性
  • 按照真实业务场景全面测试
  • 采用固定的Schema设计(某个DBCollection下的文档结构一致)
  • 采用索引(和其它关系型数据使用索引的意义是一致的)

QA#

MongoDB入门实践的更多相关文章

  1. Spring Boot WebFlux 快速入门实践

    02:WebFlux 快速入门实践 Spring Boot 2.0 spring.io 官网有句醒目的话是: BUILD ANYTHING WITH SPRING BOOT Spring Boot ( ...

  2. Spring Boot WebFlux-01——WebFlux 快速入门实践

    第01课:WebFlux 快速入门实践 Spring Boot 2.0 spring.io 官网有句醒目的话是: BUILD ANYTHING WITH SPRING BOOT Spring Boot ...

  3. 分布式学习系列【dubbo入门实践】

    分布式学习系列[dubbo入门实践] dubbo架构 组成部分:provider,consumer,registry,monitor: provider,consumer注册,订阅类似于消息队列的注册 ...

  4. sass、less和stylus的安装使用和入门实践

    刚 开始的时候,说实话,我很反感使用css预处理器这种新玩意的,因为其中涉及到了编程的东西,私以为很复杂,而且考虑到项目不是一天能够完成的,也很少是 一个人完成的,对于这种团队的项目开发,前端实践用c ...

  5. MongoDB 入门之基础 DCL

    此文章主要记录部分主要的 MongoDB 的 DCL 操作. MongoDB 默认不需要用户名和密码就可以用 mongodb.exe 登录 一.开启 MonogoDB 的权限模式 修改 MongoDB ...

  6. MongoDB入门三:MongoDB shell

    MongoDB shell MongDB shell是一个功能完备的Javascript解释器,可以运行Javascript程序.也可以用于连接MongoDB服务器,执行脚本,对数据库进行操作.类似于 ...

  7. mongodb 最佳实践

    MongoDB功能预览:http://pan.baidu.com/s/1k2UfW MongoDB在赶集网的应用:http://pan.baidu.com/s/1bngxgLp MongoDB在京东的 ...

  8. MongoDB 入门之查询(find)

    MongoDB 入门之查询(find) 1. find 简介 (1)find的第一个参数决定了要返回哪些文档. 空的查询文档会匹配集合的全部内容.默认就是{}.结果将批量返回集合c中的所有文档. db ...

  9. MongoDB入门简介

    MongoDB入门简介 http://blog.csdn.net/lolinzhang/article/details/4353699 有关于MongoDB的资料现在较少,且大多为英文网站,以上内容大 ...

随机推荐

  1. New Concept English three(21)

    27W 59 Boxing matches were very popular in England two hundred years ago. In those days, boxers foug ...

  2. jQuery 滑动选项卡jQuery tabulous.js

    A jQuery tabs module for todays web! 实例DEMO 运行一下 Documentation Tabulous.js can be used with any cont ...

  3. (二) ffmpeg filter学习--混音实现

    Audio 混音实现 从FFMPEG原生代码doc/examples/filtering_audio.c修改而来. ffmpeg版本信息 ffmpeg version N-82997-g557c0df ...

  4. echarts-detail---饼图

    echarts-饼图 1.饼图上面显示纵坐标的百分比数值 series: [ { name: arr[i].name, type: 'pie', radius: ['30%', '50%'], avo ...

  5. 在ROS Kinetic中使用Gazebo 8进行机器人仿真

    在ROS Kinetic中使用Gazebo 8比在ROS Indigo中使用Gazebo 3-8要容易一些. 目前最新稳定版本的Gazebo8为8.1.1. 安装流程如下: $  sudo apt-g ...

  6. 通过摄像机视频设备或者流媒体服务器SDK获取到数据转换成RTMP流实现网页/手机微信播放

    写这篇博客主要是为了给新入门的流媒体开发者解惑,现在看到各种开发者的需求:网页播放RTSP摄像机.微信播放RTSP摄像机.网页播放摄像机SDK输出的视频流.网页播放第三方流媒体平台输出的视频流.包括G ...

  7. 【Java实战】源码解析为什么覆盖equals方法时总要覆盖hashCode方法

    1.背景知识 本文代码基于jdk1.8分析,<Java编程思想>中有如下描述: 另外再看下Object.java对hashCode()方法的说明: /** * Returns a hash ...

  8. Mac怎么快速创建便签和发送附件的邮件

    1.如何快速创建便签        在Mac的任意界面选中文字:shift+command+y 就能创建便签2.如何快速发送附件的邮件(网页界面)        在Safari网页界面 command ...

  9. appium-java,连接真机启动微信

    1.启动appium 2.设置信息 3.设置IP和端口 4.appium连接手机,微信中打开debugx5.qq.com,信息->TBS settings->是否打开TBS内核Insper ...

  10. hihoCoder1599 bfs

    特殊的剪枝,整体上和辗转相除法有点像 #1599 : 逃离迷宫4 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 小Hi被坏女巫抓进一座由无限多个格子组成的矩阵迷宫. 小 ...