Skip to content

NoSQL

NoSQL(Not Only SQL,非关系型数据库)的主要特点包括非关系型的、分布式的、开源的、水平可扩展的。

NoSQL 的原始目的是为了大规模 Web 应用,这场全新的数据库革命运动很早就有人提出,发展至 2009 年趋势越发高涨。
NoSQL 的拥护者们提倡运用非关系型的数据存储,通常的应用如模式自由、支持简易复制、简单的 API、最终一致性(非 ACID)、大容量数据等。
NoSQL 用得最多的是 Key-Value(键值对)存储,当然还有文档型、列存储、图型数据库、XML 数据库等。
相对于目前铺天盖地的关系型数据库运用,这一概念无疑是一种全新的思维

产生背景

随着互联网 Web 2.0 网站的兴起,非关系型数据库已经成为一个及其热门的新领域,非关系型数据库产品的发展迅速,而传统的关系型数据库在应付 Web 2.0 网站,特别时超大规模的高并发的 SNS(Social Network Service, 社交网络服务) 类型的 Web 2.0 纯动态网站时已经显得力不从心,暴露了很多难以克服的问题,例如:

  1. 对数据库高并发读写的需求
    Web 2.0 网站要根据用户个性化信息实时生成动态页面和提供动态信息,所以基本上无法使用动态页面静态化技术,因为数据库并发负载非常高,往往要达到每秒上万次读写请求。关系型数据库应付上万次 SQL 查询还勉强可以,但是应付上万次 SQL 写数据请求,硬盘 I/O 就无法承受了。对于普通的 BBS 网站,往往也存在对高并发写请求的需求。

  2. 对海量数据的高效率存储和访问的需求
    对于大型 SNS 网站,每天用户产生海量的用户动态信息,甚至一个月就能达到 2.5 亿条用户动态,对于关系型数据库来说,在一张存储 2.5 亿条记录的表里进行 SQL 查询,效率是极其低下甚至是不可忍受的。此外,大型 Web 网站的用户登陆系统,例如腾讯、盛大、动辄数以亿计的账号,关系数据库也很难应付。

  3. 对数据库的高可扩展性和高可用性的需求
    在基于 Web 的架构当中,数据库是最难进行横向扩展的,当一个应用系统的用户量和访问量与日俱增的时候,你的数据库却没有办法像 Web Server 和 APP Server 那样简单地通过添加更多的硬件和服务节点来扩展性能和负载能力。
    对于很多需要提供 24 小时不间断服务的网站来说,对数据库系统进行升级和扩展是非常痛苦的事情,往往需要停机维护和数据迁移,可以停机维护随之带来的就是公司收入的减少。

在上面提到的“三高”需求面前,关系数据库遇到了难以克服的障碍,而对于 Web 2.0 网站来说,关系数据库的很多主要特性却无用武之地,例如:

数据库事物一致性需求。很多 Web 实时系统并不要求严格的数据库事务,对读一致性的要求很低,有些场合对写一致性要求也不高。
因此数据库事务管理成了数据库高负载下一个沉重的负担。

数据库的写实时性和读实时性需求。对关系数据库来说,插入一条数据之后立刻查询,是肯定可以读出这条数据的,但是对于很多 Web 应用来说,并不要求这么高的实时性

对复杂的 SQL 查询,特别是多表关联查询的需求。任何大数据量的 Web 系统都非常忌讳多个大表的关联查询,以及复杂的数据分析类型的复杂 SQL 报表查询,特别是 SNS 类型的网站,从需求以及产品设计角度,就需要避免产生这种情况。往往更多的只是单表的主键查询,以及单表的简单条件分页查询,SQL 的功能被极大地弱化了

因此,关系数据在这些越来越多的应用场景下显得不那么合适了,为了解决这类问题的 NoSQL 数据库应运而生。

NoSQL 的种类及其特性

NoSQL 是非关系型数据存储的广义定义。它打破了长久以来关系型数据库与 ACID 理论长期垄断数据库市场的局面。
NoSQL 数据存储不需要固定的表结构,通常也不存在连接操作。在大量数据存取上具备关系型数据库无法比拟的性能优势,该概念在 2009 年年初得到了广泛认同

1.满足海量存储需求和访问的面向文档的数据库

MongoDB

MongoDB 是用 C++ 开发的,主要解决的是海量数据的访问效率问题。根据官方文档记载,当数据量达到 50GB 以上的时候,MongoDB 的数据库访问速度是 MySQL 的 10 倍以上。MongoDB 的并发读写效率不是特别出色,根据官方提供的性能测试表明,大约每秒可以处理 0.5 万~1.5万次读写请求

MongodB 还自带了一个出色的分布式文件系统 GridFS,可以支持海量的数据存储。

MongoDB 也有一个 Ruby 的项目 MongoMapper,是模仿 Merb 的 DataMapper 编写的 MongoDB 接口,使用起来非常简单,几乎和 DataMapper 一模一样,功能非常强大。

2.满足极高读写性能需求的 Key-Value 数据库

Redis

Redis 本质上是一个 Key-Value 类型的内存数据库,类似 Memcached,整个数据库加载在内存当中进行操作,定期通过异步操作吧数据库数据 flush 到硬盘上进行保存。因为是纯内存操作,Redis 的性能非常出色,每秒可以处理超过 10 万次读写操作。

Redis 的出色之处不仅仅 是性能,Redis 最大的魅力是支持保存 List 列表和 Set 集合的数据结构,而且还支持对 List 进行各种操作。例如,从 List 两端 push 和 pop 数据、取 List 区间、排序,以及对 Set 支持各种集合的并集交集操作。此外,单个 Value 的最大限制是 1GC,因此 Redis 可以用来实现很多有用的功能。例如,用它的 List 来做 FIFO 双向链表,实现一个轻量级的高性能消息队列服务,用它的 Set 可以做高性能的 tag 系统等。由于 Redis 也可以对存入的 Key-Value 设置 expire 时间,因此也可以当作一个功能加强版的 Memcached。

Redis 的主要缺点是数据库容量受到物理内存的限制,不能用作海量数据的高性能读写,并且它没有原生的可扩展机制,不具有可扩展能力,要依赖客户端来实现分布式读写