theorchard / openpyxl

Other
54 stars 21 forks source link

Error on Styles #18

Open waseidel opened 1 year ago

waseidel commented 1 year ago

I have a function to save a dataframe to an excel file, but if the file exists it deletes all the formats/styles in all the sheets of the excel file, and if it doesn't just don't create the new formats/styles, I have searched and readed lot of stackoverflow but there is not answer to this issue

pip freeze
absl-py==1.3.0
et-xmlfile==1.1.0
greenlet==2.0.1
msgpack==1.0.4
numpy==1.23.5
openpyxl==3.0.10
ortools==9.5.2237
pandas==1.5.2
protobuf==4.21.11
PuLP==2.7.0
pynvim==0.4.3
python-dateutil==2.8.2
pytz==2022.6
scipy==1.9.3
six==1.16.0

python --version
Python 3.10.8

This is the code to save and format the excel file

import os

from openpyxl import Workbook, load_workbook
from openpyxl.styles import Alignment, Font
from openpyxl.styles.borders import Border, Side, BORDER_THIN
from openpyxl.styles.numbers import FORMAT_DATE_TIMEDELTA, FORMAT_GENERAL
from openpyxl.utils.dataframe import dataframe_to_rows

THIN = Side(border_style=BORDER_THIN, color="303030")
BLACK_BORDER = Border(top=THIN, left=THIN, right=THIN, bottom=THIN)
FONT = Font(name="Calibri", size=11)
CENTER_ALIGN = Alignment(horizontal="center", wrap_text=False, vertical="center")
LEFT_ALIGN = Alignment(horizontal="left", wrap_text=False, vertical="center")
RIGHT_ALIGN = Alignment(horizontal="right", wrap_text=False, vertical="center")

# Diferent Formats
HOUR_FORMAT = FORMAT_DATE_TIMEDELTA
NUMBER_FORMAT = FORMAT_GENERAL
KILOMETER_FORMAT = r'_-* #,##0_-;-* #,##0_-;_-* "-"??_-;_-@_-'

COLS = [
    "Designación de tarea vehículo",
    "Subcontratista",
    "Línea",
    "Tipo de vehículo del viaje",
    "desde",
    "hasta",
    "duración",
    "Salida",
    "Punto de inicio",
    "Punto de término",
    "Entrada",
    "Largo vacio",
    "Largo",
    "Jornada",
]

def save_file(df, hoja, ruta):
    if os.path.exists(ruta):
        workbook = load_workbook(filename=ruta, read_only=False)
        if hoja in workbook.sheetnames:
            std = workbook.get_sheet_by_name(hoja)
            workbook.remove_sheet(std)
        workbook.create_sheet(hoja)
        sheet = workbook[hoja]
    else:
        workbook = Workbook()
        sheet = workbook.active
    sheet.title = hoja

    for row in dataframe_to_rows(
        df[COLS].sort_values(by="Designación de tarea vehículo"), index=False
    ):
        sheet.append(row)

    for row in sheet.iter_rows():
        for _, cell in enumerate(row):
            cell.alignment = LEFT_ALIGN
            cell.font = FONT
            cell.border = BLACK_BORDER
            cell.number_format = NUMBER_FORMAT

    for row in sheet.iter_rows(min_row=2, min_col=6, max_col=7):
        for _, cell in enumerate(row):
            cell.alignment = RIGHT_ALIGN
            cell.number_format = HOUR_FORMAT

    for row in sheet.iter_rows(min_row=2, min_col=12, max_col=13):
        for _, cell in enumerate(row):
            cell.alignment = RIGHT_ALIGN
            cell.number_format = KILOMETER_FORMAT

    workbook.save(ruta)