ABONAMENTE VIDEO REDACȚIA
RO
EN
×
▼ LISTĂ EDIȚII ▼
Numărul 36
Abonament PDF

Model Driven Design – de la teorie la practică

Daniel Donea
Associate IT Consultant
@.msg systems Romania
PROGRAMARE


Acest articol oferă o abordare teoretică minimală asupra Designului bazat pe modele (Model Drive Design), dezvoltat printr-o Arhitectura bazată pe Modele (Model Driven Architecture). De asemenea, descrie ce este un Model Conceptual și cum este el legat de Modelul Domeniului/Modelul Problemei. Ulterior, va oferi un exemplu simplu despre cum este creat un Model și manipulat în dezvoltarea software-ului bazat pe Modele.

Primul subiect supus discuției: ce este un model? Conceptul de "Model" cât și modul în care acesta conduce spre o soluție sunt, în continuare, supuse unor discuții. Din acest motiv, există mai multe definiții pentru modele și, de asemenea, există o serie de tipuri de modele (model conceptual, modelul de domeniu, modelul de business, etc.). În acest sens, ar trebui să clarificăm anumite aspecte legate de terminologia formată în jurul conceptului de "Model".

Concepte

Orice software soluționează o problemă a clientului. Această problemă poate fi împărțită în mai multe zone de interes. Pe baza acestor zone de interes, se extrag topicuri (teme) relevante software-ului.

Un domeniu descrie una sau mai multe zone de interes din cadrul unei probleme. Dacă zona de interes corespunde unor probleme de business, acesta va fi un domeniu de business. În general, se folosește noțiunea de domeniu al problemei, termen de ansamblu, care reflectă una sau mai multe zone de interes.

În știința calculatoarelor, modelul domeniului constă în reprezentarea tuturor topicurilor specifice unei probleme / zone de interes. În fapt, modelul domeniului descrie problema prin separarea ei în subprobleme, în funcție de domeniul de interes. Aceasta se realizează prin extragerea conceptelor cheie ale subproblemelor și legându-le împreună. La sfârșitul acestui proces, vom vedeam o perspectivă mai ușoară de înțeles a problemei și potențiala ei soluție.

Bazându-ne pe acest model al domeniului, noi descriem modelul conceptual (numit pe scurt "model") care propune o posibilă soluție a problemei. Modelul conceptual este o abstractizare bazată pe conceptele și relațiile formate din modelul domeniului.

Modelul devine o abstractizare a unui sistem fizic, în care programatorul va descrie diferite entități, atributele lor, relațiile și constrângerile dintre entități. Acesta, de asemenea, creează o perspectivă structurală asupra soluției în care accentul este pus pe ceea ce e important, ignorând detaliile.

Despre Model driven design/model driven architecture

Există mai multe păreri legat de ceea ce este Model Driven Design (MDD) și cum ar trebui să arate Model Driven Architecture (MDA). Opinia larg acceptată provine de la Object Management Group (OMG) - un consorțiu de organizații software care dezvoltă și susțin specificații, pentru a îmbunătăți practicile de dezvoltare și implementare a software-ului enterprise.

Acest grup a creat framework-ul conceptual, numit "Model Driven Architecture", care separă deciziile de business (ceea ce face aplicația), de deciziile orientate pe software (cum face aplicația), folosind "o abordare a specificațiilor de sistem, bazată pe utilizarea modelelor formale". [1]

MDA folosește modele pentru descrierea businessului (funcționalității) soluției, independent de orice constrângere de sistem (decizii orientate către software).

În MDA, "Modelele independente de platformă sunt exprimate într-un limbaj de modelare independent de platformă". Pe scurt, modelul este descris în funcție de specificație, independent de limbajul de programare în care va fi transformat, iar codul sursă propriu-zis este descris o dată cu modelul sau după ce modelul este terminat. Modelul va fi întotdeauna prioritar.

Exemplul oferit în acest articol este influențat de viziunea dată de către cei de la Object Management Group asupra MDA.

Despre Model driven software development

Thomas Stahl descrie Model-driven software development (MDSD) ca fiind : "o alternativă la round-trip engineering. Round-trip engineering este conceptul de a fi capabili de a face orice fel de schimbare asupra unui model, precum și asupra codului generat de acel model. Modificările sunt propagate bidirecțional și ambele artefacte sunt întotdeauna consistente. Trecerea de la cod la model (inginerie inversă) este deosebit de interesantă în acest context. Model Driven Engineering oferă instrumentele utilizate pentru constrângeri specifice domeniului și realizează verificarea modelului. "[2]

Din acest motiv, Model-driven software development este un mijloc prin care se pot dezvolta aplicații descrise printr-o Model Driven Architecture. Model-driven software development este format din:

Produsul final va fi cod descris într-un limbaj specific, care reflectă modelul specificat. Aceasta asigură nu numai consistența conceptuală a arhitecturii, dar și ajută la dezvoltarea funcțională a aplicației. "Capacitatea de a sintetiza artefacte din modele contribuie la asigurarea coerenței între implementarea aplicațiilor și analiza informațiilor asociate cu cerințele funcționale și QoS, cerințe surprinse de către modele."[3]

Există și alte avantaje în folosirea acestui tip de software development.

Un exemplu constă în refolosirea eforturilor precedente. Modelul conceptual poate fi specific domeniului, dar soluția poate fi inspirată și din alte proiecte, sau la rândul ei, poate să fie sursa de inspirație pentru alte proiecte. Aceasta duce la refolosirea soluțiilor prin transformarea modelului într-un alt model conceptual specific unui alt domeniu. Această abordare este susținută de către OMG și reflectă unul din cele patru principii de la MDA[1].

Acestea sunt piesele pe care se creează aplicații Model Driven. Pentru a ilustra cum funcționează, vom descrie o Problemă și o potențială soluție dezvoltată pe modele.

Problemă

Presupunem următorul scenariu dintr-un domeniu tehnic: Clientul nostru folosește ca Interfață grafică o versiune particularizată a aplicației Eclipse Rich Client Platform (Eclipse RCP). În acestă versiune, denumită "myRCP", el dorește să ruleze o serie de aplicații, cu diferite scopuri.

Noua noastră aplicație trebuie să ruleze în această versiune particularizată de RCP ca o perspectivă nouă.

Tranzacțiile de business sunt realizate de către un Application server.

Pentru a oferi un framework comun între toate aceste aplicații, clientul myRCP a definit o structură de date care poate să asigure orice fel de necesitate. Această structură de date extinde EObject din Eclipse RCP. Exemplu. - toate obiectele extind MyRCPObject.

Modelul domeniului: Aplicația va rula într-un soft particularizat. Acest soft conține un set propriu de contracte (interfețe) pentru toate Obiectele și oferă un set de instrucțiuni particularizate pentru afișarea elementelor vizuale. Acest software este în continuă schimbare și aplicația noastră trebuie să se schimbe odată cu ea.

Vom separa funcționalitățile de business (manipularea obiectelor) de funcționalitățile de afișare. Prin aceasta vom crea două componente: componenta RCP și componenta de business. Componenta RCP va conține orice topic legat de elementele vizuale, managementul acțiuniilor și orice altă interacțiune cu utilizatorul, în timp ce componenta de business se va ocupa de toate topicurile legate de managementul acțiunilor și funcțiilor de business.

Aceste două componente vor comunica prin contractul lor comun - obiectul MyRCPObject.

Modelul Conceptual: fiecare din cele două componente va primi propriul model conceptual (unul sau mai multe, în funcție de nevoie). Acest model se va ocupa de toate topic-urile din domeniul tehnic cât și de domeniul de business al aplicației. În acest fel, modelul nostru poate oferii o perspectivă atât tehnică și funcțională.

Motivație

Componenta RCP este dezvoltată într-un framework personalizat - myRCP. Acest framework definește cum sunt afișate elementele grafice în RCP, împreună cu acținile dintre aceste componente.

Acest lucru ridică unele probleme legate de ciclul de implementare. Orice developer va trebui să învețe acest framework personalizat și (probabil) framework-ul RCP. Pentru a evita acest impediment, vom modela toate elementele din interfața cu utilizatorul.

Descrierea modelului conceptual se va face folosind un Limbaj de Modelare Specific Domeniului (LMSD). Prin acest limbaj utilizatorul va descrie componentele vizuale și comportamentul așteptat. Elementele vor fi conectate cu Obiectele de Business și comportamentele cu Servicii de business. Acest un Limbaj de Modelare Specific Domeniului va fi numit ("GuiDMSL").

Schimbul de date dintre Application Server și RCP este realizat prin DTO (obiecte de transfer de date). Aceste DTO-uri vor respecta contractul MyRCPObject (așa cum este cerut de către frameworkul myRCP) și va conține datele din Obiectele de business.

Pentru a reduce sarcina de implementare, DTO-urile, Interfețele serviciilor de business, obiectele de business și relațiile dintre acestea vor fi generate folosind un Limbaj de Modelare Specific Domeniului ) - "BusinessDSML".

Interfețele serviciilor de business (comune între RCP și Application Server) vor fi generate, dar funcționalitatea de business va fi scrisă manual.

Ca un rezultat direct, cele două un Limbaje de Modelare Specific Domeniului - GuiDSML și BusinessDSML vor descrie toate modelele aplicației. Aceste modele vor oferi o perspectivă actuală și precisă asupra aplicației.

Descrierea modelelor folosind Xtext

Xtext este un framework folosit în dezvoltarea limbajelor de programare și limbajelor specifice domeniilor. Acesta acoperă toate aspectele ce țin de infrastructura unui limbaj: parsere, interpretatoare și compilatoare; de asemenea oferă o integrare completă în Eclipse-IDE. Aduce și o serie de șabloane pentru toate aceste aspecte care în același timp pot fi ușor adaptate la nevoile individuale. [4]

Xtext oferă un mod simplu de proiectare a unui limbaj specific domeniului. După ce arhitectul descrie gramatica folosită de către limbajul specific domeniului, xtext va genera un parser. Acest parser va fi folosit în implementarea descrierii Modelului Conceptual. Programatorul va descrie modelul conceptual în fișierele DSML, folosindu-se de parser-ul generat, concentrându-se numai asupra ceea ce este esențial pentru businessul soluției și nu asupra implementării.

Xtext oferă suport Eclipse și o serie de instrumente folosite în dezvoltarea gramaticilor și a modelelor precum: asistență de conținut, validare și quick-fix, integrare avansată Java, integrare cu alte instrumente Eclipse, etc. .

Folosind parser-ul în definirea modelelor, asigurăm respectarea celor patru principii ale MDA. Exemplu [1]:

  1. Modelul este descris într-o notație bine definită;

  2. Sistemul este organizat în jurul unui set de modele care acceptă transformări;

  3. Existența unui meta-model : gramatica Xtext;

  4. Xtext este un framework open source.

Modelul conceptual pentru componenta RCP - GuiDSML

În acest model conceptual, programatorul va descrie o reprezentare abstractă a componentelor vizuale și a comportamentului așteptat. Aceasta se realizează prin împărțirea perspectivei în editoare și view-uri. Aceste editoare vor conține sub-editoare și/sau elemente de control grafice.

Să luăm următorul exemplu din LDAP Studio (C):

https://directory.apache.org/studio/users-guide/ldap_browser/tools_ldap_perspective.html

Zona principală a aplicației este perspectiva - 1. Fiecare perspectivă conține cel puțin un editor și poate conține și view-uri. Fiecare editor conține sub-editoare, paragrafe și/sau elemente de control grafice. Fiecare paragraf conține diferite elemente de control grafice.

Modelul trebuie să fie cababil să descrie toate aceste elemente și interacțiunea dintre ele. Cu Xtext noi vom descrie componentele și obiectele de business cu care lucrează.

Să luăm următorul exemplu GuiDSML - Entry editor - 2:

{"Descriere pentru o posibilă transformare."}
editor EntryEditor opensIn MainEditor {
    title Titles.EntryEditor
    behavior EntryEditorBehaviours
    businessObject EntryDTO

    paragraphs{
        submenu DN …
        table EntryDescriptionTable
    }
}

{" Descriere pentru o posibilă transformare."}
Table EntryDescriptionTable {
     Title Titles.EntryDescriptionTable
     businessObject EntryDTO.descriptionDTO
     columns {
       column AttributeDescription {
       value descriptionDTO.attributeDescription
       }
       column Value {
       value descriptionDTO.value
       }

       }
}

Acesta este o descriere a unui element de control grafic și obiectul de business din spatele lui. Interacțiunea dintre componente este descrisă cu ajutorul unui element behavior, unde funcționalitatea businessului va fi dezvoltată.

Behavior EntryEditorBehaviours {
    businessObject EntryDTO
    Load 
    Save
    customAction changeColorField
    customServerAction EntryService.deleteField(descriptionDTO.attributeDescription)
}

Modelul conceptual descrie comportamentul. Operațiile de Load și Save sunt comportamente standard și codul generat va conține o implementare standard. Această implementare este comună tuturor obiectelor de business, iar identificarea obiectelor se face prin DTOs.

Cuvântul customAction descrie o acțiune particulară RCP. Aici modelul conceptual prezintă un comportament, dar lasă sarcina implementării programatorului. Codul sursă final va fi generat parțial și programatorul va primi o definiție de metodă unde el trebuie să decidă particularitățile implementării.

Practic, modelul oferă o serie de comportamente comune, iar dacă acestea nu sunt suficiente, lasă la latitudinea programatorului să definească noi acțiuni particularizate.

Operația de deleteField este un apel la componenta de business, care oferă o anumită funcționalitate. Pentru a folosi această funcționalitate, programatorul va lega acțiunea la un buton specific. Apelul va fi făcut către server, iar rezultatul acțiunii va fi vizibil într-o zonă specifică.

{"Description for possible transformation."}
Table EntryDescriptionTable {
   . . .
   columns {
   . . .
   }
   button buttonName action EntryService. 
      deleteField(descriptionDTO.attribute)
}

Utilizatorul va putea să particularizeze funcționalitatea, folosind un cuvânt cheie custom la sfârșitul descrierii unui buton.

Modelul conceptual pentru componenta de Business - BusinessDSML

Acest model conceptual trebuie să descrie toate obiectele de business (cum ar fi Entry și Description) și serviciile de business, cum ar fi deleteField(descriptionsDTO. attributeDescription).

Obiecte de Business:

{"Description for possible transformation."}
entity Entry {
    description : listof DescriptionEntity;
}

{"Description for possible transformation."}
entity DescriptionEntity {
    attributeDescription : String;
    value : String;
}

{"Description for possible transformation."}
dto EntryDTO link Entry {
    link descriptionDTO : listof DescriptionDTO;
}

Servicii de Busines:

service EntryService {
    {"Description for possible transformation."}
    operation deleteField (
        {"Information anout inout."}
           attributeDescription: String
    ) :  void;
}

Meta-modelul

Acum că am definit limbajul de modelare specific domeniului, următorul pas constă în definirea meta-modelului și framework-ului de generare de cod.

La baza acestor descrieri de model (DSML) se află un set de meta-modele. "Capacitatea de a analiza, automatiza și transforma modelele necesită un mod clar și lipsit de ambiguități pentru a descrie semantica modelului. Prin urmare, modelele intrinseci trebuie să fie descrise într-un model, pe care îl numim meta-model." [1]

Meta-modelele noastre (unul pentru Gui și unul pentru Business) vor descrie gramatica (semantica) folosită în construirea modelelor. Astfel, de fiecare dată când un programator descrie un obiect de business, un serviciu, orice element specific limbajului de modelare specific domeniului, rezultatul (modelul) este analizat și compilat pentru a evita potențiale probleme.

Un exemplu dintr-un editor in GuiDSML:

Editor EntryEditor opensIn MainEditor {
    Title Titles.EntryEditor
    Behavior EntryEditorBehaviours
    businessObject EntryDTO

    paragraphs{
        submenu DN …
        table EntryDescriptionTable
    }
}

Editorul descris în gramatica meta-modelului

Editor :
   'editor'name=GUI_ID'opensIn
    'EditorComponent=EDITOR_ID'{'
    'title' title=[Titles::TitleElement]
    ('behavior'service=[dm::BusinessService])?
    ('readOnly'service=[dm::ReadOnly])?
    'businessObject 'object=[dm::BusinessObject]
    'paragraphs''{' (paragraph+=Paragraph)+ '}'
    '}';

În Xtext noi descriem gramatica specifică tuturor zonelor de interes din modelul domeniului (exemplu: editorul), implicit toate zonele de interes din modelul conceptual. Din exemplul anterior putem deduce faptul că un 'editor' trebuie să conțină un name și un EditorComponent. După ce acolada este deschisă, Xtext așteaptă un 'title'. Elementele behavior și readOnly sunt marcate ca fiind opționale, semnul parantezei.

Folosind gramatica rezultat, xtext generează un parser - metamodelul aplicației. Acesta verifică dacă modelele GuiDSML au fost corect construite, comparându-l cu gramatica descrisă.

Un meta-model poate fi folosit pentru toate modelele descrise în componenta RCP, și un meta-model poate fi folosit pentru toate modelele din componenta Business.

Acest plugin va oferi toate instrumentele necesare pentru descrierea unui model în GuiDSML și BusinessDSML. După ce programatorul termină descrierea conceptuală a modelului (GuiDSML și BusinessDSML) un instrument de generare va crea codul final.

Framework-ul de generare de cod

Până în acest punct, toate deciziile au fost independente de platforma de dezvoltare. Aici modelarea ajunge la capăt și codul rezultat este produs.

În acest exemplu, noi folosim unul dintre instrumentele de generare oferite de către Eclipse Modeling Framework - Xpand. Acesta este un limbaj static care generează cod pe baza unor template-uri definite. Vom folosi acest instrument deoarece oferă un set de template-uri care ajută la generarea Obiectelor RCP.

Exemplul unui editor:

«DEFINE editorTemplate FOR Editor-»
  «EXPAND DefaultEditor(editorTemplate.name)-»
  «EXPAND editorTemplate_Vars(editorTemplate.name)-»
  «EXPAND 
     editorTemplate_Components_BusinessObject 
     (editorTemplate.businessObject)-»
  «EXPAND editorTemplate_Components_Behaviour 
     (editorTemplate)-»
«ENDDEFINE»

«DEFINE editorTemplate_Vars(String name) 
   FOR editorTemplate -»
    «IF 'readOnly' == true-»
    private booleanreadOnly = true;
    «ENDIF-»
    private String editorName = « name »;
«ENDDEFINE»

«DEFINE DefaultEditor(String name)-»
Import staticorg.junit.Assert.*;

Import java.io.IOException;
Import java.util.HashMap;
Import java.util.Map;
Import java.util.Set;
…
public static class « name » {
…
«ENDDEFINE»

Codul rezultat care reprezintă editorul este generat în ordinea specificată de către elementele DEFINE/ EXPAND. Spre exemplu, definiția clasei generate:

Import staticorg.junit.Assert.*;

Import java.io.IOException;
Import java.util.HashMap;
Import java.util.Map;
Import java.util.Set;
…
public static class EntryEditor {
private String editorName = EntryEditor;
// template components
}

După ce procesul de generare este terminat, clasele generate sunt împachetate în fișiere jar și trimise către proiectele care le folosesc. Clasele generate parțial sunt generate o singură dată - o nouă generare a întregului model nu va rescrie clasa deja implementată. Aceste clase sunt parțial scrise de mână, procesul de generare a codului sursă nu trebuie să suprascrie codul adăugat manual.

Xpand este o soluție bună pentru generarea obiectelor RCP, dar pentru o abordare mai generală, recomand folosirea limbajului Xtend. Este mai flexibil și mai ușor de citit/scris.

În practică, fiecare element al unui model conceptual este analizat în detaliu. După un studiu atent și aprofundat al domeniului modelului, modelul conceptual este descris (la un nivel abstract), și, apoi începe crearea de meta-modele. După ce meta-modelul este terminat, acesta va fi transmis dezvoltatorilor pentru utilizare. Din acest punct înainte, meta-modelul va suferi schimbări dacă este necesar și în funcție de modificarea domeniului problemei.

Acest articol este doar o prezentare generală a unei aplicații proiectate folosind dezvoltare software model-driven. Dacă fiecare domeniu problemă este diferit, atunci fiecare model conceptual va fi diferit. Pentru mai multe informații recomand citirea articolelor din zona de referință și să încercați unele dintre instrumente folosite în MDD [8].

Referințe

[1] An introduction to Model-Driven Architecture (MDA) - Alan W. Brown, Jim Conallen

[2] Model-Driven Software Development, (Technology, Engineering, Management)- Thomas Stahl, Markus Volter

[3] Towards the Automatic derivation of Malaca Agents using MDE - Inmaculada Ayala, Nercedes Amor and Lidia Fuentes - E.T.S.I. Informatica, Universidad de Malaga

[4] Xtext

[5] http://www.omg.org/mda/mda\_files/Model-Driven\_Architecture.pdf

[6] http://ftp.icm.edu.pl/packages/ace/ACE/PDF/GEI.pdf

[7] https://eclipse.org/community/images/apacheldap.png

[8] mdwhatever.free.fr/index.php/2010/06/model-driven-tools-the-big-list/

LANSAREA NUMĂRULUI 87

Prezentări articole și
Panel: Project management

Joi, 19 Septembrie, ora 18:00
Hugo (The Office), Cluj-Napoca

Înregistrează-te

Facebook Meetup

Conferință

Sponsori

  • ntt data
  • 3PillarGlobal
  • Betfair
  • Telenav
  • Accenture
  • Siemens
  • Bosch
  • FlowTraders
  • MHP
  • Connatix
  • UIPatj
  • MetroSystems
  • Globant
  • Colors in projects