Экспорт в xlsx с использованием Python и XlsxWriter - PullRequest
0 голосов
/ 30 мая 2018

Я использую XlsxWriter (версия 1.0.2) для создания файла Excel, но при экспорте и открытии файла появляется ошибка: «Мы обнаружили проблему с некоторым содержимым в filename.xlsx.Вы хотите, чтобы мы попытались восстановить столько, сколько мы можем?Если вы доверяете источнику этой книги, нажмите «Да». Когда я нажимаю кнопку «Да» и после: «Закрыть», Excel открывается, и все в порядке, поэтому я не могу понять, почему отображается эта ошибка.Я использую Python 3.6.4, Django 2.0.1, Microsoft Office 2016, Windows 10 и модуль ввода-вывода Python.Я хотел бы знать, как решить эту проблему.

Добавлен код после комментариев:

def testError(request):
    data = [["Goal 1", 0, 0], ["1", "Activity 1", "Alex, Peter"], ["1.1", "Activity 1.1", "Matthew"], ["1.1.1", "Activity 1.1.1", "Jhon"]]
    output = io.BytesIO()
    workbook = xlsxwriter.Workbook(output, {'in_memory': True})
    worksheet = workbook.add_worksheet("Sheet1")
    bold = workbook.add_format({'bold': True})
    title = 'Example'
    merge_format = workbook.add_format({
        'bold': 1,
        'align': 'left',
        'valign': 'vcenter'})
    worksheet.merge_range('A1:C1', title, merge_format)
    a = 'B3:D'
    a += str(len(data)+4)
    worksheet.add_table(a, {'columns': [{'header': 'No'}, {'header': 'ACTIVITY'}, {'header': 'PARTAKERS'}], 'banded_rows': False, 'banded_columns': False, 'autofilter': 0})
    border_format = workbook.add_format({
        'border': 1,
        'align': 'left',
        'font_size': 10
    })
    merge_format = workbook.add_format({
        'bold': 1,
        'border': 1,
        'align': 'left',
        'valign': 'vcenter',
    })
    header_format = workbook.add_format({
        'bold': 1,
        'align': 'center',
        'valign': 'vcenter',
    })
    tab = 'B3:D'
    tab += str(len(data)+3)
    worksheet.autofilter(tab)
    it = 0
    countElem = (len(data))
    max_width_number = 0
    max_width_name = 0
    max_width_partaker = 0
    for ite in range(3, countElem+3):
        cel = 'B'
        cel += str(ite+1)
        if (data[it][0] != 0 and data[it][1] == 0 and data[it][2] == 0):
            worksheet.write_row(cel, data[it])
            iniCel = cel
            finCel = 'D'
            finCel += str(ite+1)
            mergecel = iniCel+':'+finCel
            worksheet.merge_range(mergecel, data[it][0], merge_format)
        else:
            i = 1
            for d in data[it]:
                worksheet.write_rich_string((str('B'+str(ite+1))), str(data[it][0]))
                if len(str(data[it][0])) > max_width_number:
                    max_width_number = len(str(data[it][0]))
                worksheet.write_rich_string((str('C'+str(ite+1))), str(data[it][1]))
                if len(data[it][1]) > max_width_name:
                    max_width_name = len(data[it][1])
                worksheet.write((str('D'+str(ite+1))), data[it][2])
                if len(data[it][2]) > max_width_partaker:
                    max_width_partaker = len(data[it][2])
        it = it+1
    worksheet.conditional_format(a, {'type': 'no_blanks', 'format': border_format})
    worksheet.conditional_format('B3:D3', {'type': 'no_blanks', 'format': header_format})
    worksheet.set_column(1, 1, max(5, max_width_number))
    worksheet.set_column(2, 2, max(20.57, max_width_name))
    worksheet.set_column(3, 3, max(8.29, max_width_partaker))
    workbook.close()
    output.seek(0)
    response = HttpResponse(output.read(), content_type="application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
    response['Content-Disposition'] = str("attachment; filename= workbook_example.xlsx")
    return response

1 Ответ

0 голосов
/ 31 мая 2018

В вашем коде есть две проблемы.

Во-первых, вы не можете объединять ячейки в таблице.Excel не позволяет этого.Поэтому удалите эту строку:

worksheet.merge_range(mergecel, data[it][0], merge_format)

Кроме того, вам не следует добавлять автофильтр в таблицу следующим образом:

worksheet.autofilter(tab)

Вместо этого используйте свойство автофильтра add_table():

worksheet.add_table(a, {..., 'autofilter': True})

После этого рабочая книга откроется без предупреждения и отобразится следующим образом:

enter image description here

Возможно, вам нужно настроить диапазон таблицытакже.Обратите внимание, вам не нужно создавать диапазон для таблицы следующим образом:

tab = 'B3:D'
tab += str(len(data)+3)

Метод add_table() и почти все другие методы в XlsxWriter, возьмите (row, col) нотацию, см.документы .

...