File size: 5,030 Bytes
56e3c4a
 
 
 
 
284e2d2
 
 
56e3c4a
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
3b31e1a
 
 
56e3c4a
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
b4296f5
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
import gradio as gr
import pandas as pd
from io import StringIO
from datetime import datetime
import boto3
import os
ACCESS = os.environ.get("ACCESS_KEY")
SECRET = os.environ.get("SECRET")

def validar(data):
    try:
        buffer = StringIO(data)
        df = pd.read_csv(buffer, sep="\t", na_values=["null", "NULL", "NaN", ""])
        df_limpio = df.dropna(axis=1, how='all')

        if df_limpio.shape[1] < 3:
            return None, "⚠️ Error: Debes tener al menos 3 columnas (Activity Type, Spreadsheet Field y una fecha)."

        col0, col1, col2 = df_limpio.columns[:3]
        if col0.strip() != 'Activity Type':
            return None, "⚠️ Error: La primera columna debe llamarse exactamente 'Activity Type'."
        if col1.strip() != 'Spreadsheet Field':
            return None, "⚠️ Error: La segunda columna debe llamarse exactamente 'Spreadsheet Field'."
        if len(df)!=2:
            return None, "⚠️ Error: Debes tener exactamente 2 filas de 'Spreadsheet Field'."
        df_limpio.fillna(0, inplace=True)
        try:
            # Identificar las columnas que contienen fechas (todas excepto las dos primeras)
            columnas_fecha = df_limpio.columns.difference(['Activity Type', 'Spreadsheet Field'])

            # Aplicar conversión solo en columnas de fechas
            df_limpio[columnas_fecha] = df_limpio[columnas_fecha].applymap(
                lambda x: float(str(x).replace(',', '.')) if isinstance(x, str) and ',' in x else x
            )
            datetime.strptime(col2.strip(), "%d-%b-%y")
        except ValueError:
            return None, "⚠️ Error: La tercera columna debe ser una fecha en formato dd-MMM-yy."

        return df_limpio, "✅ ¡Datos válidos! Ya puedes enviarlos al servidor."

    except Exception as e:
        if str(e) == 'No columns to parse from file':
            e = "⚠️ No se encontraron columnas para analizar. Asegúrate copiar la información correcta."
        return None, f"❌ Error inesperado: {str(e)}"

def enviar_al_servidor(df, EMPRESA, PROYECTO):
    print(EMPRESA, PROYECTO)
    # Inicializar cliente DynamoDB
    dynamodb = boto3.resource('dynamodb', region_name='us-east-1',
                                              aws_access_key_id=ACCESS,
                                              aws_secret_access_key=SECRET)

    # Validar existencia del proyecto
    tabla_proyecto = dynamodb.Table('proyecto')
    respuesta = tabla_proyecto.get_item(Key={'empresa': EMPRESA, 'proyecto': PROYECTO})

    if 'Item' not in respuesta:
        print("❌ El proyecto no existe en la tabla 'proyecto'.")
        return "❌ Error: El proyecto no existe en la tabla 'proyecto'."

    
    FINAL = df.groupby('Activity Type')[df.columns[1:]].agg('sum').reset_index()
    
    
    # Initialize the DynamoDB client
    table_name = "cum_budgeted_labor_units"  # Replace with your actual table name
    table = dynamodb.Table(table_name)

    FINAL = FINAL.map(str)
    FINAL.rename(columns={'Activity Type':'tipo'}, inplace=True)
    for index, row in FINAL.iterrows():
        
        item = row.to_dict()  
        item['id_empresa_proyecto'] = EMPRESA+'_'+PROYECTO
        response = table.put_item(Item=item)  # Insert into DynamoDB
        print(f"Inserted row {index}: {response}")

    print("Datos enviados al servidor:")
    return "✅ Datos enviados al servidor con éxito."

def enviar_al_servidor_botton(df_limpio, EMPRESA, PROYECTO):
    EMPRESA = EMPRESA.strip()
    PROYECTO = PROYECTO.strip()
    if df_limpio is not None:
        return enviar_al_servidor(df_limpio, EMPRESA, PROYECTO)
    return "❌ No hay datos válidos para enviar."

# Usamos gr.Blocks para mayor control
with gr.Blocks() as demo:
    gr.File(value="Layout cum_units.plf", label="📁 Descargar LAYOUT de P6 para extracción de HH", interactive=False)

    textbox_input0 = gr.Textbox(label="Escribe el nombre de la empresa en mayúsculas",
        lines=1,
        placeholder= 'Ejemplo: TECNASIC'
        )

    textbox_input1 = gr.Textbox(label="Escribe el nombre del proyecto como se ve en plataforma",
        lines=1,
        placeholder= 'Ejemplo: OT2936 Lomas Bayas'
        )
    textbox_input2 = gr.Textbox(
        label="Pega aquí tu tabla de remanentes de la Línea Base",
        lines=4,
        placeholder="Activity Type\tSpreadsheet Field\t06-May-24\t13-May-24\t20-May-24\nTask Dependent\tCum Earned Value Labor Units\t\t551\t\t10\t\t700\nTask Dependent\tCum Remaining Labor Units\t\t551\t\t10\t\t700"
    )
    validar_btn = gr.Button("Validar datos")
    df_output = gr.Dataframe(label="Remanentes limpios")
    status_box = gr.Textbox(label="Estado de validación", interactive=False)
    enviar_btn = gr.Button("Enviar datos al servidor")

    validar_btn.click(fn=validar, inputs=textbox_input2, outputs=[df_output, status_box])
    enviar_btn.click(fn=enviar_al_servidor_botton, inputs=[df_output,textbox_input0,textbox_input1], outputs=status_box)

if __name__ == "__main__":
    demo.launch()