campo-sirio/src/f9/f9lib02.cpp
Simone Palacino 1de19f9346 Patch level : 12.0 972
Files correlati     : f90.exe d181.des f181.dir/.trr f9ProspIntegr.rep masks f90104.sql
Commento            :
- Rimosso controllo vendite in ogni caso. Incompatibilita' con diverse situazioni tra cui note di credito interne che non sono fatture elettroniche.
- Rimosso flag check vendite e il suo utilizzo nel codice.
- Aggiornamento stato estrazione solo dopo scrittura f9iva.
- Migliorata e resa piu' sicura query per iva aggiungendo tipi diversi e controllo lunghezza colonna.
- Corretti nomi campi, che venivano invertiti IVA_ANNPROT e IVA_NUMPROT.
- Aggiunto controllo in apertura controllo estrazione solo se il pacchetto e' in errore diag. gest.
- Spostata in una classe separata la maschera per l'apertura del pacchetto (Apri estr.).
- Corretta modifica f9wa rimaneva vuoto il record in alcuni casi.
- Aggiunta possibilita' di esclusione movimenti dall'Apri estr.
- Aggiunto controllo esistenza categorie documentali, caricamento cat. doc. di default e controllo tipi documento duplicati.
- Aggiunta colonna a F9DRT in caso mancasse (Dovuta a creazione da fp).
- Aggiunta funzione provvisoria per calcolo somma imponibili e imposte da rmoviva.
2020-07-01 17:23:56 +02:00

540 lines
16 KiB
C++

#include "f9lib01.h"
#include "applicat.h"
#include "docf9.h"
#include "annessif9.h"
#include "f901tab.h"
#include "mov.h"
#include "anagr.h"
#include "comuni.h"
#include "clifo.h"
#include "report.h"
#define AMBIENTE_F9 "CODSOC" // Codice ambiente (codsoc)
#define ADDRCART_F9 "ADDRCART"
#define ADDRDOC_F9 "ADDDOC" // Indirizzo documenti cartacei
#define ESTENSIONI_F9 "DOCUMENTI_EXT" //
#define CARTEXP_F9 "CARTEXP" // Flag esporta documenti cartacei
#define CHECKVEND_F9 "CHECKVEND" // Flag controlli per vendite (quando hai fatt. con Campo)
#define VIEWMOV_F9 "VIEWMOVPRE" // Flag visualizza movimenti prima di estrarre
TF9_config F9CONF;
void TF9_config::set_ambiente(const TString& cod_amb)
{
ini_set_string(CONFIG_DITTA, "F9", AMBIENTE_F9, cod_amb);
_ambiente = cod_amb;
}
void TF9_config::set_addr_doc(const TString& path)
{
ini_set_string(CONFIG_DITTA, "F9", ADDRDOC_F9, path);
_addr_doc = path;
}
void TF9_config::set_has_cartexp(const bool flag)
{
ini_set_bool(CONFIG_DITTA, "F9", CARTEXP_F9, flag);
_cartexp = flag;
}
void TF9_config::set_has_checkvend(const bool flag)
{
ini_set_bool(CONFIG_DITTA, "F9", CHECKVEND_F9, false);
_checkvend = flag;
}
void TF9_config::set_viewmov(const bool flag)
{
ini_set_bool(CONFIG_DITTA, "F9", VIEWMOV_F9, flag);
_viewmovpre = flag;
}
void TF9_config::set_addr_cart(const TString& path)
{
ini_set_string(CONFIG_DITTA, "F9", ADDRCART_F9, path);
_addr_cart = path;
}
void TF9_config::set_estensioni(const TString& ext)
{
ini_set_string(CONFIG_DITTA, "F9", ESTENSIONI_F9, ext);
_estensioni = ext;
}
TF9_config::TF9_config()
{
_ambiente = ini_get_string(CONFIG_DITTA, "F9", AMBIENTE_F9);
_addr_cart = ini_get_string(CONFIG_DITTA, "F9", ADDRCART_F9);
_addr_doc = ini_get_string(CONFIG_DITTA, "F9", ADDRDOC_F9);
_cartexp = ini_get_bool (CONFIG_DITTA, "F9", CARTEXP_F9);
_checkvend = ini_get_bool (CONFIG_DITTA, "F9", CHECKVEND_F9, true);
_estensioni = ini_get_string(CONFIG_DITTA, "F9", ESTENSIONI_F9);
_viewmovpre = ini_get_bool (CONFIG_DITTA, "F9", VIEWMOV_F9);
}
///////////////////////////////////////////////////////////////////////////////
// TF9_doccart
///////////////////////////////////////////////////////////////////////////////
bool TF9_doccart::doc_already_exists(const TFilename& file, _Out_ TString& numreg, _Out_ bool& annesso)
{
numreg = "";
annesso = false;
_tdocs.zero();
_tdocs.setkey(2);
_tdocs.put(F9C_FILENAME, file.name());
bool ok = _tdocs.read() == NOERR;
if (ok)
numreg = _tdocs.get(F9C_NUMREG);
else
{
_tannessi.zero();
_tannessi.setkey(2);
_tannessi.put(F9A_FILENAME, file.name());
ok = _tannessi.read() == NOERR;
if (ok)
{
numreg = _tannessi.get(F9A_NUMREG);
annesso = true;
}
}
return ok;
}
bool TF9_doccart::mov2doc(const TString& numreg, _Out_ TFilename& doc)
{
_tdocs.zero();
_tdocs.setkey(1); // Ricerca per NUMREG
_tdocs.put(F9C_NUMREG, numreg);
const bool ok = _tdocs.read() == NOERR;
doc.cut(0);
if (ok)
doc << TFilename(F9CONF.get_addr_cart()).slash_terminate() << _tdocs.get(F9C_FILENAME);
return ok;
}
bool TF9_doccart::mov2listann(const TString& numreg, _Out_ TString_array& list_annessi)
{
list_annessi.destroy();
_tannessi.zero();
_tannessi.setkey(1);
_tannessi.put(F9A_NUMREG, numreg);
TString numreg_fetched;
bool ok = false;
// Si posiziona nl primo record giusto. Poi per sapere quando terminare guardo se la chiave e' ancora quella giusta.
for (_tannessi.read(_isgteq); (numreg_fetched = _tannessi.get(F9A_NUMREG)) == numreg; _tannessi.next())
{
ok = true;
TString filename = _tannessi.get(F9A_FILENAME);
TToken_string t;
t.add(numreg_fetched);
t.add(_tannessi.get(F9A_FILENAME));
t.add(_tannessi.get(F9A_CATDOCPAD));
t.add(_tannessi.get(F9A_CATDOCANN));
t.add(_tannessi.get(F9A_LOADDATE));
t.add(_tannessi.get(F9A_USER));
list_annessi.add(t);
#ifdef DBG
CHECK(numreg_fetched == numreg_fetched, "*Maledetooo*");
#endif
}
return ok;
}
bool TF9_doccart::mov2listann_vect(const TString& numreg, _Out_ vector<annesso_t>& list_annessi)
{
list_annessi.clear();
_tannessi.zero();
_tannessi.setkey(1);
_tannessi.put(F9A_NUMREG, numreg);
TString numreg_fetched;
bool ok = false;
// Si posiziona nl primo record giusto. Poi per sapere quando terminare guardo se la chiave e' ancora quella giusta.
for (bool r = _tannessi.read(_isgteq) == NOERR; (numreg_fetched = _tannessi.get(F9A_NUMREG)) == numreg && r; r = _tannessi.next() == NOERR)
{
ok = true;
TString filename = _tannessi.get(F9A_FILENAME);
annesso_t t;
t.numreg = numreg_fetched;
t.filename = _tannessi.get(F9A_FILENAME);
t.catdocpad = _tannessi.get(F9A_CATDOCPAD);
t.catdocann = _tannessi.get(F9A_CATDOCANN);
t.loaddate = _tannessi.get(F9A_LOADDATE);
t.user = _tannessi.get(F9A_USER);
list_annessi.emplace_back(t);
#ifdef DBG
CHECK(numreg_fetched == numreg_fetched, "*Maledetooo*");
#endif
}
return ok;
}
///////////////////////////////////////////////////////////////////////////////
// TIva_insert_prepared_stat
///////////////////////////////////////////////////////////////////////////////
void TIva_insert_prepared_stat::add_value(const char* field, const TString& value)
{
_fields.insert(_fields.end(), { field, value });
}
void TIva_insert_prepared_stat::write()
{
TString vals_appo;
_query.cut(0) << "INSERT INTO " F9_IVA " (\n";
int count = 0;
bool first = true;
for(auto it = _fields.begin(); it != _fields.end(); ++it)
{
if (!first)
{
_query << ", ";
vals_appo << ", ";
}
if (!first && count == 0)
{
_query << "\n";
vals_appo << "\n";
}
_query << it->first;
vals_appo << it->second;
first = false;
count = ++count % 3;
}
_query << "\n)\nVALUES (\n" << vals_appo << "\n)";
}
void TIva_insert_prepared_stat::add(const char* field, const TString& str, const int len)
{
if (len == -1 || str.len() <= len)
{
TString v; v << "'" << check_str(str) << "'";
add_value(field, v);
}
else
_ok &= false;
}
void TIva_insert_prepared_stat::add(const char* field, const TDate& date)
{
TString v;
if (date.ok())
v << "'" << date.date2ansi() << "'";
else
v << "'00010101'";
add_value(field, v);
}
void TIva_insert_prepared_stat::add(const char* field, const char* str, const int len)
{
add(field, TString(str), len);
}
void TIva_insert_prepared_stat::add(const char* field, char c)
{
TString v; v << "'" << c << "'";
add_value(field, v);
}
void TIva_insert_prepared_stat::add(const char* field, long l)
{
TString v; v << l;
add_value(field, v);
}
void TIva_insert_prepared_stat::add_getdate(const char* field)
{
_fields.insert(_fields.end(), { field, "GETDATE()" });
}
bool TIva_insert_prepared_stat::get(TString& query)
{
if (_query.empty())
write();
query.cut(0) << _query;
return _ok;
}
void TIva_insert_prepared_stat::reset()
{
_fields.clear();
_ok = true;
_query.cut(0);
}
///////////////////////////////////////////////////////////////////////////////
// TProspetto_recset
///////////////////////////////////////////////////////////////////////////////
void TProspetto_recset::precarica_tabelle()
{
TString sql;
const char* v[] = { "RMOVIVA", "MOV", "PCON", "TABCOM" };
for (auto& i : v)
{
sql.cut(0) << "SELECT * FROM " << i;
set(sql);
items();
}
}
void TProspetto_recset::get_sum_imponibile_imposta(const char* numreg_ven, real& s_imponibili, real& s_imposte)
{
TRecord_array iva(LF_RMOVIVA, RMI_NUMRIG);
TRectype* ivafilter = new TRectype(LF_RMOVIVA);
ivafilter->put(RMI_NUMREG, numreg_ven);
iva.read(ivafilter);
s_imponibili = ZERO;
s_imposte = ZERO;
for (int i = iva.first_row(); i <= iva.rows(); ++i)
{
TRectype& r = iva[i];
s_imponibili += r.get_real("IMPONIBILE");
s_imposte += r.get_real("IMPOSTA");
}
}
TProspetto_recset::TProspetto_recset(const char* numreg_acq, const char* numreg_ven) : TSQL_recordset("")
{
_numreg = new TString;
_today = new TString;
_ragsoc = new TString;
_address = new TString;
_cap = new TString;
_citta = new TString;
_provin = new TString;
_codfisc = new TString;
_partiva = new TString;
_ndoc = new TString;
_datadoc = new TString;
_totdoc = new TString;
_codforn = new TString;
_ragsocforn = new TString;
_addrforn = new TString;
_capforn = new TString;
_cittaforn = new TString;
_provinforn = new TString;
_partivaforn = new TString;
_regacq = new TString;
_protivaacq = new TString;
_dataregacq = new TString;
_totale = new TString;
_totimponibile = new TString;
_totimposta = new TString;
// In modo da dare la possibilita' a SQLite di caricare le tabelle di campo,
// altrimenti con tutte le join e from concatenate non ce la fa e fallirebbe.
precarica_tabelle();
TLocalisamfile anagraf(LF_ANAG), clifo(LF_CLIFO), comuni(LF_COMUNI), mov_acq(LF_MOV), mov_ven(LF_MOV), rmoviva(LF_RMOVIVA);
mov_acq.put(MOV_NUMREG, numreg_acq);
mov_acq.read();
anagraf.put(ANA_TIPOA, "G");
anagraf.put(ANA_CODANAGR, prefix().get_codditta());
anagraf.read();
format_string(*_numreg, TString(numreg_ven));
format_string(*_today, TDate(TODAY));
// DATI SOCIETA':
format_string(*_ragsoc, anagraf.get(ANA_RAGSOC));
format_string(*_address, TString(anagraf.get(ANA_INDRES)) << ", " << anagraf.get(ANA_CIVRES));
format_string(*_cap, anagraf.get(ANA_CAPRES));
comuni.put(COM_COM, anagraf.get(ANA_COMRES));
if (comuni.read() == NOERR)
{
format_string(*_citta, comuni.get(COM_DENCOM));
format_string(*_provin, comuni.get(COM_PROVCOM));
}
else
{
format_string(*_citta, TString(""));
format_string(*_provin, TString(""));
}
format_string(*_codfisc, anagraf.get(ANA_COFI));
format_string(*_partiva, anagraf.get(ANA_PAIV));
TString ndoc_s; ndoc_s << mov_acq.get(MOV_NUMDOCEXT);
if (ndoc_s.empty())
ndoc_s << mov_acq.get(MOV_NUMDOC);
format_string(*_ndoc, ndoc_s);
format_string(*_datadoc, mov_acq.get(MOV_DATADOC));
format_string(*_totdoc, mov_acq.get(MOV_TOTDOC));
TString codforn_s; codforn_s << mov_acq.get(MOV_CODCF);
clifo.zero();
clifo.put(CLI_TIPOCF, "F");
clifo.put(CLI_CODCF, codforn_s);
bool ok = clifo.read() == NOERR;
format_string(*_codforn, codforn_s);
format_string(*_ragsocforn, ok ? clifo.get(CLI_RAGSOC) : "");
format_string(*_addrforn, ok ? TString(clifo.get(CLI_INDCF)) << ", " << clifo.get(CLI_CIVCF) : "");
format_string(*_capforn, ok ? clifo.get(CLI_CAPCF) : "");
if (ok)
{
comuni.zero();
comuni.put(COM_COM, clifo.get(CLI_COMCF));
comuni.read();
}
format_string(*_cittaforn, ok ? comuni.get(COM_DENCOM) : "");
format_string(*_provinforn, ok ? comuni.get(COM_PROVCOM) : "");
format_string(*_partivaforn, ok ? clifo.get(CLI_PAIV) : "");
// Info registrazioni
format_string(*_regacq, mov_acq.get(MOV_REG));
format_string(*_protivaacq, mov_acq.get(MOV_PROTIVA));
format_string(*_dataregacq, mov_acq.get(MOV_DATAREG));
// Calcolo dal rmoviva
real s_imponibili, s_imposte;
/*TMovimento_contabile movimento_pn;
TLocalisamfile mov(LF_MOV);
mov.put(MOV_NUMREG, numreg_ven);
mov.read();
if (movimento_pn.read(mov) != NOERR)
bool simo = true;
s_imponibili = movimento_pn.imponibile("");
s_imposte = movimento_pn.imposta("");*/
/*TMovimentoPN _movimento_pn;
TRectype& rec = _movimento_pn.curr();
rec.put(MOV_NUMREG, numreg_ven);
if (_movimento_pn.read() != NOERR)
bool simo = true;*/
get_sum_imponibile_imposta(numreg_ven, s_imponibili, s_imposte);
format_string(*_totale, TString() << s_imponibili + s_imposte);
format_string(*_totimponibile, s_imponibili.stringa());
format_string(*_totimposta, s_imposte.stringa());
TString sql; sql << "SELECT COD, CODTAB, S0, R0,\n"
"B.GRUPPO, B.CONTO, B.SOTTOCONTO, B.DESCR,\n"
"B.NUMREG, B.CODIVA, B.IMPONIBILE, B.IMPOSTA, B.GRUPPO, B.CONTO, B.SOTTOCONTO, B.DATAREG, B.DATADOC, B.REG, B.PROTIVA, B.TOTDOC,\n"
<< *_today << " AS TODAY, " << *_ragsoc << " AS RAGSOC, " << *_address << " AS ADDRSEDE, " << *_cap << " AS CAP, " << *_citta << " AS CITTA, " << *_provin << " AS PROVIN,\n"
<< *_codfisc << " AS CODFISC, " << *_partiva << " AS PARTIVA,\n"
<< *_ndoc << " AS NDOC, " << *_datadoc << " AS DATADOC,\n"
<< *_codforn << " AS CODFORN, " << *_ragsocforn << " AS RAGSOCFORN, " << *_addrforn << " AS ADDRFORN, " << *_capforn << " AS CAPFORN, " << *_cittaforn << " AS CITTAFORN, " << *_provinforn << " AS PROVINFORN, " << *_partivaforn << " AS PARTIVAFORN,\n"
<< *_totdoc << " AS TOTDOC,\n"
<< *_regacq << " AS REGACQ, " << *_protivaacq << " AS PROTIVAACQ, " << *_dataregacq << " AS DATAREGACQ,\n"
<< *_totale << " AS TOTALE, " << *_totimponibile << " AS TOTIMPONIBILE, " << *_totimposta << " AS TOTIMPOSTA\n"
"FROM(\n"
"\n"
" SELECT PCON.GRUPPO, PCON.CONTO, PCON.SOTTOCONTO, PCON.DESCR,\n"
" A.NUMREG AS NUMREG, A.CODIVA, A.IMPONIBILE, A.IMPOSTA, A.GRUPPO, A.CONTO, A.SOTTOCONTO, A.DATAREG, A.DATADOC, A.REG, A.PROTIVA, A.TOTDOC\n"
" FROM(\n"
" SELECT RMOVIVA.NUMREG AS NUMREG, CODIVA, IMPONIBILE, IMPOSTA, GRUPPO, CONTO, SOTTOCONTO, DATAREG, DATADOC, REG, PROTIVA, TOTDOC\n"
" FROM RMOVIVA\n"
" JOIN MOV\n"
" ON MOV.NUMREG = RMOVIVA.NUMREG\n"
" WHERE MOV.NUMREG = " << *_numreg << "\n"
"\n"
" ) A\n"
" JOIN PCON\n"
" ON PCON.GRUPPO = A.GRUPPO AND PCON.CONTO = A.CONTO AND PCON.SOTTOCONTO = A.SOTTOCONTO\n"
") B\n"
"JOIN TABCOM\n"
"ON COD = 'IVA' AND CODTAB = B.CODIVA";
set(sql);
}
TProspetto_recset::~TProspetto_recset()
{
delete _numreg;
delete _today;
delete _ragsoc;
delete _address;
delete _cap;
delete _citta;
delete _provin;
delete _codfisc;
delete _partiva;
delete _ndoc;
delete _datadoc;
delete _totdoc;
delete _codforn;
delete _ragsocforn;
delete _addrforn;
delete _capforn;
delete _cittaforn;
delete _provinforn;
delete _partivaforn;
delete _regacq;
delete _protivaacq;
delete _dataregacq;
delete _totale;
delete _totimponibile;
delete _totimposta;
}
///////////////////////////////////////////////////////////////////////////////
// TF9Prospetto_integr
///////////////////////////////////////////////////////////////////////////////
TFilename TF9Prospetto_integr::get_path_rep()
{
// Guardo prima nella custom, altrimenti nella root di Campo
TFilename freport = firm2dir(-1);
freport.add("custom");
freport.add(_name);
freport.ext("rep");
if (!freport.exist())
{
freport.currdir().slash_terminate() << _name;
freport.ext("rep");
}
return freport;
}
bool TF9Prospetto_integr::export_pdf(TFilename& tmp)
{
return _book.export_pdf(tmp, false);
}
const char* TF9Prospetto_integr::make_name_rep()
{
return "prosp_rev.pdf";
}
bool TF9Prospetto_integr::preview()
{
return _book.preview();
}
bool TF9Prospetto_integr::operator()(const char* numreg_acq, const char* numreg_ven)
{
if (_rep.load(_f_report))
{
TFilename fprosp; fprosp.tempdir().slash_terminate() << make_name_rep();
TProspetto_recset* _prosp_rs = new TProspetto_recset(numreg_acq, numreg_ven);
_items = _prosp_rs->items();
_rep.set_recordset(&*_prosp_rs);
_book.add(_rep);
}
else
{
warning_box("Impossibile trovare il report %s per la generazione\ndel prospetto di integrazione Reverse Charge", _name);
return false;
}
return true;
}
TF9Prospetto_integr::TF9Prospetto_integr() : _f_report(get_path_rep()), _items(0)
{ }