Codice generico o codice facile da capire?

2

Al lavoro ora ho avuto una discussione con il collega, perché ho creato una pagina che ritiene troppo generica .

La pagina ha 3 modalità (semplice, avanzata e speciale) - deve funzionare in questo modo, perché non scegliamo come vengono scritte le specifiche. in ogni modalità la pagina ha un aspetto diverso (le modifiche non sono grandi - mostra / nasconde 5 campi di testo in diverse combinazioni in base alla modalità).

Il mio collega pensa che dovrebbe essere 3 pagine e quando cambi qualcosa dovresti semplicemente unire le modifiche ad altre due modalità.

I campi ora hanno il codice come rendered="#{mode!=2}" , ecc.

P.S. Ora la differenza è di 5 campi, ma in futuro no1 so quanto sarà cambiato .

Usiamo Seam (JSF / Facelets), ecco il codice pseudo facelet (per renderlo più facile da capire). Non l'ho inserito in panelGroup per presentare meglio il problema.

<h:output rendered="mode=2" value="Name: " />
<h:input rendered="mode=2" value="bean.name" />
<h:output rendered="mode=2" value="Surename: " />
<h:input rendered="mode=2" value="bean.surname"  />

<h:output rendered="mode!=2" value="Surename: " />
<h:input rendered="mode!=2" value="bean.surname"  />
<h:output rendered="mode!=2" value="#{mode==1?'My Name':'My friends name'}" />
<h:input rendered="mode!=2" value="bean.name" />

Ho duplicato la versione sarebbe simile a questo (pseudo codice)

<c:if test=mode=1>
        <ui:include view=modeSimple.xhtml>
</c:if>
<c:if test=mode=2>
        <ui:include view=modeAdv.xhtml>
</c:if>
<c:if test=mode=3>
        <ui:include view=modeSpec.xhtml>
</c:if>


modeSimple.xhtml
    <h:output value="Surename: " />
    <h:input value="bean.surname"  />
    <h:output value="My Name" />
    <h:input value="bean.name" />
modeAdv.xhtml
    <h:output value="Name: " />
    <h:input value="bean.name" />
    <h:output value="Surename: " />
    <h:input value="bean.surname"  />
modeSpec.xhtml
    <h:output value="Surename: " />
    <h:input value="bean.surname"  />
    <h:output value="My friends name" />
    <h:input value="bean.name" />
    
posta IAdapter 28.01.2011 - 10:02
fonte

8 risposte

8

Dovresti strutturare i tuoi modelli usando le stesse regole della programmazione. Ciò significa essenzialmente estrarre elementi di progettazione comuni in file separati per evitare la duplicazione e ottenere quindi un design più riutilizzabile. Questa è la regola n. 1 ( DRY ) e il metodo è chiamato refactoring in termini di programmazione.

La seconda regola è che dovresti sforzarti per la semplicità e la chiarezza. Dovrebbe essere facile capire il layout e dove andare quando hai bisogno di cambiare le cose.

Seguire la prima regola della lettera porta a una pesante decomposizione della tua gui in molti e piccoli snippet che possono rendere difficile capire come viene creato il layout. Devi cacciare molto per trovare dove sono le cose. Ciò viola la seconda regola, quindi devi trovare un equilibrio tra questi due opposti.

Ma l'approccio migliore è trovare una soluzione che eviti completamente questo problema. Penso che in questo caso dovresti considerare complessivamente un approccio più semplice . Presumo che questo sia HTML e si menzionano stati "semplici e avanzati" nella GUI. Hai considerato sempre generando tutti campi e quindi gestendo la logica della GUI in JavaScript? In altre parole, scrivi il codice lato client che nasconde e mostra i campi rilevanti al volo a seconda della modalità (stato) in cui si trova?

Questo ha anche il vantaggio di essere in grado di cambiare la modalità su richiesta senza coinvolgere il server e non devi compromettere nessuna delle regole. Un'altra cosa grandiosa è che puoi lasciare che i giocatori front-end facciano questi cambiamenti senza dover coinvolgere i programmatori di back-end che di solito non sono così entusiasti di passare il tempo a modificare e lucidare il design e l'interazione.

    
risposta data 28.01.2011 - 12:02
fonte
3

Senza vedere il codice, posso solo speculare, ma suppongo che al momento il tuo codice sia "sul bordo".

Per le modalità 2 o 3 con un numero limitato di modifiche tra quelle modalità, ciò che hai ora è probabilmente OK. Tuttavia, se fosse più complicato, sembra che dovrebbe essere rifatto in pagine separate.

Personalmente preferisco un codice facile da capire - è molto più gestibile, sia per gli altri sviluppatori che per te stesso quando devi riprenderlo di nuovo 6 mesi prima.

Tuttavia, non ha senso nel rifattorizzare il codice ora per risolvere un problema che potrebbe non esistere in futuro. Dici di non sapere quanto cambieranno i requisiti - e questo include nessun cambiamento - quindi applicare YAGNI (non ne hai bisogno) non fare nulla ora.

Contrassegna il codice in modo che richieda attenzione in futuro, in modo da non dimenticarlo, ma non cambiarlo (e potenzialmente interromperlo) ora.

    
risposta data 28.01.2011 - 10:11
fonte
3

Ho praticamente fatto la stessa cosa Credimi, dopo aver implementato alcuni comportamenti diversi per ogni modalità, la "pagina principale" diventa un casino quasi impossibile da leggere. Vedresti quindi solo un gruppo di blocchi di controllo (seguiti a breve da Matrix pioggia digitale). Mi sono ritrovato a rimuovere alcuni blocchi solo per avere una visione chiara di cosa c'è all'interno di una determinata modalità.

Quindi le "pagine separate" sono la strada da percorrere. Tuttavia, quando lo fai, devi "combattere" il problema della duplicazione del codice. È qui che il tuo collega potrebbe sbagliare suggerendo l'unione. Purtroppo l'ho fatto anche io. Fondamentalmente funziona, ma consuma un sacco di tempo prezioso e alla fine con una scarsa fusione "area comune" delle pagine non è sincronizzata e la fusione diventa un vero incubo. Quindi hai ragione nel contestare un'unione come soluzione ragionevole.

Come puoi vedere da molte risposte, l'approccio corretto è quello di estrarre parti veramente "comuni" su entità esterne (frammenti di pagine JSP, snippet JSF, qualunque cosa) e includerle in quelle pagine.

    
risposta data 28.01.2011 - 12:09
fonte
2

La duplicazione del codice non è praticamente mai una buona cosa. Detto questo, una piccola quantità duplicata non è più di due volte accettabile nella vita reale - è meglio essere pragmatici che religiosi a riguardo. Nel tuo caso, sembra una quantità maggiore di codice e 3 posizioni, quindi è leggermente superiore alla mia soglia personale. Quindi mi propongo per la versione generica. E in ogni caso, se funziona ora, non è necessario toccarlo solo per ragioni teoriche.

OTOH quando dici che ci possono essere più differenze tra le pagine in futuro, questo potrebbe significare che a un certo punto nel tempo diventa più economico passare a pagine separate (cercando di minimizzare la duplicazione tra loro estraendo elementi comuni come il più possibile). Quindi rivalutare la situazione prima di ogni cambiamento futuro.

    
risposta data 28.01.2011 - 10:13
fonte
0

Questo sembra JSF. Ogni render="..." significa essenzialmente che hai un if nel tuo codice, che causa ulteriore complessità.

Ho fatto la stessa cosa perché "è la stessa pagina solo con alcune differenze qua e là" e in parole semplici, non funziona a lungo termine perché < em> non è la stessa pagina e avrai bisogno di fare trucchi sempre più elaborati per farlo funzionare correttamente causando inutilmente difficoltà di manutenzione.

Se usi JSF con facelets invece di JSP (che dovresti se potessi), puoi creare frammenti XML corrispondenti a un blocco della pagina, che puoi quindi includere dove necessario. Questo ti comprerà la modularità e ti consentirà comunque di riutilizzare il contenuto tra le pagine.

Ascolta il tuo collega di lavoro. Ha ragione.

    
risposta data 28.01.2011 - 10:12
fonte
0

C'è la possibilità di generare la pagina usando il codice? In questo caso, che ne pensi di qualcosa di simile:

page1 = {
   showField1 = true;
   showField2 = false;
   showField3 = true;
  }
page2 = {
   showField1 = true;
   showField2 = false;
   showField3 = false;
  }

E nel codice di rendering della pagina

if page.showField1 then ....
if page.showField2 then ....

O in stile OOP:

class Page1 {
   renderField1() { ...}
   renderField2() {}
   renderField2() { ...}
}
class Page2 {
   renderField1() { ...}
   renderField2() {}
   renderField2() {}
}
    
risposta data 28.01.2011 - 10:15
fonte
0

il codice modale può solo peggiorare . Classificare e decidere una volta all'inizio e diramazione per ripulire le implementazioni senza modalità.

    
risposta data 28.01.2011 - 16:46
fonte
0

L'essenza di questa domanda sembra essere: quando hai tre pagine web molto simili con alcune piccole differenze, è meglio duplicare queste tre pagine e modificarle a seconda delle necessità, o costruire in una singola pagina la logica per dinamicamente rendere la pagina in base alla quale viene visualizzata la "modalità".

Per la cronaca, sono un ragazzo JSF e mi piace, e uso il rendering condizionale.

Se si sceglie di avere tre pagine, sussiste il rischio che man mano che si verificano dei cambiamenti, il manutentore potrebbe non applicarlo correttamente a tutte e tre le pagine.

Se scegli di utilizzare il rendering condizionale, risolvi il problema ma hai spostato alcune logiche di business nella tua pagina che potrebbero aver bisogno di un po 'di riflessione.

Personalmente non avrei problemi con l'uso del rendering condizionale, ma mi piacerebbe davvero vedere la logica della modalità spostata su un bean di supporto, ad esempio: invece di:

<h:output rendered="mode=2" value="Name: " />

Mi piace:

<h:output rendered="#{myBean.advancedMode}" value="Name: " />

Dove il bean gestisce la logica e restituisce true o false per controllare il rendering dell'elemento.

La ragione per cui la modalità visualizzata potrebbe dover controllare più di una sola pagina, potrebbe essere necessario mantenerla al di là anche della singola sessione dell'utente, oppure potrebbe essere necessario cambiare le modalità completamente in fondo alla strada.

Oppure, puoi accettare che entrambi gli approcci hanno potenziali aspetti negativi, e tutti i lati negativi sembrano riguardare l'allentamento dei dolori lungo la strada, e acconsentire a preoccuparsene ulteriormente quando una di quelle cose "in fondo alla strada" viene effettivamente fuori, e quindi prendere una decisione migliore ora che si sa di più su come i requisiti potrebbero cambiare.

    
risposta data 24.08.2017 - 18:36
fonte

Leggi altre domande sui tag