我试图从数据库(Python,Postgres)中获取结果集中字段的表名。PHP中有一个函数用于获取字段的表名,我使用了它,它可以工作,所以我知道它可以完成(在PHP中)。我在Python中寻找类似的函数。
PHP中的pg_field_table()函数获取结果和字段号,并“返回该字段所属的表的名称”。这正是我需要的,但在Python中。
简单示例-创建表、插入行、选择数据:
CREATE TABLE table_a (
id INT,
name VARCHAR(10)
);
CREATE TABLE table_b (
id INT,
name VARCHAR(10)
);
INSERT INTO table_a (id, name) VALUES (1, 'hello');
INSERT INTO table_b (id, name) VALUES (1, 'world');
当使用
psycopg2
或sqlalchemy
时,我得到了正确的数据和字段名,但没有表名的信息。import psycopg2
query = '''
SELECT *
FROM table_a A
LEFT JOIN table_b B
ON A.id = B.id
'''
con = psycopg2.connect('dbname=testdb user=postgres password=postgres')
cur = con.cursor()
cur.execute(query)
data = cur.fetchall()
print('fields', [desc[0] for desc in cur.description])
print('data', data)
上面的示例打印字段名。输出为:
fields ['id', 'name', 'id', 'name']
data [(1, 'hello', 1, 'world')]
我知道有
cursor.description
,但它不包含表名,只包含字段名。我需要的是-当使用原始SQL查询数据时,用某种方法检索结果集中字段的表名。
编辑1:我需要知道“hello”是来自“table_a”还是“table_ab”,这两个字段的名称都是相同的(“name”)。如果没有表名的信息,就无法判断值在哪个表中。
编辑2:我知道有一些解决方法,比如SQL别名:
SELECT table_a.name AS name1, table_b.name AS name2
,但我确实在问如何从结果集中检索表名。编辑3:我正在寻找一种解决方案,它允许我编写任何原始的SQL查询,有时
SELECT *
,有时SELECT A.id, B.id ...
,执行该查询后,我将获得结果集中字段的字段名和表名。 最佳答案
有必要查询pg_attribute
catalog中的表限定列名:
query = '''
select
string_agg(format(
'%%1$s.%%2$s as "%%1$s.%%2$s"',
attrelid::regclass, attname
) , ', ')
from pg_attribute
where attrelid = any (%s::regclass[]) and attnum > 0 and not attisdropped
'''
cursor.execute(query, ([t for t in ('a','b')],))
select_list = cursor.fetchone()[0]
query = '''
select {}
from a left join b on a.id = b.id
'''.format(select_list)
print cursor.mogrify(query)
cursor.execute(query)
print [desc[0] for desc in cursor.description]
输出:
select a.id as "a.id", a.name as "a.name", b.id as "b.id", b.name as "b.name"
from a left join b on a.id = b.id
['a.id', 'a.name', 'b.id', 'b.name']