python - 将字符串分配给字段对象

时间:2017-06-13 12:35:38

标签: python google-bigquery

我正在使用Google BigQuery的python客户端。 我正在编写一个程序来自动创建/导出表格。

一切正常,但有一个小问题 - 我想把表的架构作为用户的输入。

以下是目前如何分配表架构的方法:

 table.schema = (
    bigquery.SchemaField('Name', 'STRING'),
    bigquery.SchemaField('Gender', 'STRING'),
    bigquery.SchemaField('Frequency', 'INTEGER')
)

它在代码中是硬编码的。

我编写了代码来处理用户输入并将其转换为上述格式。

我的代码返回的是一个字符串 - bq_schema - 看起来像:

bigquery.SchemaField(Name, STRING),bigquery.SchemaField(Gender, STRING),bigquery.SchemaField(Frequency, INTEGER)

现在,当我尝试将此字符串分配给表模式时,

table.schema = (bq_schema)

我收到一条错误,指出Schema items must be fields

那么如何根据用户输入使表模式动态化呢?

编辑:根据要求,这里是将用户输入转换为字符串的代码:

s_raw = raw_input('\n\nEnter the schema for the table in the following format- fieldName:TYPE, anotherField:TYPE\n')
s = s_raw.split(',')
schema = []

for obj in s:
    temp = obj.split(':')
    schema.append(temp[0])
    schema.append(temp[1])

bq_schema = ''

for i in range(0, len(schema), 2):
    bq_schema+=('bigquery.SchemaField(\'{}\', \'{}\'),'.format(schema[i], schema[i+1])) 

2 个答案:

答案 0 :(得分:1)

要定义字段在BigQuery中的行为方式,您基本上需要3 inputsnametypemode

处理输入模式时可能会遇到的一个问题是管理RECORD类型的字段,因为每个字段都在其中定义了其他字段。

在这种情况下,用户在字符串中为您提供他正在使用的架构设置会有些困难。

我建议你做的是接收一个类似JSON的输入数据和相应的模式。例如,您可以将此作为输入:

[{"name": "sku", "type": "INT64", "mode": "NULLABLE"},
   {"name": "name", "type": "STRING", "mode": "NULLABLE"},
   {"name": "type", "type": "STRING", "mode": "NULLABLE"},
   {"fields":
     [{"name": "id", "type": "STRING", "mode": "NULLABLE"}, {"name": "name", "type": "STRING", "mode": "NULLABLE"}],
    "name": "category", "type": "RECORD", "mode": "REPEATED"},
   {"name": "description", "type": "STRING", "mode": "NULLABLE"},
   {"name": "manufacturer", "type": "STRING", "mode": "NULLABLE"}]

请注意,此JSON以直接的方式完全定义了架构。字段“category”的类型为“RECORD”,它包含每个子字段的模式定义,即“name”和“id”。

在Python中,你所要做的就是处理这个JSON输入。这个功能可以解决这个问题:

from google.cloud.bigquery import SchemaField
def get_schema_from_json(input_json, res=[]):
     if not input_json:
         return res
     cur = input_json.pop()
     res.append(SchemaField(name=cur['name'], field_type=cur['type'], mode=cur['mode'], fields = None if 'fields' not in cur else get_schema_from_json(cur['fields'], [])))
     return get_schema_from_json(input_json, res)

然后你就可以像这样提取架构:

table.schema = get_schema_from_json(user_json_input_data)

答案 1 :(得分:0)

  

问题:我的代码返回的是字符串--bq_schema

您所面对的是__str__ bigquery对象的bq_schema = [] for i in range(0, len(schema), 2): bq_schema.append(SchemaField(schema[i], schema[i+1])) 重新定位。

更改以下内容:

{{1}}