用Python实现一个文档型数据库

849 阅读3分钟
原文链接: mp.weixin.qq.com

介绍

TangoDB是一个轻量级文档型数据库,使用纯Python语言编写。

轻量级:整个项目的源码差不多200行,包括注释和空行。

文档型:不同于关系型数据库,文档型数据库较为灵活,每个文档都有自己的key和value(json格式)。

使用

导入相关的库

from tangodb import TangoDBfrom tangodb.storage import LocalFileStorage, MemoryStorage

获取一个数据库对象和表对象

db = TangoDB(storage=LocalFileStorage, path='/root/db.json')#db = TangoDB(storage=MemoryStorage)table = db.gettable()    #get default table

插入数据(通过表对象)

table.insert({'name':'tom', 'age':25})
table.insert({'name':'joe', 'age':23, 'sex':'male'})
table.insert({'name':'alice', 'age':21, 'sex':'female'})

删除数据

table.remove(cond={'name':'joe'})

更新数据

table.update({'age':26, 'sex':'male'}, cond={'name':'tom'})

查找数据

print table.search(name='alice')

源码结构

TangoDB
    __init__.py
    const.py
    database.py
    storage.py
    storagehub.py
    tool.py

_init_.py:主要定义了一个__all__,把对外可见的接口都放到了__all__里面

const.py:常量都定义在这个文件里

database.py:主体文件,定义及实现了Document、Table和TangoDB类

storage.py:定义了存储引擎,目前已经实现了两种:LocalFileStorage和MemoryStorage,表示数据以何种形式存储

storagehub.py:database和storage的中间层,将数据库和某个表连接起来,起到解耦的作用

框架图

源码分析

我们采用从下到上的顺序来看源码:

storage.py:主要对外提供两个接口:read、write。我们可以抽象出一个类出来,提供这两个方法。抽象类的定义如下:

class storage(object):
    __metaclass__ = ABCMeta    @abstractmethod
    def read(self):
        raise NotImplementError    @abstractmethod
    def write(self, data):
        raise NotImplementError

其他的存储引擎(比如说LocalFileStorage)继承自这个类并且实现read、write接口即可,比如说LocalFileStorage实现write可以这样做,将数据序列化之后存储到本地文件中,而MemoryStorage将数据序列化之后存储到内存中。序列化规定了数据以何种形式存储、传输。序列化的方式有多种,序列化的方式有很多种,比如说json、bson、xml等,我采用的方式是json。

storagehub.py:将存储引擎和数据库中的某个表联系起来,利用storage提供的read、write方法抽象出了更高的方法供table调用,使得table不直接操作storage。因为storagehub是被table调用的,所以它暴露出来的方法应该是对table友好的,TangoDB是文档性数据库,所以storagehub暴露出的方法也是基于文档的操作,如read、write、deleteDocument等,read根据docid返回对应文档的内容,write将一个文档存进table中,deleteDocument从table中删除一个文档。

database.py:数据库的主体部分,定义了三个类:TangoDB、Table和Document,分别对应数据库、表和文档。TangoDB主要提供gettable方法,通过表名获取table对象;Table则实现了增删改查,Document定义了文档结构,是一个dict类型,有一个docid和value。

后记

严格来说,TangoDB并不是真正意义上的数据库,它并不符合ACID的全部原则,ACID即原子性、一致性、隔离性和持久性。TangoDB也不是线程安全的,多个线程同时操作某个表可能会造成表的混乱。后续版本会尽可能的支持这些特性

后续版本在支持这些新特性的同时,也会逐渐完善整个TangoDB框架,如数据的序列化这块完全可以放进一个单独的模块,用户可选择数据的序列化方式,如json、bson等。还会加入锁机制、读缓存等等。

如果可以的话,可以去github点个star。

github地址:

https://github.com/TanLian/300-lines-or-less/tree/master/tangodb