Affinare l’implementazione architetturale del software – Parte 1

Mediterranean Flavour of IT

Affinare l’implementazione architetturale del software – Parte 1

17 Febbraio 2019 Suggerimenti 0

AngularJS, Angular, Express, Spring, JavaScript, TypeScript, Java, FronEnd, BackEnd… Framework e linguaggi diversi che condividono le stesse problematiche di sviluppo; negli anni ho sempre seguito concetti come la centralizzazione del codice, l’atomicità dei componenti/classi, la riusabilità e l’estensibilità degli stessi, finendo per iniziare ogni nuovo progetto da quelle che definisco “le fondamenta”: una serie di utility che permettono di sviluppare più rapidamente e risolvere problematiche comuni a diverse funzionalità, pagine o servizi, agendo in un unico punto e seguendo un filo logico intuitivo favorendo eventuali passaggi di consegne.

Spesso si inizia un progetto senza avere una visione chiara del prodotto finale o quello che si andrà a fare a livello tecnico: uno degli errori più grandi è procedere senza uno schema iniziale; è infatti indispensabile da subito dedicare utility, funzioni wrapper, file di configurazione e costanti.

Configurazioni: Costanti, Enumeratori

Anche se apparentemente banale, dedicare file specifici per set di stringhe, valori, parametri di configurazione ed espressioni regolari, è di vitale importanza per avere da subito un insieme specifico di file dedicati per contenere valori frequentemente utilizzati nel progetto; di seguito qualche esempio concettuale:

  • Criteri di validazione
    • Espressioni regolari
    • lunghezza minima e massima stringa
    • valore minimo e massimo numerico
  • Parametri di configurazione web/client
    • Timeout (utili per simulare timeout di produzione inferiori ai 120 secondi dei browser)
    • Eventuali header da iniettare in ogni chiamata
  • Output (nel caso non provengano da un db)
    • Testi per l’utente / localizzazione
    • Errori / Codici di errore

Utility

Anche realizzare utility per le operazioni più banali è spesso una pratica molto sottovalitata; di seguito un esempio tra le più banali ed utili:

  • Conversione di formati con controllo valorizzazione
    • Parsing di date se valide e non null (da a diversi formati)
    • Parsing di flag (ad esempio Y/N) in booleani o null
    • Conversione tra enumeratori
  • Lettura e scrittura dati volatili comuni
    • cache
    • sessione

Wrapper di servizi

Una comodità, e spesso una necessità, è rappresentata dai wrapper di servizi, o il wrapper, a seconda del linguaggio può essere un metodo, una classe da estendere, una funzione o un servizio; sostanzialmente si tratta di un algoritmo, o una serie di algoritmi che vengono utilizzati prima e/o dopo ogni chiamata ai servizi http in modo da gestire opportunamente la predisposizione dati delle request, le casistiche di successo e di errore agendo sulle stesse per “reinterpretarle” dove necessario (sollevando eccezioni, reject o errore in caso di problematiche logiche come ad esempio i servizi soap). Di seguito alcuni vantaggi o logiche che è possibile integrare in funzionalità di questo tipo:

  • Animazioni di caricamento (loader / spinner)
  • Cache
  • Gestione promise concorrenti (per lo stesso servizio con il medesimo input)
  • Eventuali Header o input di configurazione
    • Chiavi per i servizi di terze parti
    • Header di identificazione
    • Header o parametri per il tipo dati accettato
  • Gestione degli errori centralizzata
    • Mapping di codici di errore logici
    • Mapping di codici HTTP
    • Output automatico errori
      • Modali / popup / snackbar / redirect
      • Codici HTTP / messaggi logici di risposta

Suggerisco sempre di combinare il wrapper di servizi con dei file di costanti/configurazione, in modo da rendere ancora più utile e pratico lo strumento stesso.

Questo post è disponibile anche in: Inglese