Python Data Persistence 简明教程
Data Persistence - ZODB
ZODB ( Zope object Database ) 是一个用于存储 Python 对象的数据库。它是 ACID 兼容的——在 NOSQL 数据库中找不到此特性。ZODB 也是开源的,像许多 NoSQL 数据库一样,横向可伸缩且无模式。然而,它不分布式,也没有提供简单的复制。它为 Python 对象提供了持久性机制。它属于 Zope 应用程序服务器的一部分,但也可以独立使用。
ZODB (Zope object Database) is database for storing Python objects. It is ACID compliant - feature not found in NOSQL databases. The ZODB is also open source, horizontally scalable and schema-free, like many NoSQL databases. However, it is not distributed and does not offer easy replication. It provides persistence mechanism for Python objects. It is a part of Zope Application server, but can also be independently used.
ZODB 由 Zope Corporation 的 Jim Fulton 创建。它最初只是一个简单的持久对象系统。其当前版本是 5.5.0,是用 Python 完全编写的,使用 Python 内置对象持久性(pickle)的扩展版本。
ZODB was created by Jim Fulton of Zope Corporation. It started as simple Persistent Object System. Its current version is 5.5.0 and is written completely in Python. using an extended version of Python’s built-in object persistence (pickle).
ZODB 的一些主要特性包括:
Some of the main features of ZODB are −
-
transactions
-
history/undo
-
transparently pluggable storage
-
built-in caching
-
multiversion concurrency control (MVCC)
-
scalability across a network
ZODB 是一个 hierarchical 数据库。有一个根对象,在创建数据库时初始化。根对象像 Python 字典一样使用,它可以包含其他对象(这些对象本身也可以像字典)。将一个对象存储在数据库中,只需将其分配给容器中一个新的键即可。
The ZODB is a hierarchical database. There is a root object, initialized when a database is created. The root object is used like a Python dictionary and it can contain other objects (which can be dictionary-like themselves). To store an object in the database, it’s enough to assign it to a new key inside its container.
ZODB 对于数据分层并且可能存在比写入更多的读取的应用程序很有用。ZODB 是 pickle 对象的拓展。这就是为什么它只能通过 Python 脚本处理。
ZODB is useful for applications where data is hierarchical and there are likely to be more reads than writes. ZODB is an extension of pickle object. That’s why it can be processed through Python script only.
要安装 ZODB 的最新版本,我们可以使用 pip 实用程序:
To install latest version of ZODB let use pip utility −
pip install zodb
以下依赖项也将被安装:
Following dependencies are also installed −
-
BTrees==4.6.1
-
cffi==1.13.2
-
persistent==4.5.1
-
pycparser==2.19
-
six==1.13.0
-
transaction==2.4.0
ZODB 提供以下存储选项:
ZODB provides following storage options −
FileStorage
这是默认值。所有内容存储在一个大型 Data.fs 文件中,它本质上是一个事务日志。
This is the default. Everything stored in one big Data.fs file, which is essentially a transaction log.
DirectoryStorage
这为每个对象修订版存储一个文件。在这种情况下,它不需要在非正常关闭时重建 Data.fs.index。
This stores one file per object revision. In this case, it does not require the Data.fs.index to be rebuilt on an unclean shutdown.
RelStorage
这将 pickle 存储在关系数据库中。PostgreSQL、MySQL 和 Oracle 均受支持。
This stores pickles in a relational database. PostgreSQL, MySQL and Oracle are supported.
要创建 ZODB 数据库,我们需要一个存储、一个数据库和最终一个连接。
To create ZODB database we need a storage, a database and finally a connection.
第一步是拥有一个存储对象。
First step is to have storage object.
import ZODB, ZODB.FileStorage
storage = ZODB.FileStorage.FileStorage('mydata.fs')
DB 类使用这个存储对象获取数据库对象。
DB class uses this storage object to obtain database object.
db = ZODB.DB(storage)
向 DB 构造函数传递 None 创建一个内存数据库。
Pass None to DB constructor to create in-memory database.
Db=ZODB.DB(None)
最后,我们与数据库建立连接。
Finally, we establish connection with the database.
conn=db.open()
然后,连接对象允许你通过“root()”方法访问数据库的“根”。“根”对象是保存所有持久性对象的字典。
The connection object then gives you access to the ‘root’ of the database with the ‘root()’ method. The ‘root’ object is the dictionary that holds all of your persistent objects.
root = conn.root()
例如,我们这样向根对象添加一个学生列表:
For example, we add a list of students to the root object as follows −
root['students'] = ['Mary', 'Maya', 'Meet']
更改没有持久性储存到数据库中,直至我们提交交易。
This change is not permanently saved in the database till we commit the transaction.
import transaction
transaction.commit()
要储存对象的用户定义类,该类必须继承自持久性父类的 Persistent。
To store object of a user defined class, the class must be inherited from persistent.Persistent parent class.
Advantages of Subclassing
Persistent 类的子类的优点如下:
Subclassing Persistent class has its advantages as follows −
-
The database will automatically track object changes made by setting attributes.
-
Data will be saved in its own database record.
-
You can save data that doesn’t subclass Persistent, but it will be stored in the database record of whatever persistent object references it. Non-persistent objects are owned by their containing persistent object and if multiple persistent objects refer to the same non-persistent subobject, they’ll get their own copies.
这里使用将 Student 类定义为 Persistent 类的子类:
Let use define a student class subclassing Persistent class as under −
import persistent
class student(persistent.Persistent):
def __init__(self, name):
self.name = name
def __repr__(self):
return str(self.name)
要添加此类的对象,让我们首先像上面描述的那样设置连接。
To add object of this class, let us first set up the connection as described above.
import ZODB, ZODB.FileStorage
storage = ZODB.FileStorage.FileStorage('studentdata.fs')
db = ZODB.DB(storage)
conn=db.open()
root = conn.root()
声明对象,然后将其添加到根,再提交交易
Declare object an add to root and then commit the transaction
s1=student("Akash")
root['s1']=s1
import transaction
transaction.commit()
conn.close()
存储在根中的所有对象的列表都可以作为视图对象通过 items() 方法检索,因为根对象类似于内置字典。
List of all objects added to root can be retrieved as a view object with the help of items() method since root object is similar to built in dictionary.
print (root.items())
ItemsView({'s1': Akash})
要从根中获取特定对象属性:
To fetch attribute of specific object from root,
print (root['s1'].name)
Akash
该对象可以很容易地更新。由于 ZODB API 是纯 Python 包,因此不需要使用任何外部 SQL 类型语言。
The object can be easily updated. Since the ZODB API is a pure Python package, it doesn’t require any external SQL type language to be used.
root['s1'].name='Abhishek'
import transaction
transaction.commit()
数据库将立即更新。请注意,事务类还定义了 abort() 函数,该函数类似于 SQL 中的 rollback() 事务控制。
The database will be updated instantly. Note that transaction class also defines abort() function which is similar to rollback() transaction control in SQL.