Auf*_*ind 4 python metadata sqlalchemy
我试图了解MySQL关于MetaData对象和engine对象的行为.这个SO-Answer描述MetaData为
表定义的集合
而engine作为
特定数据库的方言和连接详细信息
到现在为止还挺好.但什么时候将这两者分开是有用的?表定义是否未链接到特定数据库?
zzz*_*eek 10
SQLAlchemy 0.1没有"元数据"对象 - Engine直接绑定到每个对象Table.这个想法变得非常快,部分是因为人们想要在连接之前声明他们的Table对象,并且出现了"绑定元数据".然后,发生了长时间的大规模混乱.人们有超级硬的习惯(因为我告诉他们这样做)这样的话:
table.insert().execute()
result = table.select().execute()
Run Code Online (Sandbox Code Playgroud)
即,没有交易,每次都使用新的连接.然后我们会说,"哦,你应该使用交易,你应该更有效率地进行交易",然后我们基本上告诉他们他们必须重写他们的应用程序,而"sqlalchemy有太多方法"模因像气球一样爆炸.
与此同时,Pylons和其他早期的WSGI框架正在努力让多个"应用程序"同时运行 - 在某些情况下,不同的"用户"会在不同的数据库中拥有自己的一组表,这类似的东西.更常见的是水平扩展方法,其中相同的表位于许多数据库中.我这里有一个应用程序,它有一个内置的"复制"系统,其中记录定期从"主"数据库复制到"历史"数据库,并且那里的表元数据也是共享的.
关键在于所有这些用例,用户会来到SQLA,他们对事物的理解始于"绑定元数据".各地的博客和教程都使用它.这些用户中的很大一部分需要突破该系统,并且完全混淆了整个"其他方式"的工作方式.所以很明显,"绑定元数据"系统只是一个默认的过于严格.理想情况下,我希望我从来没有实现它,我自己从不使用它.这就是为什么现在将文档推送到一个部分,只是浏览文档的新用户,他们的性质给邮件列表增加了巨大的支持负担,但是找不到它并且不会混淆.该部分本身有很多子弹,准确地解释了它何时以及为何令人困惑.我假设您已阅读它,请访问http://www.sqlalchemy.org/docs/core/schema.html#binding-metadata-to-an-engine-or-connection.
实际上,表定义未链接到特定数据库.sqlalchemy元数据对象和所有附加对象(表,列,索引等)定义完全抽象的模式,而不引用任何特定的数据库.引擎基本上是三件事:连接信息,方言和连接池.方言是这里的重要部分,它定义了如何连接到特定数据库,但更重要的是关于你的问题,它还定义了如何将sqla的抽象模式对象(metadata等)转换为特定于该数据库的 sql命令和司机.
这种分离有许多不同的用途:
应用程序可以在模块级别定义他们的模式,在导入模块时创建表格和元数据......但是没有定义引擎直到应用程序实际启动并运行(因为知道完整的连接URL和方言通常需要读取配置首先获取文件或获取用户输入).
您可以将多个引擎的情况绑定到同一组元数据,例如webapp,其中每个用户/密码使用它自己的凭据连接到数据库(不是这是有效的,但有时出于安全目的需要).由于元数据是一个全局对象,因此在这种情况下将它绑定到特定引擎是没有意义的.
这种情况很少见,但您也可以使用相反的情况,为单个引擎提供多个元数据实例.当多个子组件共享同一个数据库但使用不同的表名时,可能会发生这种情况.此外,当尝试将应用程序在一个元数据实例中的当前架构与从服务器反射的另一个元数据实例(例如用于架构迁移的目的)进行比较时,可能会发生这种情况.这不会严格阻止您将每个绑定到引擎,但确实有助于演示如何有效地使用多个元数据或引擎实例.
可能还有一些我现在想不到的更多用例,但这应该让你大致了解为什么它们在概念上与彼此分离.