Database Django Models/SQLAlchemy太夸张了!有真正的Python DB模型吗?
使事情尽可能简单,但不要简单。 我们能找到修复Python数据库世界的解决方案吗 更新:-如果您知道任何具有多个后端的轻量级高级数据库库,我们可以用syntax sugar蜂蜜包装,请加入强>Database Django Models/SQLAlchemy太夸张了!有真正的Python DB模型吗?,database,nosql,python,Database,Nosql,Python,使事情尽可能简单,但不要简单。 我们能找到修复Python数据库世界的解决方案吗 更新:-如果您知道任何具有多个后端的轻量级高级数据库库,我们可以用syntax sugar蜂蜜包装,请加入 from someAmazingDB import * #we imported a smart model class and db object which talk to database adapter/s class Task (model): title = '' done
from someAmazingDB import *
#we imported a smart model class and db object which talk to database adapter/s
class Task (model):
title = ''
done = False #native types not a custom object we have to think about!
db.taskList = []
#or
db.taskList = expandableTypeCollection(Task) #not sure what this syntax would be
db['taskList'].append(Task(title='Beat old sql interfaces',done=False))
db.taskList.append(Task('Illustrate different syntax modes',True)) # ok maybe we should just use kwargs
#at this point it should be autosaved to a default db option
#by default we should be able to reload the console and access the default db:
>> from someAmazingDB import *
>> print 'Done tasks:'
>> for task in db.taskList:
>> if task.done:
>> print task.title
'Illustrate different syntax modes'
我是Python、webPy和Cherry Py的粉丝,一般来说,KISS
我们正在讨论自动Python到SQL类型转换或NoSQL。
我们不必完全兼容SQL!只是一个可伸缩的子集,或者忽略它
Re:模型更改,当开发人员试图更改模型或有一组合理的默认值时,可以询问开发人员
这里是一个挑战:上述代码应该只需要很少的修改或思考就可以工作。既然我们知道得更多,为什么我们必须容忍妥协
现在是2010年,我们应该能够在睡眠中编写可伸缩的简单数据库。
如果你认为这很重要,请投票 如何使用?忘记ORM!我喜欢香草SQL。用于postgreSQL的python包装器(如
psycopg2
)可以进行自动类型转换,提供了很好的SQL注入保护,而且非常简单
sql = "SELECT * FROM table WHERE id=%s"
data = (5,)
cursor.execute(sql, data)
我想你应该试试。它是为存储python对象而设计的面向对象数据库。它的API与您在问题中提供的示例非常接近,请看一个at教程。您所请求的内容无法在Python2中完成。无论如何,由于一个非常特殊的原因。你想写:
class Task(model):
title = ''
isDone = False
在Python 2.anything中,无论
可能是什么,这都不能让您预测两个字段的任何“顺序”,因为类
语句的语义是:
dict
Task('Illustrate different syntax modes', True)
无法将参数的值与模型的各个字段相关联。(试图通过类型关联进行猜测——希望没有两个字段具有相同的类型——比您所表达的希望使用db.tasklist
和db['tasklist']
而不加区别和互换的愿望更加糟糕)
Python3中的一个向后不兼容的更改是专门为处理这种情况而引入的。在Python3中,自定义元类可以定义一个\uuuuu prepare\uuuuuu
函数,该函数在上述简化列表中的“步骤1”之前运行,这使它可以对类的主体进行更多的控制。具体来说,引用…:
\uuuu prepare\uuuu
返回一个类似字典的对象,该对象用于存储
类主体求值期间的类成员定义。
换句话说,类主体作为功能块进行计算
(就像现在一样),除了局部变量字典
替换为从返回的字典。这
字典对象可以是常规字典或自定义映射
类型
例如,一个元类
使用有关
对成员声明进行排序以创建C结构。元类
将提供一个自定义词典,只需记录
插入顺序
您不希望像本例中那样“创建C结构”,但字段的顺序是至关重要的(以允许使用所需的位置参数),因此自定义元类(通过basemodel
获得)将有一个\u prepare\u
classmethod返回有序字典。这消除了特定的问题,但是,当然,只有当您愿意使用这个“神奇的ORM”将所有代码切换到Python3时。你愿意吗
一旦解决了这个问题,问题是,您希望执行哪些数据库操作,以及如何执行。当然,你的例子根本没有阐明这一点。taskList
属性名称是否特殊,或者分配给db
对象的任何其他属性是否应在使用时“自动保存”(按名称和其他特征)和“自动计量”?是否有方法删除实体、更改实体、定位实体(除了曾经在db
对象的同一属性中列出)?如果DB服务需要身份验证,您的示例代码如何知道要使用哪个DB服务以及如何对其进行身份验证(例如,通过用户ID和密码)
您列出的特定任务并不难实现(例如,在Google App Engine的存储服务之上,它不需要身份验证,也不需要指定“要使用什么DB服务”)model
的元类将内省类的字段并为类生成GAEmodel
,db
对象将使用\uuuuu setattr\uuuu
设置atexit
触发器来存储属性的最终值(当然,作为另一种模型
中的实体),和\uuuu getattr\uuuu
从存储器中获取该属性的信息。当然,如果没有一些额外的数据库功能,这一切都是毫无用处的;-)
编辑:所以我做了一个小原型(Python2.6,基于sqlite)并把它放在上面——它是一个3K的zipfile,包括225行lustdb.py
(太长了,无法在这里发布)和两个小测试文件,大致相当于OP的原始文件:test0.py
是…:
from lustdb import *
class Task(Model):
title = ''
done = False
db.taskList = []
db.taskList.append(Task(title='Beat old sql interfaces', done=False))
db.taskList.append(Task(title='Illustrate different syntax modes', done=True))
from lustdb import *
print 'Done tasks:'
for task in db.taskList:
if task.done:
print task
而且test1.p1
是…:
from lustdb import *
class Task(Model):
title = ''
done = False
db.taskList = []
db.taskList.append(Task(title='Beat old sql interfaces', done=False))
db.taskList.append(Task(title='Illustrate different syntax modes', done=True))
from lustdb import *
print 'Done tasks:'
for task in db.taskList:
if task.done:
print task
运行test0.py
(在具有可写/tmp
目录的计算机上——即任何Unix-y操作系统,或在Windows上,在任何以前运行过mkdir\tmp
的操作系统上-
1. no (expletive delete) redundancy whereby `db.taskList` is a synonym of `db['taskList']`, only the sensible former syntax (attribute-access) is supported
2. no mysterious (and totally crazy) way whereby a `done` attribute magically becomes `isDone` instead midway through the code
3. no mysterious (and utterly batty) way whereby a `print task` arbitrarily (or magically?) picks and prints just one of the attributes of the task
4. no weird gyrations and incantations to allow positional-attributes in lieu of named ones (this one the OP agreed to)
class Book:
def __init__(self, attributes):
self.attributes = attributes
def __getattr__(....): pass
$ python
>>> import book
>>> my_stuff.library = {'garp':
Book({'author': 'John Irving', 'title': 'The World According to Garp',
'isbn': '0-525-23770-4', 'location': 'kitchen table',
'bookmark': 'page 127'}),
...
}
>>> exit
$ python
>>> import my_stuff
>>> print my_stuff.library['garp'].location
'kitchen table'
# or even
>>> for book in my_stuff.library where book.location.contains('kitchen'):
print book.title