Principio aperto / chiuso, buone pratiche e regole aziendali

2

Sto scoprendo l'artigianato e sto cercando di impararlo, e ho deciso prima di tutto di capire come lavorare con i principi SOLID.

In realtà sto affrontando alcuni problemi mentre si tratta del principio Open / Closed.

Come sto lavorando

In effetti, di solito sto sviluppando applicazioni come le seguenti:

  • Livello di presentazione con Angolare
  • Livello aziendale con Node.js (utilizzando servizio / repository)
  • A questo punto estraiamo il DAL, solo per scopi di apprendimento

In realtà, inserivo le mie regole aziendali nei miei servizi, utilizzando più if e else istruzioni. Ma il fatto è che sono davvero aperto alle modifiche ma non all'estensione in quel caso. Voglio cambiarlo, in modo buono e aperto.

Le mie regole

Facciamo un semplice esempio in cui nella mia domanda devo raccogliere un indirizzo mail che deve corrispondere alle seguenti regole aziendali:

  • Il dominio dovrebbe essere esempio.com
  • La prima parte dell'indirizzo e-mail dovrebbe contenere un "." come "firstname.lastname"
  • La prima parte dell'indirizzo email deve essere inferiore a 100 caratteri

Come ho provato a ridefinire le mie istruzioni multiple if:

class BusinessMail{

  checkMail(){
      const ruleArray = []
      ruleArray.push(new MailCheckDomain(mail))
      ruleArray.push(new MailCheckLength(mail))
      ruleArray.push(new MailCheckDot(mail))

      for(const rule of ruleArray){
        if(!rule.apply()) return false
      }

      return true
    }

}

Proprio lì, sto lasciando le mie dichiarazioni if / else. Ma la mia funzione di controllo della posta è davvero aperta alle modifiche, perché se ho bisogno di avere una regola, devo averla nel mio corpo della funzione.

Un'altra soluzione sarebbe quella di iniettare il mio array nel mio servizio:

class BusinessMail {

  constructor (mailRules = []) {
    this.mailRules = mailRules
  }

  checkMail () {
    for (const rule of this.mailRules) {
      if (!rule.apply()) return false
    }

    return true
  }

}

In questo modo, non sono obbligato a creare le mie regole all'interno del mio servizio.

Ma cosa succede se ho una grande quantità di materiale all'interno di questa classe? Voglio dire, il mio dominio aziendale è davvero piccolo in quel caso. Ma cosa succede se ho un servizio che deve controllare come 50 regole diverse, su diverse funzioni? Significa che probabilmente dovrei inizializzare più matrici di regole.

Non mi sento bene con questa soluzione e sto cercando qualcosa di meglio se possibile.

Qualcuno sa come dovrei fare questo per applicare il mio principio OP al mio livello aziendale senza questa sensazione di "mancanza di fiducia"?

    
posta mfrachet 23.08.2016 - 08:22
fonte

1 risposta

8

Sei in un buon modo, ma quello che ti è successo succederà ancora e ancora: una volta che inizi a concentrarti su principi come SOLID e a rifare il tuo codice per essere migliore in qualche modo, succede qualcosa di strano - inizi a vedere le cose.

Suoni spettrali e a volte sembra così. Il punto, tuttavia, è che un design migliorato, per esempio. tramite i principi SOLID, rende molto più facile vedere punti vitali che non hai mai visto prima.

Ad esempio, ora ti lamenti di avere 50 diverse regole che dovrebbero essere inserite nel tuo costruttore. Contrariamente alla situazione precedente al tuo cambiamento, hai avuto le stesse 50 regole nascoste, incorporate e implicite da qualche parte all'interno della classe. Sono stati lì tutto il tempo, ma ora puoi davvero vederli. Perché non ti ha infastidito prima?

Come ti occupi di problemi come un artigiano? Semplice: accettalo come un fatto, poi risciacqua e ripeti. Hai risolto il problema di non essere aperto all'estensione, ora hai solo un altro problema da risolvere.

Ecco un'idea per una soluzione semplice e tipica: stai passando una serie di condizioni che un indirizzo e-mail deve soddisfare. Le condizioni (o predicati come talvolta vengono chiamati in quel contesto) hanno una composizione davvero fantastica. if (a && b) è facile da capire, ma ruleA && ruleB è possibile allo stesso modo! Alcuni linguaggi hanno anche operazioni integrate per questo (ad esempio in Java hai Predicate#and , #or , ecc.).

Il mio punto è: non si passano 10 regole per verificare la propria e-mail, ma si passa invece una singola condizione di verifica e-mail. Invece del ciclo for si applica semplicemente quella singola condizione, che di per sé applica tutte le altre condizioni.

Non posso dare suggerimenti simili per le altre 50 regole che hai, dato che ovviamente non ho idea di cosa siano. Lo schema generale rimane comunque: hai una versione migliorata del tuo codice, hai visto nuovi problemi e hai bisogno di trovare nuove soluzioni.

E un'ultima osservazione importante: non esagerare con questo! Assicurati che lo sforzo che fai sia giustificato, dal momento che questo ciclo di miglioramento può praticamente continuare all'infinito. Quanto migliore diventerai un artigiano, più problemi ti appariranno e più lavoro ci sarà da fare. Parte del lavoro professionale però è anche valutare il merito di questo lavoro. Migliorare il codice di una funzionalità esistente e funzionante non sta guadagnando nulla all'impresa immediatamente. Potrebbe ripagare in futuro con correzioni / miglioramenti / ecc., Ma potrebbe anche non esserlo. Questo tipo di giudizio è davvero difficile e hai bisogno di tanta esperienza. Se hai appena iniziato in quella direzione, ti suggerisco di farti aiutare da un mentore.

    
risposta data 23.08.2016 - 10:18
fonte