Firebird проверяет типы в столбцах - PullRequest
0 голосов
/ 11 февраля 2020

Я хотел бы выполнить что-то по строчкам псевдокода в строке cur.execute ('stuff'):

import fdb

tableName = "MostCertainlyNotHelloWorldTable"

con = fdb.connect(dsn="dsnString",user="MostCertainlyNotSYSDBA",password="MostCertainlyNotMasterkey")
cur = con.cursor()

# this is my pseudo-code
cur.execute("SELECT * FROM tableName WHERE Type(column) IS NOT BLOB") 
# The idea is to remove all BLOB type columns within a given table from the SELECT command's output for that table

for row in cur.fetchall():
    for col in row:
        print(col, end = ',')
    print()

Мне нужно напечатать все столбцы внутри данной таблицы из База данных Firebird, за исключением (как упомянуто в комментарии к коду) тех, которые имеют «BLOB» в качестве типа ввода. Честно говоря, я не собираюсь печатать вещи, я собираюсь добавить их в текстовый файл, но я предполагаю, что печать дает тот же результат (я думаю?) Без затопления папок проекта.

I мне бы хотелось что-то, что позволило бы мне фильтровать данные по типу, а именно, исключая BLOB-объекты, но все же позволяло мне получить csv-подобный формат (столбцы внутри строки, разделенные запятыми, строки, разделенные '\ n').

Если отфильтровать BLOB-объекты НЕВОЗМОЖНО, мне нужен способ работы со столбцами BLOB, у которых запятые находятся в своих значениях, поскольку они эффективно нарушают структуру моих таблиц.

Поэтому мне нужно либо:

  • Способ полного пропуска столбцов BLOB.

или

  • Способ обработки запятых внутри них.

1 Ответ

1 голос
/ 12 февраля 2020

Как я уже говорил ранее, вы не можете сделать это в самом запросе. Либо вы должны проверить таблицы метаданных и создать соответствующий запрос, включающий только соответствующие столбцы, либо вам необходимо выполнить самоанализ типа для курсора и пропустить столбцы с помощью большого двоичного объекта.

Например, чтобы пропустить столбцы большого двоичного объекта в FDB, вы можете сделать что-то вроде:

import fdb
import csv

def is_blob(descriptor):
    return (descriptor[fdb.DESCRIPTION_DISPLAY_SIZE] == 0 
        and descriptor[fdb.DESCRIPTION_INTERNAL_SIZE] == 8)

with fdb.connect(dsn="localhost:exampledb", user="sysdba", password="masterkey") as con:
    cur = con.cursor()
    cur.execute("SELECT * FROM DATAEXAMPLE") 

    with open('output.csv', 'w', newline='') as csvfile:
        writer = csv.writer(csvfile)
        for row in cur.fetchall():
            values = [column for index, column in enumerate(row) 
                        if not is_blob(cur.description[index])]
            writer.writerow(values)

Проверка для размера дисплея 0 и внутреннего размера 8 будет определять капли. Это немного клочок, но код type_code (fdb.DESCRIPTION_TYPE_CODE) в Cursor.description не предоставляет достаточной информации, чтобы отличить капли от неблобов.

Я также использую csv модуль для создания в файл CSV. Это устранит проблемы, например, с колонками varchar, содержащими запятые в своих значениях, путем кавычек. Проверьте документацию csv, если вам нужно точно настроить сгенерированный файл CSV. По умолчанию генерируется CSV, который совместим с тем, как Microsoft Excel читает и записывает CSV.

Использование модуля CSV может также позволить вам включать столбцы BLOB-объектов (при условии, что они blob sub_type text). Это может зависеть от того, может ли потребитель жить с символами новой строки внутри значения или нет. Если у вас также есть столбцы blob sub_type binary, вам может потребоваться сделать что-то для них дополнительное, например, base64-кодирование значения перед включением его в CSV.

...