diff --git a/CHANGELOG.md b/CHANGELOG.md index 564b0e7f2..8db9e1787 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,11 +4,8 @@ Tutti i maggiori cambiamenti di questo progetto saranno documentati in questo fi Il formato utilizzato è basato sulle linee guida di [Keep a Changelog](http://keepachangelog.com/), e il progetto segue il [Semantic Versioning](http://semver.org/) per definire le versioni delle release. -## Tabella dei contenuti - -- [Tabella dei contenuti](#tabella-dei-contenuti) - [2.3 (In sviluppo)](#23-in-sviluppo) - [2.2 (2016-11-10)](#22-2016-11-10) - [2.1 (2015-04-02)](#21-2015-04-02) @@ -21,55 +18,26 @@ Il formato utilizzato è basato sulle linee guida di [Keep a Changelog](http://k - Creazione della documentazione ufficiale per sviluppatori (disponibile nel Wiki e in `docs/`) - Creazione di un sistema API ufficiale -- Creazione di un sistema per controllare gli accessi degli utenti -- Nuovi moduli _Viste_, _Utenti e permessi_, _Opzioni_, con ulteriori moduli per la gestione di tabelle secondarie (_IVA_, _Pagamenti_, ...) -- Nuova struttura per permettere il richiamo via AJAX delle procedure per la creazione di nuovi elementi all'esterno del modulo specifico (tramite il file `add.php`) -- Possibilità di vedere se ci sono altri utenti che stanno visualizzando lo stesso record (opzione "Sessione avanzata" nel modulo _Opzioni_) -- Nuove funzioni PHP (con commenti) in `lib/functions.php` - - getRevision - - str\_replace\_once - - filter - - post - - get - - readSQLFile - - array\_pluck - - starts_with - - ends_with - - slashes - - prepare - - tr (con aggiunta della funzione di gettext nel caso questi non sia abilitato - `_`) - - safe\_truncate (in sostituzione a cut\_text) - - secure\_random\_string - - random\_string - - safe\_truncate - - force\_download - - isHTTPS -- Nuovi oggetti per la gestione delle operazioni di base (posizionati in `lib/classes/`) - - Auth - - Database - - Filter (in sostituzione a HTMLHelper, ora deprecato ma ancora presente) - - HTMLBuilder - - Modules - - Options - - Permissions - - Translator (per la futura internazionalizzazione e traduzione del progetto, inoltre disponibile in `locale/it/`) - - Update - - Widgtes (modificati per lavorare secondo una metodologia statica) +- Creazione di sistemi centralizzati per la gestione della connessione al database, dell'autenticazione, degli input degli utenti, dei permessi, delle impostazioni, delle traduzioni e degli aggiornamenti (secondo una logica ad oggetti) - Nuova gestione delle operazioni di debugging e logging +- Nuovi plugins e widgets +- Nuovi moduli _Viste_, _Utenti e permessi_, _Opzioni_, con ulteriori moduli per la gestione di tabelle secondarie (_IVA_, _Pagamenti_, ...) +- Possibilità di vedere se ci sono altri utenti che stanno visualizzando lo stesso record (opzione "Sessione avanzata" nel modulo _Opzioni_) +- Possibilità di creare nuovi elementi dei moduli all'interno del record (oltre che dalla visualizzazione generale del modulo) +- Nuova struttura per permettere il richiamo via AJAX delle procedure per la creazione di nuovi elementi all'esterno del modulo specifico (tramite il file `add.php`) +- Miglioramento della documentazione integrata delle funzioni PHP in `lib/functions.php` - Nuovo file `lib/init.js` per permettere una rapida inizializzazione dei componenti JS - Creazione di cartelle di default per i backup (`backup/`) e i log (`logs/`) - Nuovo pulsante per resettare i filtri di ricerca (nella sezione generica dei moduli) - Nuovo modulo per gestire i file `.ini` dei componenti degli impianti -- Nuovi plugins e widgets - Nuova gestione generalizzata degli upload - Nuove funzioni relative ai diversi moduli - - Possibilità di inserire in fattura un range di serial number - Possibilità di individuare i componenti dell'impianto su cui l'intervento viene effettuato - Possibilità di gestire le ritenute d'acconto - Firma degli interventi - Selezione della tipologia di attività per ogni sessione di lavoro - Tabella riepilogativa più completa dei costi - - Sconto incondizionato in _Interventi_ + - Sconto globale in _Interventi_, _Fatture_, _DDT_, _Ordini_, _Preventivi_ ### Modificato (Changed) @@ -80,16 +48,16 @@ Il formato utilizzato è basato sulle linee guida di [Keep a Changelog](http://k - Miglioramenti delle informazioni disponibili sul progetto e della procedura di segnalazione dei bug - Impianti ora identificati tramite numerazione univoca (non più tramite matricola) - Sostituzione di Chosen con Select2 -- Miglioramento dell'interpretazione del template per la generazione degli input (`lib/htmlbuilder.php`), ora inoltre disponibile ovunque all'interno del progetto +- Miglioramento dell'interpretazione del template per la generazione degli input, ora disponibile ovunque all'interno del progetto - Miglioramento generale sull'identificazione del modulo attualmente in uso e sull'inclusione dei file necessari per il funzionamento - Miglioramento della gestione dei permessi -- Gestione della connessione al database tramite Medoo (possibile futuro ampliamento dei DMBS supportati) +- Gestione della connessione al database tramite PDO (con possibile futuro ampliamento dei DMBS supportati) - Gestione delle tabelle ora completamente basata su Datatables - Ottimizzazione della schermata per aggiunta dell'intervento - Miglioramento dei riquadri delle spese aggiuntive e degli articoli - La prima anagrafica di tipo Azienda caricata viene impostata come Azienda predefinita - Passaggio completo all'estensione `.php` per tutti i file dei moduli -- Miglioramento dei permessi di visione per il modulo _MyImpianti_, per cui ora ogni cliente vede solo i propri impianti +- Miglioramento dei permessi di visione per il modulo _MyImpianti_ (ora ogni cliente vede solo i propri impianti) - Miglioramento della procedura di aggiornamento del gestionale - Aggiunto sistema di ripresa dell'aggiornamento (se questi è stato bloccato in una fase intermedia tra i singoli aggiornamenti) - Aggiunto sistema di bloccaggio dell'aggiornamento, per evitare problemi nel caso molteplici richieste di update @@ -99,20 +67,7 @@ Il formato utilizzato è basato sulle linee guida di [Keep a Changelog](http://k ### Deprecato (Deprecated) - Classe HTMLHelper, a favore della nuova classe Filter -- Funzioni PHP - - readDateTime - - readDateTimePrint - - get\_permessi - - saveDateTime - - saveDate - - fix\_str - - clean - - makeid - - read - - readTime - - readDate - - build\_html\_element - +- Funzioni PHP (`lib/deprecated.php`) ### Rimosso (Removed) @@ -148,8 +103,9 @@ Il formato utilizzato è basato sulle linee guida di [Keep a Changelog](http://k ### Sicurezza (Security) -- Aggiunta protezione contro l'XSS +- Aggiunta protezione contro attacchi di tipo XSS - Aggiunta base per contrastare l'SQL Injection +- Aggiunta protezione (temporaneamente disabilitata) contro attacchi CSRF - Passaggio della codifica della password con algoritmo di hashing BCrypt ## 2.2 (2016-11-10) diff --git a/modules/anagrafiche/actions.php b/modules/anagrafiche/actions.php index 1bd7aa66c..271064a6a 100644 --- a/modules/anagrafiche/actions.php +++ b/modules/anagrafiche/actions.php @@ -68,14 +68,8 @@ switch (post('op')) { $dbo->query('UPDATE an_anagrafiche SET codice='.prepare($post['codice']).' WHERE idanagrafica='.prepare($id_record)); } - // Aggiorno gli agenti secondari collegati - $dbo->query('DELETE FROM an_anagrafiche_agenti WHERE idanagrafica='.prepare($id_record)); - - if (!empty($post['idagenti'])) { - foreach ($post['idagenti'] as $idagente) { - $dbo->query('INSERT INTO an_anagrafiche_agenti(idanagrafica, idagente) VALUES ('.prepare($id_record).', '.prepare($idagente).')'); - } - } + // Aggiorno gli agenti collegati + $dbo->sync('an_anagrafiche_agenti', ['idanagrafica' => $id_record], ['idagente' => (array) $post['idagenti']]); // Se l'agente di default è stato elencato anche tra gli agenti secondari lo rimuovo if(!empty($post['idagente'])){ diff --git a/modules/anagrafiche/edit.php b/modules/anagrafiche/edit.php index 6e5291f9c..994cd94bc 100644 --- a/modules/anagrafiche/edit.php +++ b/modules/anagrafiche/edit.php @@ -186,9 +186,6 @@ if ($fornitore) { {[ "type": "select", "label": "", "name": "idtipointervento_default", "values": "query=SELECT idtipointervento AS id, descrizione FROM in_tipiintervento ORDER BY descrizione ASC", "value": "$idtipointervento_default$" ]} -
{[ "type": "select", "label": "Agente principale", "name": "idagente", "values": "query=SELECT an_anagrafiche.idanagrafica AS id, IF(deleted=1, CONCAT(ragione_sociale, ' (Eliminato)'), ragione_sociale ) AS descrizione FROM an_anagrafiche INNER JOIN (an_tipianagrafiche_anagrafiche INNER JOIN an_tipianagrafiche ON an_tipianagrafiche_anagrafiche.idtipoanagrafica=an_tipianagrafiche.idtipoanagrafica) ON an_anagrafiche.idanagrafica=an_tipianagrafiche_anagrafiche.idanagrafica WHERE (descrizione='Agente' AND deleted=0)ORDER BY ragione_sociale", "value": "$idagente$" ]}
diff --git a/modules/contratti/modutil.php b/modules/contratti/modutil.php index 77ee95c9e..32d966b9c 100644 --- a/modules/contratti/modutil.php +++ b/modules/contratti/modutil.php @@ -170,6 +170,7 @@ function get_stato_preventivo($idpreventivo) /** * Aggiorna il budget del preventivo leggendo tutte le righe inserite. + * @deprecated 2.3 */ function update_budget_preventivo($idpreventivo) { diff --git a/modules/fatture/actions.php b/modules/fatture/actions.php index 2dc39a5eb..75d531cb6 100644 --- a/modules/fatture/actions.php +++ b/modules/fatture/actions.php @@ -197,6 +197,18 @@ switch (post('op')) { rimuovi_articolo_dafattura($rs[$i]['idarticolo'], $id_record, $rs[$i]['id']); } + // Se delle righe sono state create da un ordine, devo riportare la quantità evasa nella tabella degli ordini al valore di prima, riaggiungendo la quantità che sto togliendo + $rs = $dbo->fetchArray('SELECT qta, descrizione, idarticolo, idordine, idiva FROM co_righe_documenti WHERE iddocumento='.prepare($iddocumento)); + foreach ($rs as $r) { + $dbo->query('UPDATE or_righe_ordini SET qta_evasa=qta_evasa-'.$r['qta'].' WHERE descrizione='.prepare($r['descrizione']).' AND idarticolo='.prepare($r['idarticolo']).' AND idordine='.prepare($r['idordine']).' AND idiva='.prepare($r['idiva'])); + } + + // Se delle righe sono state create da un ddt, devo riportare la quantità evasa nella tabella dei ddt al valore di prima, riaggiungendo la quantità che sto togliendo + $rs = $dbo->fetchArray('SELECT qta, descrizione, idarticolo, idddt, idiva FROM co_righe_documenti WHERE iddocumento='.prepare($iddocumento)); + foreach ($rs as $r) { + $dbo->query('UPDATE dt_righe_ddt SET qta_evasa=qta_evasa-'.$r['qta'].' WHERE descrizione='.prepare($r['descrizione']).' AND idarticolo='.prepare($r['idarticolo']).' AND idddt='.prepare($r['idddt']).' AND idiva='.prepare($r['idiva'])); + } + $dbo->query('DELETE FROM co_documenti WHERE id='.prepare($id_record)); $dbo->query('DELETE FROM co_righe_documenti WHERE iddocumento='.prepare($id_record)); $dbo->query('DELETE FROM co_scadenziario WHERE iddocumento='.prepare($id_record)); @@ -321,12 +333,12 @@ switch (post('op')) { // Calcolo rivalsa inps $query = 'SELECT * FROM co_rivalsainps WHERE id='.prepare(get_var('Percentuale rivalsa INPS')); $rs = $dbo->fetchArray($query); - $rivalsainps = $subtot / 100 * $rs[0]['percentuale']; + $rivalsainps = ($subtot - $sconto) / 100 * $rs[0]['percentuale']; // Calcolo ritenuta d'acconto $query = 'SELECT * FROM co_ritenutaacconto WHERE id='.prepare(get_var("Percentuale ritenuta d'acconto")); $rs = $dbo->fetchArray($query); - $ritenutaacconto = ($subtot + $rivalsainps) / 100 * $rs[0]['percentuale']; + $ritenutaacconto = ($subtot - $sconto + $rivalsainps) / 100 * $rs[0]['percentuale']; $query = 'INSERT INTO co_righe_documenti(iddocumento, idintervento, idiva, desc_iva, iva, iva_indetraibile, descrizione, subtotale, um, qta, idrivalsainps, rivalsainps, idritenutaacconto, ritenutaacconto, idgruppo, `order`) VALUES('.prepare($id_record).', NULL, '.prepare($idiva).', '.prepare($desc_iva).', '.prepare($iva).', '.prepare($iva_indetraibile).', '.prepare('Trasferta intervento '.$codice.' del '.Translator::dateToLocale($data)).', '.prepare($subtot).", 'km' ".prepare($km).', '.prepare(get_var('Percentuale rivalsa INPS')).', '.prepare($rivalsainps).', '.prepare(get_var("Percentuale ritenuta d'acconto")).', '.prepare($ritenutaacconto).', (SELECT IFNULL(MAX(`idgruppo`) + 1, 0) FROM co_righe_documenti AS t WHERE iddocumento='.prepare($id_record).'), (SELECT IFNULL(MAX(`order`) + 1, 0) FROM co_righe_documenti AS t WHERE iddocumento='.prepare($id_record).'))'; $dbo->query($query); @@ -377,12 +389,12 @@ switch (post('op')) { // Calcolo rivalsa inps $query = 'SELECT * FROM co_rivalsainps WHERE id='.prepare(get_var('Percentuale rivalsa INPS')); $rs = $dbo->fetchArray($query); - $rivalsainps = $subtot / 100 * $rs[0]['percentuale']; + $rivalsainps = ($subtot - $sconto) / 100 * $rs[0]['percentuale']; // Calcolo ritenuta d'acconto $query = 'SELECT * FROM co_ritenutaacconto WHERE id='.prepare(get_var("Percentuale ritenuta d'acconto")); $rs = $dbo->fetchArray($query); - $ritenutaacconto = ($subtot + $rivalsainps) / 100 * $rs[0]['percentuale']; + $ritenutaacconto = ($subtot - $sconto + $rivalsainps) / 100 * $rs[0]['percentuale']; // Aggiunta riga intervento sul documento $query = 'INSERT INTO co_righe_documenti(iddocumento, idintervento, idconto, idiva, desc_iva, iva, iva_indetraibile, descrizione, subtotale, sconto, sconto_unitario, tipo_sconto, um, qta, idrivalsainps, rivalsainps, idritenutaacconto, ritenutaacconto, idgruppo, `order`) VALUES('.prepare($id_record).', '.prepare($idintervento).', '.prepare($idconto).', '.prepare($idiva).', '.prepare($desc_iva).', '.prepare($iva).', '.prepare($iva_indetraibile).', '.prepare($descrizione).', '.prepare($subtot).', '.prepare($sconto).', '.prepare($sconto_unitario).', '.prepare($tipo_sconto).", '-', ".prepare($qta).', '.prepare(get_var('Percentuale rivalsa INPS')).', '.prepare($rivalsainps).', '.prepare(get_var("Percentuale ritenuta d'acconto")).', '.prepare($ritenutaacconto).', (SELECT IFNULL(MAX(`idgruppo`) + 1, 0) FROM co_righe_documenti AS t WHERE iddocumento='.prepare($id_record).'), (SELECT IFNULL(MAX(`order`) + 1, 0) FROM co_righe_documenti AS t WHERE iddocumento='.prepare($id_record).'))'; @@ -542,12 +554,12 @@ switch (post('op')) { // Calcolo rivalsa inps $query = 'SELECT * FROM co_rivalsainps WHERE id='.prepare(get_var('Percentuale rivalsa INPS')); $rs = $dbo->fetchArray($query); - $rivalsainps = $prezzo / 100 * $rs[0]['percentuale']; + $rivalsainps = ($prezzo - $sconto) / 100 * $rs[0]['percentuale']; // Calcolo ritenuta d'acconto $query = 'SELECT * FROM co_ritenutaacconto WHERE id='.prepare(get_var("Percentuale ritenuta d'acconto")); $rs = $dbo->fetchArray($query); - $ritenutaacconto = ($prezzo) / 100 * $rs[0]['percentuale']; + $ritenutaacconto = ($prezzo - $sconto + $rivalsainps) / 100 * $rs[0]['percentuale']; // Aggiunta riga contratto sul documento $query = 'INSERT INTO co_righe_documenti(iddocumento, idcontratto, idconto, idiva, desc_iva, iva, iva_indetraibile, descrizione, subtotale, sconto, sconto_unitario, tipo_sconto, um, qta, idrivalsainps, rivalsainps, idritenutaacconto, ritenutaacconto, idgruppo, `order`) VALUES('.prepare($id_record).', '.prepare($idcontratto).', '.prepare($idconto).', '.prepare($idiva).', '.prepare($desc_iva).', '.prepare($iva).', '.prepare($iva_indetraibile).', '.prepare($descrizione).', '.prepare($prezzo).', '.prepare($sconto).', '.prepare($sconto_unitario).', '.prepare($tipo_sconto).", '-', 1, ".prepare(get_var('Percentuale rivalsa INPS')).', '.prepare($rivalsainps).', '.prepare(get_var("Percentuale ritenuta d'acconto")).', '.prepare($ritenutaacconto).', (SELECT IFNULL(MAX(`idgruppo`) + 1, 0) FROM co_righe_documenti AS t WHERE iddocumento='.prepare($id_record).'), (SELECT IFNULL(MAX(`order`) + 1, 0) FROM co_righe_documenti AS t WHERE iddocumento='.prepare($id_record).'))'; @@ -627,7 +639,7 @@ switch (post('op')) { // Calcolo rivalsa inps $query = 'SELECT * FROM co_rivalsainps WHERE id='.prepare(post('idrivalsainps')); $rs = $dbo->fetchArray($query); - $rivalsainps = $prezzo * $qta / 100 * $rs[0]['percentuale']; + $rivalsainps = ($prezzo * $qta - $sconto) / 100 * $rs[0]['percentuale']; // Calcolo ritenuta d'acconto $query = 'SELECT * FROM co_ritenutaacconto WHERE id='.prepare(post('idritenutaacconto')); @@ -692,12 +704,12 @@ switch (post('op')) { // Calcolo rivalsa inps $query = 'SELECT * FROM co_rivalsainps WHERE id='.prepare(post('idrivalsainps')); $rs = $dbo->fetchArray($query); - $rivalsainps = $prezzo * $qta / 100 * $rs[0]['percentuale']; + $rivalsainps = ($prezzo * $qta - $sconto) / 100 * $rs[0]['percentuale']; // Calcolo ritenuta d'acconto $query = 'SELECT * FROM co_ritenutaacconto WHERE id='.prepare(post('idritenutaacconto')); $rs = $dbo->fetchArray($query); - $ritenutaacconto = (($prezzo * $qta) + $rivalsainps) / 100 * $rs[0]['percentuale']; + $ritenutaacconto = (($prezzo * $qta) - $sconto + $rivalsainps) / 100 * $rs[0]['percentuale']; // Modifica riga generica sul documento $query = 'UPDATE co_righe_documenti SET idconto='.prepare($idconto).', idiva='.prepare($idiva).', desc_iva='.prepare($desc_iva).', iva='.prepare($iva).', iva_indetraibile='.prepare($iva_indetraibile).', descrizione='.prepare($descrizione).', subtotale='.prepare($subtot).', sconto='.prepare($sconto).', sconto_unitario='.prepare($sconto_unitario).', tipo_sconto='.prepare($tipo_sconto).', um='.prepare($um).', idritenutaacconto='.prepare(post('idritenutaacconto')).', ritenutaacconto='.prepare($ritenutaacconto).', idrivalsainps='.prepare(post('idrivalsainps')).', rivalsainps='.prepare($rivalsainps).' WHERE idgruppo='.prepare($idgruppo).' AND iddocumento='.prepare($iddocumento); diff --git a/modules/partitario/dettagli_movimento.php b/modules/partitario/dettagli_movimento.php new file mode 100644 index 000000000..d0a982b13 --- /dev/null +++ b/modules/partitario/dettagli_movimento.php @@ -0,0 +1,55 @@ +fetchArray($query); + +echo ' + + + + + '._('Um').' + '; + +$totale_imponibile = 0; + +for ($i = 0; $i < sizeof($rs); ++$i) { + echo ' + + + + + + + + + '; + + $totale_imponibile += $rs[$i]['imponibile']; + $totale_qta += $rs[$i]['qta']; +} + +echo ' + + + + + + +
'._('Descrizione riga').''._('Imponibile').''._('Q.tà').'
+ '.$rs[$i]['desc_riga'].' + + '.Translator::numberToLocale($rs[$i]['imponibile']).' € + '.Translator::numberToLocale($rs[$i]['qta']).' + + '.$rs[$i]['um'].' +
'._('Totali').': '.Translator::numberToLocale($totale_imponibile).' €'.Translator::numberToLocale($totale_qta).'
+ +
'.$rs[0]['desc_fatt'].''; diff --git a/modules/partitario/edit.php b/modules/partitario/edit.php index 21c3c671e..f6289b7b2 100644 --- a/modules/partitario/edit.php +++ b/modules/partitario/edit.php @@ -104,7 +104,8 @@ for ($x = 0; $x < $n1; ++$x) { if ($rs[$i]['iddocumento'] != '') { ($rs[$i]['dir'] == 'entrata') ? $id_module = Modules::getModule('Fatture di vendita')['id'] : $id_module = Modules::getModule('Fatture di acquisto')['id']; - echo " ".$rs[$i]['descrizione']."\n"; + echo "".$rs[$i]['descrizione']."\n"; + //echo " ".$rs[$i]['descrizione']."\n"; } else { echo ' '.$rs[$i]['descrizione']."\n"; } diff --git a/modules/preventivi/modutil.php b/modules/preventivi/modutil.php index dfef46aba..d4a69c60b 100644 --- a/modules/preventivi/modutil.php +++ b/modules/preventivi/modutil.php @@ -180,6 +180,7 @@ function get_stato_preventivo($idpreventivo) /** * Aggiorna il budget del preventivo leggendo tutte le righe inserite. + * @deprecated 2.3 */ function update_budget_preventivo($idpreventivo) {