Beispiel #1
0
def initialize():
    """
	Inizializzazione delle variabili globali

	:return None
	"""
    global aqua_data, fpro, tipo_lettura, fprol, fproc, fprot, fpros, logger

    try:
        # Controllo presenza dei dati dell'azienda
        if 'Fatpro' not in aqua_data:
            raise DataMissingError('', "Mancano i dati dell'azienda.")

        fpro = aqua_data['Fatpro'][0]
        tipo_lettura = fpro.fp_tipo_let

        logger.prefix_info("Utente:\t[%d/%s]", fpro.fp_aconto, fpro.fp_azienda)
        logger.prefix_info("Lettura:\t[%s/%d/%d %s]", tipo_lettura,
                           fpro.fp_numlet_pr, fpro.fp_numlet_aa,
                           fpro.fp_data_let)

        if fpro.fp_periodo <= 0:
            raise InvalidDataError('',
                                   'Il periodo non può essere di 0 giorni.')

        # Controllo della presenza delle letture
        if 'Fatprol' not in aqua_data:
            raise DataMissingError('', "Mancano le letture.")

        fprol = aqua_data['Fatprol'] if 'Fatprol' in aqua_data else None

        # Controllo della presenza delle tariffe
        if 'Fatprot' not in aqua_data:
            raise DataMissingError('', "Mancano le tariffe.")

        fprot = sorted(aqua_data['Fatprot'],
                       key=lambda t:
                       (t.fpt_vigore, t.fpt_codtar, t.fpt_colonna))

        # Controllo della presenza dei costi
        if 'Fatproc' not in aqua_data:
            raise DataMissingError("", "Mancano i costi.")

        # Filtro le righe con quantità 0
        fproc = [c for c in aqua_data['Fatproc'] if c.fpc_qta != 0]
        # Il codice 'CS' deve essere presente
        if len([c for c in fproc if c.fpc_bcodart == 'CS']) == 0:
            raise CostCodeMissingError(
                "", "Mancano le Competenze di Servizio (cod. CS).")

        # Controllo della presenza degli storni e filtro le righe con quantità 0
        if 'Fatpros' not in aqua_data:
            logger.prefix_warn("Non sono stati specificati storni.")
        else:
            fpros = [s for s in aqua_data['Fatpros'] if s.fps_qta != 0]

    except:
        logger.error("Errore durante l'inizializzazione!")
        raise
Beispiel #2
0
def costo_acqua_calda(qta):
    """
	Calcola il costo dell'acqua calda

	:param qta: <int> - Quantità consumata
	:return <Output()>
	"""
    assert isinstance(qta, (int, Decimal))

    codart = 'AC' if tipo_lettura == 'R' else 'ACS'
    try:
        ac = [x for x in fproc if x.fpc_bcodart == codart][0]
        importo = ac.fpc_costo
        return output_line(ac.fpc_bgiorni, 'C', codart, qta, importo)
    except:
        raise DataMissingError(
            '', "Nei costi manca il codice '{0}'".format(codart))
Beispiel #3
0
def main():
    global results

    # Isolamento letture casa da letture garage
    letture_casa = [x for x in fprol if x.fpl_garage == '']
    letture_garage = [x for x in fprol if x.fpl_garage == 'G']

    # Consumi casa
    mc_consumo_fredda_casa = consumo_mc(
        [x for x in letture_casa if x.fpl_fc == 0])
    mc_consumo_calda_casa = consumo_mc(
        [x for x in letture_casa if x.fpl_fc == 1])

    # Consumi garage
    mc_consumo_fredda_garage = consumo_mc(
        [x for x in letture_garage if x.fpl_fc == 0])
    mc_consumo_calda_garage = consumo_mc(
        [x for x in letture_garage if x.fpl_fc == 1])

    # ----------------------------------------------------------------------------------------------
    ##	Consumi totali - Attenzione: nei consorzi l'acqua calda NON SI SOMMA
    # ----------------------------------------------------------------------------------------------
    mc_consumo_totale_garage = mc_consumo_fredda_garage  # + mc_consumo_calda_garage
    mc_consumo_totale_casa = mc_consumo_fredda_casa  # + mc_consumo_calda_casa

    mc_consumo_totale_calda = mc_consumo_calda_casa + mc_consumo_calda_garage
    # mc_consumo_totale_fredda = mc_consumo_fredda_casa + mc_consumo_fredda_garage

    mc_consumo_totale = mc_consumo_totale_casa + mc_consumo_totale_garage
    # ----------------------------------------------------------------------------------------------

    # Periodo di riferimento dei consumi
    end_date = fpro.fp_data_let
    start_date = end_date - timedelta(days=fpro.fp_periodo)

    # Consumi
    gt = giorni_tariffe(start_date, end_date)
    if len([gt.items()]) == 0:
        msg = 'Nessuna tariffa applicabile al periodo specificato [{0} - {1}].'.format(
            start_date, end_date)
        raise InvalidDataError('', msg)

    # Lista ordinata di date di inizio periodo. Serve per dare un ordinamento ai record in output
    # (nella tupla delle chiavi di 'gt' il primo elemento è la data di inizio del periodo)
    periodi = sorted(set([x[0] for x in gt.keys()]))

    for k in gt.keys():
        data_vigore = k[0]

        # Per ogni periodo di tariffazione numfat viene incrementato di 1000 * (ordinale_periodo - 1)
        # Es: 1^ periodo: numfat + 1000 * 0 = numfat, 2^ periodo = numfat + 1000 * 1 = numfat + 1000, ecc.
        # In pratica il moltiplicatore è l'indice della data di inizio periodo nella lista ordinata "periodi"
        def ordina_tariffe(o):
            o.fpo_numfat += 1000 * periodi.index(data_vigore)
            return o

        res = []
        ts = [
            x for x in fprot
            if x.fpt_vigore == data_vigore and x.fpt_codtar == k[1]
        ]
        consumo = Decimal(round(mc_consumo_totale / fpro.fp_periodo * gt[k]))

        for tar in ts:
            qty = 0
            if tar.fpt_codtar[0] == 'A':
                if consumo > 0:
                    sc = scaglione(tar, gt[k])
                    qty = sc if consumo > sc else consumo
                    consumo -= qty
            else:
                qty = consumo if tar.fpt_costo_um == 'MC' else gt[k]

            if qty != 0:
                res += [ordina_tariffe(costo(tar, qty))]

        results += res

    # Per non aver problemi con l'ordinamento dell'output in caso di più di due periodi di tariffazione
    # impongo l'ordinamento a numfat + 1000 * numero di scadenze
    # Es. se ci sono 2 periodi sarà: nufat + 1000 * 2 = numfat + 2000
    def ordina(o):
        o.fpo_numfat += 1000 * len(periodi)
        return o

    # Acqua calda, se presente
    try:
        if mc_consumo_totale_calda > 0:
            results += [ordina(costo_acqua_calda(mc_consumo_totale_calda))]
    except:
        msg = "Consumo acqua calda > 0 (mc {0}) ma non sono presenti i relativi costi".format(
            mc_consumo_totale_calda)
        raise DataMissingError("Fatproc", msg)

    # Costi
    results += [ordina(c) for c in altri_costi()]

    # Storni
    if fpros:
        results += [
            ordina(s)
            for s in [calcolo_storno(fps) for fps in compatta_storni(fpros)]
        ]

    # Ordino i risultati rispetto fpo_numfat
    results.sort(key=lambda r: r.fpo_numfat)

    write_output(results)

    logger.debug('main(): Results written to %s',
                 basename(globals()['output_filename']))