1.1 Motivareaalegeriitemei . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2 2 Tehnologii folosite 5 2.1 Java [617100]

i
Cuprins
1 Introducere 1
1.1 Motivareaalegeriitemei . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2
2 Tehnologii folosite 5
2.1 Java . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
2.1.1 JavaEE . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6
2.1.2 EJB . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6
2.1.3 AutentificareaEJB . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7
2.1.4 JPA . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8
2.2 Wildfly . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8
2.3 PostgreSQL . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9
2.4 Hibernate . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
2.5 Wicket . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
2.6 Bootstrap . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
2.7 SVG.js . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
2.8 Gradle . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
2.9 Git. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
3 Prezentarea proiectului 15
3.1 Configurareaspațiuluidelucru . . . . . . . . . . . . . . . . . . . . . . . . . . 15
3.2 Autentificareșiautorizare . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20
3.3 Structurabazeidedate . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21
3.4 Structurapaginilor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 23
3.5 Generareaplanului2Dalmeselor . . . . . . . . . . . . . . . . . . . . . . . . 23
3.6 Descriereapaginilor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29
3.6.1 Paginapentrucreareaunuicont . . . . . . . . . . . . . . . . . . . . . 29
3.6.2 Paginadelogin . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30
3.6.3 Paginapentrucreareauneicompanii . . . . . . . . . . . . . . . . . . . 31
3.6.4 Paginapentrucreareaunuirestaurant . . . . . . . . . . . . . . . . . . 32
3.6.5 Paginaangajaților . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33

ii
3.6.6 Paginarolurilor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
3.6.7 Paginapentruconfigurațiasălilor . . . . . . . . . . . . . . . . . . . . 34
3.6.8 Paginaevenimentelor . . . . . . . . . . . . . . . . . . . . . . . . . . . 35
3.6.9 Paginacuistoriculmodificărilor . . . . . . . . . . . . . . . . . . . . . 35
3.6.10 Paginaaranjareinvitați . . . . . . . . . . . . . . . . . . . . . . . . . . 38
3.6.11 Paginaculistainvitațilorpentruuneveniment . . . . . . . . . . . . . . 39
3.6.12 Paginiledeprofil . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39
3.7 Testareaaplicațieicuunevenimentreal . . . . . . . . . . . . . . . . . . . . . 41
4 Concluzii 45
Bibliografie 47
Listă de abrevieri 49
Listă de figuri 51

1
1 Introducere
Lucrarea de față are ca și scop prezentarea unei platforme online care va facilita aranjarea in-
vitațilorlameseîncadrulevenimentelorprecumnunți,majorate,conferințesauoricealtfelde
eveniment. Aranjarea la mese se face prin vizualizarea planului 2D al meselor și prin metoda
dedrag-and-dropalnumelorinvitațilorlamese.
În primul rând, aplicația este destinată restaurantelor sau organizatorilor de evenimente.
Aceștia vor putea sa iși creeze un plan al meselor în sala în care va avea evenimentul. Atât
restaurantele, cât și organizatorii de evenimente vor avea posibilitatea de a crea evenimente
pentru anumiți clienți sau chiar evenimente proprii. În cadrul acestor evenimente, clienții vor
aveaposibilitateasăîșiaranjezeapoiinvitațiilamese. Listelecuaranjareainvitațilorlamesevor
puteafidescărcateînformatPDFatâtdecătreclient,câtsidecătregazdaevenimentului. For-
matulpoatefi,înfuncțiedepreferințe,listareaalfabeticăainvitaților,saulistareacartonașelor
caresevorpunepefiecaremasă,cuinvitațiirepartizațilaaceamasă.
În al doilea rând, aplicația este destinată, în mod evident, utilizatorului final, adică acelor
persoane care organizează un eveniment și doresc o metodă ușoară și rapidă prin care își pot
aranja invitații la mese. În mod inițial, aplicația poate fi folosită de toți cetățenii români sau
vorbitoridelimbaromânădeoareceinterfațaaplicațieiesterealizatăînlimbaromână,însă,din
fericire, tehnologiile de internaționalizare introduse încă de la început în aplicație fac foarte
ușoarășirapidăposibilitateaportăriiaplicațieiîntr-olimbădecirculațieinternațională.
Îndezvoltareaacesteiaplicațiiamfolositanumitetehnologiicarefaccadezvoltareaaplica-
țiilor să fie mai rapidă și rezolvă probleme generale întampinate în majoritatea aplicațiilor sau
introducuneltecarefaciliteazăimplementareașidezvoltareaeficientăaaplicațiilor. Dintreteh-
nologiile folosite le voi menționa pe cele mai importante. Cum este vorba de o aplicație web,
vom avea nevoie de un server în primul rând, pe care se va stoca partea de backend și baza
de date, și, în al doilea rând, vom avea nevoie de partea de frontend, adică interfața aplicației.
Limbajul de programare ales pe partea de server este Java, mai exact Java Enterprise Edition.
Ca și server am ales să folosesc Wildfly, un server open source dezvoltat și menținut de către
compania RedHat, dar care are si o versiune enterprise plătită. Pentru persistența datelor în
bazadedateamfolositPostgreSQL,avândtotolicențădetipopensource. Pentrucomunica-
rea dintre aplicație și baza de date, adică pentru conversia Java – SQL, SQL – Java, am folosit
librăria Hibernate. Interfața aplicației constă în definitiv din cod HTML, CSS și Javascript, la

2 Capitolul 1. Introducere
fel ca la oricare altă pagină web, insă am folosit și aici anumite unelte care ușurează munca
programatorului. De menționat este librăria Wicket, dezvoltată de către Apache Foundation,
fiindșiaceastatotolibrărieopensource. WicketesteolibrăriescrisăînJavașifolositătotde
către aplicații Java, care generează cod HTML și injectează datele din Java în HTML în mod
transparentfațădedezvoltatori. DemenționatpeparteadefrontendarmaifiSVG.js,olibrărie
Javascript pe care am folosit-o la generarea imaginii SVG a configurației meselor, și librăria
Bootstrap folosită pentru a crea pagini web care se scalează vizual automat pentru telefoanele
mobileinteligente. Oaltăunealtăfolosită,carenuafecteazădirectcodulsursăalprogramului,
însăcarecredcăartrebuimenționată,esteGradle. Aceastaesteounealtădeautomatizareopen
sourcescrisăinlimbajulGroovy. Înaplicațiameaamfolosit-olagestionareadependințelorși
exportarea aplicației într-o arhivă WAR. Aș mai dori să adaug la această listă și unealta Git.
Aceastaestedeobiceifolositălacontrolulversiuniifișierelorsursăcândselucreazăînechipă,
însăîncazulmeufiinddoaropersoanăcaremodificăfișierelesursă,l-amfolositpentruaavea
unbackup alaplicației încazul încare sepierd datelede pecalculator, cât șipentru aavea un
istoricalmodificărilor.
1.1Motivareaalegeriitemei
Temaproiectuluimeuestedenumită“Websitedinamicpentruaranjareapersoanelorlameseîn
cadrulevenimentelor”și,dupăcumsepoatevedeașidintitlu,proiectulconstădintr-oplatformă
prin care utilizatorii își pot aranja invitații unui anumit eveniment la mesele disponibile din
sală. Am denumit acest proiect o platfomă online și nu doar un website, deoarece arhitectura
proiectuluiestecreatăînașafelîncâtinformațiilefurnizatepefiecarepaginăsuntdinamiceîn
funcție de utilizatorul autentificat. Tot în funcție de utilizator sunt stabilite și permisiunile de
acceslafiecarepagină,darvomvorbidespreacestlucruîncapitoleleurmătoare.
Osaîncepprinavăexplicadeundeaapărutideeadeadezvoltaaceastăplatformăonline.
Casăvăexplicdeundeaapărutaceastăidee,osăîncepîntr-unmodromantic,adicăcuonuntă.
Șinumăreferaicilanuntamea,cimaiexactlanuntafrateluimeu. Știmcutoțiicăorganizarea
uneinunținuesteunlucruatâtdesimplu,cipresupunemultăorganizaresiaranjamentefăcute
pentruaieșitotulperfect. Desigurcămiriisevorocupademultedintrelucrurilecarețindenunta
lor, însă totuși acesta este un eveniment unic in viață, și, din punctul meu de vedere, ar trebui
ca lucrurile care pot fi rezolvate și de alte persoane, să nu ocupe din timpul mirilor, deoarece
eiartrebuisăsebucuredeaceastăperioadădinviațalor. Așadarsărevenimlaacestexemplu
concret. La momentul respectiv încercam să ii ajut și eu pe cât posibil cu organizarea nunții.
Am primit deci sarcina de a mă ocupa, pe lânga altele, de organizarea meselor, a persoanelor

1.1. Motivarea alegerii temei 3
lameseșideprimireainvitațilorșiconducerealorlameseînziuanunții. Problemeleauapărut
din prisma faptului că numărul de invitați se ridica undeva în jur la 400 de persoane. Prima
problemă ar fi aranjarea fiecărui invitat la masă. În zona noastră, cel puțin, aranjarea la mese
sefacedecelemaimulteoridecătremiri,încazuluneinunți,saudecătresărbatorit,încazul
unui majorat. Prima și cea mai simplă opțiune este să faci un aranjament în Excel, care poate
fi apoi printat, însă pentru 400 de persoane acest lucru este puțin cam dificil, deoarece trebuie
săaiînminteșistructurameselorșinumăruldelocurilafiecaremasăcândfaciaranjamentele.
În plus, în cazul în care dorești să faci o modificare ulterioară, trebuie să ai grijă să nu încurci
locuriledejarepartizate. Pentruarezolvaaceastăproblemăcuaranjareainvitațiloramcăutatun
softwarespecializatpentruacestlucru. Printr-osimplăcăutarepeinternetamreușitsăaflucănu
existăunastfeldesoftwaredezvoltatînlimbaromână,așacăatrebuitsăcumpărolicențăpentru
unsoftwareextern. Adouaproblemăarfiprimireainvitaților. Încazullistelorprintate, poate
dura câteva zeci de secunde sau chiar minute până găsești numele unui invitat printre sute de
persoane,ceeaceecamincomoddacăsuntcâtevazecidepersoanecaremaiașteaptălacoadă,
așacăatunciamimprovizatoaplicațiemobilăAndroidcuposibilitatedesearchpentrunumele
sau prenumele unei persoane, sau căutare după numărul mesei. Proiectul curent urmărește să
rezolve aceste probleme printr-o interfață cât mai simplă, astfel încât orice persoană să poată
folosiaplicația,chiardacănuarecunoștințeavansateînutilizareacomputerelor.

5
2 Tehnologii folosite
2.1Java
Javaesteunlimbajdeprogramaredenivelînaltconcurent,orientatpeobiecte,proiectatdecătre
James Gosling. Scopul acestui limbaj a fost compilarea o singură dată a codului sursă și apoi
rulareape orice dispozitiv. Java este derivat dinlimbajul C si C++, însă oferă maipuține fun-
cționalitățidenivelscăzutdecâtacesteadouă. [ 4][13]LimbajulJavaafostcreatcuurmătoarele
scopuriînminte: [ 13]
1.Trebuiesăfiesimplu,orientatpeobiecteșifamiliar.
2.Trebuiesăfierobustșisecurizat.
3.Trebuiesăfieneutrudinpunctdevederearhitecturalșiportabil.
4.Trebuiesăaibăoperformanțăridicată.
5.Trebuiesăfieinterpretat,cufiredeexecuțieșidinamic.
Așaaratăexemplulclasic“HelloWorld”implementatînJava:
classHelloWorld{
public static void main(String[] args) {
System.out. println (”Hello World!”);
}
}
Primadatădeclarămoclasănumită“HelloWorld”cuajutorulcuvântuluicheieclass. Orice
cod scris în Java trebuie să facă parte dintr-o clasă. Apoi declarăm o metodă care aparține
acestei clase, numită main. Cuvântul “main” este un cuvânt rezervat în Java și este folosit la
denumireametodeiprincipaleaprogramului. Ometodădenumită“main”trebuiesăfiepublică
și statică și trebuie să aibă ca și parametrii un tablou de tipul String, denumit prin convenție
“args”, care va conține parametrii trimiși din consolă la rularea aplicației. Variabila “args” se
maipoateinițializaînJavașisubforma“String…”. Metoda“main”reprezintăpunctuldeintrare
al aplicației, de aici se va începe execuția codului. Pe următoarea linie observăm invocarea
metodei“System.out.println”carevaprintaînconsolaimplicitătextulpecareîltrimitemcași
parametru,adicăîncazulnostru“HelloWorld!”.

6 Capitolul 2. Tehnologii folosite
2.1.1JavaEE
JavaEE este o extensie a limbajului Java care conține funcționalități în plus, cum ar fi rularea
programelordistribuitesauserviciiweb. AplicațiileJavaEErulatepotfimicroserviciisauchiar
servere de aplicații, care gestionează tranzacții, asigură securitate, scalabilitate, concurență și
managementul componentelor pe care le execută. JavaEE este folosit în: comerț electronic,
contabilitate,sistemeinformaționalebancare. [ 12]JavaEEareanumitecomponenteînplusfață
deJava,caresuntnecesareîndezvoltareaaplicațiilorweb. Îndezvoltareaproprieiaplicațiiam
folositacestecomponentedisponibileînJavaEEșianumeEnterpriseJavaBeansînimplementa-
reaserverului,autentificareagestionatădecontainerșiJPA,desprecarevoivorbiîncontinuare.
2.1.2EJB
Denumirea EJB provine de la prescurtarea în engleză de la Enterprise Java Beans care face
partedinJavaEEșiconstăîntr-oarhitecturăcreatăpentruadezvoltaaplicațiirobuste,scalabile
șiperformante. OaplicațieEJBpoatefilansatăpeoriceservercareimplementeazăspecificațiile
standardJavaEE.[ 6]
EJBesteîmpărțitîntreicategoriișianume: [ 6]
1.Session Bean. Session Bean este o componentă care stochează date pentru un anumit
utilizatorpentruosingurăsesiune. Aceastăcomponentăpoatefistatefulsaustateless. O
componentăstatefulîșipăstreazăstareaconversaționalacuclientul,pecândocomponentă
statelessestefolosităpentruoperațiuniindependente. [ 17][18]ComponentaSessionBean
nu utilizează așa multe resurse ca și componentele Entity Bean. O componentă Session
Beanestedistrusăatuncicândsesiuneautilizatoruluisetermină.
2.Entity Bean. O componentă Entity Bean reprezintă stocare de date persistentă. Datele
utilizatorilorpotfisalvateîntr-obazădedatecuajutorulacesteicomponenteșipotapoi
săfierecuperatedinbazadedate.
3.MessageDrivenBean. Dupăcumîispuneșinumele,ocomponentăMessageDrivenBean
este folosită la trimiterea mesajelor. În aplicația curentă nu am avut nevoie să folosesc
aceastăcomponentă.
PrintrebeneficiilefolosiriiarhitecturiiEJBînimplementareaaplicațiilorsenumără: [ 6]
•Simplificareadezvoltăriiînaplicațiiledescarălargă.

2.1. Java 7
•ServeruldeaplicațieEJBoferăserviciilaniveldesistemcumarfimanagementultranzac-
țiilor, înregistrarea erorilor, echilibrarea încărcării serverului, mecanisme de persistență
a datelor și multe altele. Dezvoltatorii trebuie să se concentreze doar pe implementarea
propriuzisăaaplicației.
•Containerul EJB se ocupă cu crearea și distrugerea instanțelor EJB, astfel dezvoltatorul
nutrebuiesăîșifacăproblemecudistrugereaobiectelordupăcenumaiarenevoiedeele.
2.1.3AutentificareaEJB
ÎnaintesăvorbescdespreautentificareaEJB,așdorisăclarificcățivatermenipecareîivoifolosi
referitorlaautentificareșilasecuritateadatelor,șianume:
•Autentificareaesteprocesulprincareseverificăfaptulcăutilizatorulcareacceseazăapli-
cațiaesteautentic.
•Autorizareaesteprocesulprincareseverificădacautilizatorulautentificataredrepturide
acceslaoanumităresursăsauinformație.
•Utilizatorulesteaceapersoanăcareacceseazăaplicația.
•Ungrupdeutilizatorireprezintănișteutilizatoricarefacpartedintr-ungrupcareareacces
laanumiteresurse,deexemplugrupuldeadministratoriaisistemului.
•Rolurile utilizatorilor reprezintă permisiunea pe care o are un utilizator de a accesa o
resursă.
Containerul EJB oferă anumite unelte pentru securizarea componentelor EJB, care includ
atâtautentificareacâtșiautorizareautilizatorilor. ComponenteleEJBaudouămetodeprincare
potfisecurizateșianume:
1.Securitatedeclarativă. Estedepreferatsăfiefolosităaceastămetodădesecuritate. Această
metodăexprimăcerințeledesecuritatealeuneicomponenteprinfolosireaanotațiilor. Pre-
zențauneianotațiipentruometodădintr-oclasăEJBestetotceeaceestenecesarpentru
protecția acelei metode și, în unele cazuri, pentru autentificare. Totprin această metodă
declarativă dezvoltatorul poate crea roluri pentru utilizatori care le vor da drepturile de
acces la resursele serverului. Când se accesează o metodă protejată cu o anotație de se-
curitate, sistemul va cere automat autentificarea utilizatorului. Acestuia i se va cere un
nume și o parolă care vor fi comparate cu datele dintr-o bază de date. Dacă utilizatorul

8 Capitolul 2. Tehnologii folosite
estegăsitșiparolaestevalidă,rolurilepecareleareutilizatorulvorficomparatecurolu-
rile necesare accesării acelei metode securizate. Dacă utilizatorul este autentificat și are
rolurilenecesarepentruaaccesametoda,informațiilevorfireturnateutilizatorului. [ 20]
2.Securitateprogramatică. Prinaceastămetodădesecuritateseadaugăcodîninteriorulunei
metodecarevaaccesaidentitateautilizatoruluicaredoreștesăaccesezeinformațiileșiva
folosi această identitate pentru a lua decizii de securitate. Această metodă de securitate
este folositoare atunci când metoda declarativă nu poate fi folosită pentru a implementa
modelulspecificdesecuritateaaplicațieirespective.Îngeneral,managementulsecurității
artrebuisăfieimplementatînașafelîncâtsăfietransparentpentrumetodeleaplicației.
[20]
2.1.4JPA
JPA este o interfață care specifică managementul datelor relaționale în aplicații JavaEE. JPA
foloseșteentitățipentruaspecificadatelepersistente. OentitatepersistentăesteoclasăJavaa
căreistareestesalvatăîntr-obazădedaterelațională. Instanțedinacesteentitățicorespundrân-
durilorindividualedintabele. Entitățileaudeobiceirelațiicualteentități,caresuntreprezentate
prinmetadate. Acesteentitățișirelațiimetadatapotfispecificatelaniveldeclasăprinfolosirea
anotațiilor sau într-un fișier separat XML denumit descriptor care este distribuit cu aplicația.
TotodatăJPAdefineșteșiunlimbajdeinterogarespecificdenumitJavaPersistenceQueryLan-
guagesau,pescurt,JPQL.JPQLesteunlimbajdeinterogareindependentdeplatformă,orientat
peobiecte. JPQLestefolositlainterogareaentitățilorstocateînbazadedate. Interogărilesunt
asemănătoare cu SQL ca și sintaxă, dar operează cu obiectele entități, și nu direct cu tabelele
dinbazadedate. [ 10][11]
2.2Wildfly
Ca și server în implementarea aplicației am ales să folosesc Wildfly deoarece, în primul rând,
esteunserveropensource,iarînaldoilearândammailucratcuacestserverșisuntfamiliarcu
uneltelepecareleoferășiconfigurațiilenecesare.
Wildfly a fost cunoscut în trecut ca și JBoss, el fiind un server de aplicație dezvoltat de
companiaRedHat. WildflyestescrisînJavașiimplementeazăspecificațiileJavaEE.Poaterula
pemaimultesistemedeoperare. Esteunservergratuit,open-source,cuolicențădetipLGPL.
[21]

2.3. PostgreSQL 9
Tabela2.1: ComparațieîntrediferiteserveredeaplicațiipentruJava. [ 14]
Server Companie Ediție Ultima lansare Compatibilitate JavaEE Servlet JSP HTTP/2 Licență
GlassFish GlassFishCommunity 5.0.0 2017-09-21 8complet 3.1 2.3 NU GratuitCDDL,GPL
Jetty EclipseFoundation 9.3.3 2015-08-27 7parțial 3.1 2.3 DA GratuitApache2.0,EPL
Tomcat ApacheSoftwareFoundation 9.0.8 2018-05-03 8parțial 4.0 2.3 DA GratuitApachev2
Wildfly RedHat 12.0.0.Final 2018-02-28 7complet,8previzualizare 4.0 2.3 DA GratuitLGPL
2.3PostgreSQL
PostgreSQL sau Postgres este o bază de date obiect-relațională care pune accent pe extensibi-
litate și conformitatea cu standarde. Fiind un server de baze de date, principalele funcții ale
acestuiasuntaceleadeastocadateînmodsecurizatșisăreturnezedatelerespectivecașirăs-
puns la cererile altor aplicații software. Poate să susțină o capacitate de lucru de la aplicații
simplecareruleazăpeunsingurcomputer,pânălaaplicațiiwebcumulțiutilizatoriconcurenți.
Pe sistemul de operare macOS Server PostgreSQL este baza de date implicită. Totodată este
disponibilășipentrusistemeledeoperareMicrosoftWindowssauLinux. PostgreSQLsuportă
declanșatoare(triggers), chei străine, funcții și proceduri stocate, și alte extensii. Din punct de
vedere legal este dezvoltat de PostgreSQL Global Development Group și are o licență de tip
open-sourcegratuită. [ 16]
PostgreSQL se conformează standardului ACID și este tranzacțională. Standardul ACID
provine de la inițialele în engleză Atomicity, Consistency, Isolation, Durability, și reprezintă
faptul că tranzacțiile unei baze de date trebuie să garanteze valididatea chiar și în cazul unor
fenomene precum erori de sistem, căderi de tensiune sau alte erori care duc la incapacitarea
sistemului. [ 16][1]
PostgreSQLareinclusreplicarebinarăbazatăpetrimitereamodificărilorlanodurilerepli-
cate în mod asincron, cu posibilitatea de a executa interogări read-only asupra acestor noduri
replicate. Acestlucrupermiteîmpărțireatraficuluicaredoarciteștedatelelamaimultenoduri.
Aplicațiile mai vechi care permiteau acest tip de scalabilitate se bazau pe adăugarea declanșa-
toarelor(triggers)penodulprincipal,încărcând-ulînacestfelcumaimulteoperațiunideproce-
sare. PostgreSQLincludeșireplicaresincronăcareasigurăfaptulcă, pentrufiecaretranzacție
de scriere, nodul principal așteaptă până cel puțin o replică a înregistrat datele. Poate exista o
combinație de servere asincrone și sincrone în așteptare. Replicare sincronă multi-master nu
esteinclusălamomentulcurentînnucleulPostgreSQL.[ 16]
PostgreSQL oferă suport nativ pentru indexare. Indexarea în Postgres are următoarele ca-
racteristici: [ 16]

10 Capitolul 2. Tehnologii folosite
•Indecșiexpresiepotficreațicuunindexalunuirezultatauneiexpresiisaufuncții,înloc
deovaloaresimplăauneicoloane.
•Indecșiparțiali,careindexeazădoaroparteauneitabele,potficreațiadăugândoclauză
WHERElasfârșitulcomenziiCREATEINDEX.
•Planificatorul este capabil să folosească mai mulți indecși împreună pentru a satisface
interogăricomplexe.
•Indexarea k-NN(nearest neighbors-cel mai apropiat vecin) asigură o căutare eficientă a
celeimaiapropiatevalorideaceeaspecificată,fărăocăutareexhaustivă. Estefolositoare
pentrugăsireacuvintelorsimilaresaualocațiilorcuajutoruldatelorgeospațiale.
•DelaPostgreSQL9.2încoaceesteposibilăscanareabazatăpeindecși,carepoateîncărca
dateledirectdinindecși,fărăamaifinevoiesăapelezelatabelaprincipală.
2.4Hibernate
HibernateesteounealtăpentrulimbajulJavapentrumapareaobiect-relație. Oferăposibilitatea
deamapaunmodelorientatpeobiectelaobazădedaterelațională. Hibernateestegratuitavând
olicențădetipopen-sourceGNULGPL2.1. PrincipalaatribuțieaunelteiHibernateestedea
mapaclaseJavalatabeledinbazadedateșimapareatipurilordedatedinJavalatipurilededate
SQL. Hibernate oferă deasemenea și facilități de interogare. Generează interogări SQL și eli-
bereazădezvoltatoruldenecesitateadeconversiemanualăarezultatelorinterogărilor. Maparea
claselorJavalatabelesepoatefacecuajutorulanotațiilorlaniveldeclasă. Acesteanotațiipot
fifolositepentruaținebazadedatelacurentcumodificărilestructuralealeclaselor. Hibernate
oferă și unelte pentru a specifica relațiile one-to-many sau many-to-many între clase. În plus
fațădeacesterelații,Hibernateoferășiuneltepentruspecificarearelațiilorreflexiveatuncicând
unobiectareorelațieone-to-manycualteinstanțealeaceluiașitipdeclasă. [ 9]
Hibernate suportă maparea tipurilor de date specificate de client. Acest lucru fac posibile
următoarelescenarii: [ 9]
•ÎnlocuireatipuluiSQLimplicitcândsemapeazăocoloanălaoproprietate.
•MapareaEnum-urilorJavalacoloanecașicumarfiproprietățiobișnuite.
•Mapareauneisingureproprietățilamaimultecoloane.

2.5. Wicket 11
Hibernate poate fi folosit atât în aplicații Java individuale, cât și în aplicații JavaEE care
folosescservlet-urișiEJB-uri. Poatefiintegratșiînaltelimbajedeprogramare. Deexemplu,
Adobe a integrat Hibernate în versiunea 9 a platformei de dezvoltare web ColdFusion, care
ruleazăpeserveredeaplicațieJavaEE.Din2010Hibernateadevenitoimplementarecertificată
aspecificațiilorJPAfiindînconformitatecustandardulJSR317. [ 9]
2.5Wicket
ApacheWicket,sausimpluWicket,esteunframeworkwebdecategorieușoarăbazatpecom-
ponente pentru limbajul de programare Java, similar ca și concept cu JavaServer Faces(JSF).
InițialafostscrisdecătreJonathanLockein2004. AdevenitunproiectApacheîniunie2007.
[2]
Modeleletradiționalemodel-view-controller(MVC)funcționeazăpebazădecererișipagini
întregi. Fiecarecerereesteatribuităuneimetodedintr-unobiectcontroller,careapoigenerează
răspunsulînîntregime,deobiceiprinluareadatelordintr-unmodelpentruapopulaunviewscris
într-un limbaj special de marcare. Acest lucru menține fluxul de control al aplicației simplu
și clar, însă poate face reutilizarea codului dificilă. Wicket, în schimb, este creat asemănător
framework-urilor GUI cum ar fi Swing. Aplicațiile Wicket sunt arbori de componente care
folosescmetodedelegatepentruareacționacererilorHTTPînacelașifelîncarecomponentele
Swing reacționează la evenimente de la mouse sau tastatură. Wicket este categorizat ca și un
frameworkbazatpecomponente. [ 2]
WicketfoloseșteXHTMLcașișablon. Fiecarecomponentăestelegatădeunelementnumit
înXHTMLșidevineresponsabilpentrurandareaaceluielementînformafinală. Opaginăeste
componentaceamaidesusșiestelegatădeexactunșablonXHTML.Folosingoetichetăspe-
cială,ungrupdecomponenteindividualepoatefiabstractizatîntr-osingurăcomponentănumită
panou,carepoatefiapoirefolosităînaltepaginisauchiaraltepanouri. Fiecarecomponentăeste
susținutădemodelulsău,carereprezintăstareacomponentei. Wicketnuarecunoștințădefaptul
cumcomponenteleșimodeleleinteracționeazăîntreele,caresunttratatecașiobiecteopacese-
rializateautomatșipersistateîntrecereri. Modelelemaicomplexepotfifăcutedetașabileșipot
ofericârligeprincareîșiaranjeazăpropriastocareșirestaurarelaînceputulșisfârșitulfiecărui
cicludecerere. Wicketnuimpuneniciunstratspecificdepersistență,așacăaplicațiilefolosesc
deobiceiocombinațiedintreHibernate,EJB-urisauobiectesimpleJavacașimodele. ÎnWic-
ket,toatăstarealaniveldeserverestegestionatăautomat. Nuartrebuisafolosiținiciodatăun
obiect HttpSession pentru a stoca starea. Ci, în schimb, starea este asociată cu componentele.

12 Capitolul 2. Tehnologii folosite
Fiecare pagină de pe server deține o ierarhie imbricată de componente stateful, unde fiecare
componentăeste,îndefinitiv,unobiectJava. [ 2]
Wicketestebazatpesimplitate. Wicketnuarefișieredeconfigurațiecaretrebuieînvățate.
Esteesteolibrăriesimplădeclasecareareoabordareconsistentăasuprastructuriicomponetelor.
[2]
2.6Bootstrap
Bootstrapesteolibrăriefrontendgratuită,open-sourcepentrucreareasite-urilorweb. Această
librărie conține șabloane HTML și CSS pentru crearea de formulare, butoane, navigare și alte
componente,precumșiextensiiJavaScript. Spredeosebiredealtelibrării,Bootstrapestefolosit
doarpentruparteadefrontend. [ 3]
Bootstrap a fost denumit inițial Twitter Blueprint și a fost dezvoltat de către Mark Otto și
Jacob Thornton în cadrul companiei Twitter ca și o librărie care încuraja consistența în cadrul
uneltelor interne. În 19 august 2011 proiectul a fost denumit Bootstrap și a devenit un proiect
opensource. În31ianuarie2012afostlansatBootstrap2careaadăugatunsistemde12coloane
responsive,suportpentruimaginiGlyphicons,șialtecomponentenoi. În19august2013afost
lansatBootstrap3careafostreproiectatsăfoloseascăundesignminimalistșioabordaremobil-
întâi. [3]
Bootstrap3suportăultimeleversiunialebrowserelorGoogleChrome,Firefox,InternetEx-
plorer, OperașiSafari. Bootstrapoferănumeroasevariabilecarecontroleazălucruricumarfi
culoarea sau padding-ul anumitor componente. Sistemul de grilă și designul responsive este
livratînmodimplicitcuoschemădegrilăculățimeade1170pixeli. Alternativsepoatefolosi
oschemăculățimevariabilă. Pentruambelecazurilibrăriaarepatruvariațiipentrudiferitere-
zoluțiisautipuridedispozitive: telefoanemobile,portretșilandscape,tableteșicomputerecu
rezoluțiemicășimare. Fiecarevariațieajusteazălățimeacoloanelor. [ 3]
2.7SVG.js
SVG.js este o librărie javascript pentru manipularea și animarea elementelor SVG. SVG.js nu
are dependințe și urmărește să aibă o mărime cât mai mică și o acoperire cât mai mare sau
completă a specificațiilor SVG. Librăria SVG.js este o librărie gratuită cu licență de tip MIT.
[19]
Câtevadincaracteristicileacesteilibrăriisunt: [ 19]
•Adăugaredeanimațiipentrumărime,poziție,transformări,culoare.

2.7. SVG.js 13
•Posibilitatedeextensiedatorităstructuriimodulare.
•Numeroaseplugin-uridisponibile.
•APIunificatîntrediferiteletipurideforme.
•Adăugareaevenimentelorlaelemente.
•Suportcompletpentrumăștideopacitate.
•Textanimatdupăuntraseu.
•Grupurideelemente.
•Tipareșigradientedinamice.
•Documentațiecompletă.
SVG.jsestecompatibilcuurmătoareleversiunidebrowseredesktop: [ 19]
•Firefox3+
•Chrome4+
•Safari3.2+
•Opera9+
•InternetExplorer9+
SVG.jsestecompatibilcuurmătoareleversiunidebrowseremobile: [ 19]
•iOSSafari3.2+
•AndroidBrowser3+
•OperaMobile10+
•ChromepentruAndroid18+
•FirefoxpentruAndroid15+

14 Capitolul 2. Tehnologii folosite
2.8Gradle
Gradleesteounealtăopen-sourcedeautomatizareconstruităpebazaconceptelorApacheAnt
șiApacheMavencareintroduceunlimbajnumitGroovyînloculXML-uluifolositdeMaven
pentrudeclarareaconfigurațieiproiectului. Gradleafostgânditpentruautomatizareaconstruirii
multi-proiectelor. Suportăconstruireaincrementalăprindeterminareainteligentăapărțilorcare
sunt la zi cu ultimele modificări. Orice sarcină dependentă doar asupra acelor părți nemodifi-
catenumaiesteexecutată. Plugin-urileinițialesuntconcentrateînspecialpedezvoltareaJava,
GroovyșiScala,darpeviitorsedoreșteadăugareaaltorlimbajeșiproiecte. [ 8]
2.9Git
Gitesteunsistemdecontrolalversiuniipentruurmărireamodificărilorfișierelordepecompu-
terșicoordonarealucruluicuanumitefișieredecătremaimultepersoane. Estefolositînspecial
pentrumanagementulcoduluisursăîndezvoltareasoftware,darpoatefifolositpentruaurmări
schimbărileoricăruitipdefișiere. Principalelescopurialeacestuisistemsuntviteza,integrita-
tea datelor și suportul fluxurilor de lucru distribuite, neliniare. Git a fost creat de către Linus
Torvalds în 2005 pentru dezvoltarea kernelului Linux, având alți dezvoltatori care contribuiau
ladezvoltareakernelului. CodulestemenținutînprezentdecătreJunioHamano. [ 7]
Lafelcașialtesistemedistribuitedecontrolalversiunii, șispredeosebiredealtesisteme
client-server,fiecaredirectordefișiereGitdepeoricarecomputeresteundepozitcompletcutot
istoriculșitoatecapacitățiledecontrolalversiunii,independentdeacesullarețeasauunserver
central. Gitestegratuitcuolicențădetipopen-sourcenumităGNUGPLversiunea2. [ 7]

15
3 Prezentarea proiectului
3.1Configurareaspațiuluidelucru
O să încep cu primul lucru pe care îl avem de făcut atunci când începem orice proiect nou, și
anumeconfigurareaspațiuluidelucrușicreareaproiectelorîncarevomstocafișierelesursă. Ca
șimediudedezvoltareamalessăfolosescEclipse. Pentruaceastălucrareamcreattreiproiecte
Javașianume:
1.ocupamasa_ejb; acest proiect va conține toate clasele Java care vor fi persistate în baza
dedate,totodatăaicivorfistocateșiclaselecareconțininterfețeleEJBcepotfiapelate
pentruastocașiarecuperadateleîn/dinbazadedate,adicăacestavafiproiectulcareva
conțineparteadebackendaserverului.
2.ocupamasa_web; în acest proiect vom stoca fișierele HTML, CSS, JavaScript și clasele
Java care vor popula fișierele HTML cu date în timp real din baza de date înainte să
fie trimise utilizatorilor pentru a fi afișate, mai exact acest proiect constituie partea de
frontendaaplicației.
3.ocupamasa_ear;acestproiectestedoaruncontainer,nuvomadăugafișieresursăaici,ci
înacestproiectvomincludeceledouăproiecteanterioareșivafigeneratăarhivaearcare
vaputeafidistribuitășilansatăpeserveruldeaplicație.
CaurmareafaptuluicăamfolositGradlecașisistemdeautomatizarepentrucompilareași
arhivareacoduluiînfișierulear,totînaceastăetapădeconfigurareosăprezintșiconfigurațiile
necesarepentruarulaGradle. Configurațiaestedestuldesimplășidirectă,pentruaconfigura
Gradle voi adăuga câte un fișier numit build.gradle în directorul de bază al celor trei proiecte
createanterior. Fișierulbuild.gradledinproiectulocupamasa_ejbvaconțineurmătorulcod:
apply plugin: ’java’
apply plugin: ’eclipse wtp’
dependencies {
compileOnly fileTree(dir: ”${System.env.WILDFLY_HOME}/modules”,
include:’**/*.jar’)
compileOnly”com.google.guava:guava:$guavaVersion”

16 Capitolul 3. Prezentarea proiectului
compileOnly”org.apache.poi:poi ooxml:$apachePoiVersion”
testImplementation ” junit:junit: $junitVersion”
}
Dupăcumputemvedeaînacestfișier,atrebuitdoarsădeclarămfaptulcăproiectulnostru
esteunulJavașicăvomfolosiEclipsecașimediudedezvoltare,șiapoiamdeclaratdependințele
decarevomaveanevoieînacestproiect. Primeletreidependințeforfifolositelacompilaredar
nuvorfilivratealăturideproiectînarhivajar,deoareceosăleadăugămlaarhivăînproiectul
ear,iarultimadependințăestenecesarălarulareatestelordemodel. Dupăcumseobservăprima
dependințăfoloseștevariabiladesistemWILDFLY_HOMEcaretrebuiesăaratelocațiaîncare
este instalat serverul Wildfly. Pentru următoarele dependințe am folosit proprietăți pentru a
specificaversiunealibrăriei. Așadarvatrebuiadăugatîncăunfișierdenumitgradle.properties
înacelașidirectorîncareestelocatfișierulbuild.gradle. Fișierulgradle.propertiesesteunsimplu
fișiercareconțineolistăcuperechicheie-valoare,adicăînacestcaz:
guavaVersion=25.1 jre
junitVersion=4.12
apachePoiVersion=3.17
În continuare fișierul build.gradle din directorul de bază al proiectului ocupamasa_web va
conține:
apply plugin: ’war’
apply plugin: ’eclipse wtp’
sourceSets {
main{
java {
srcDir ’src/main/java’
}
resources {
srcDir ’src/main/resources’
srcDir ’src/main/java’
}
}
}
dependencies {

3.1. Configurarea spațiului de lucru 17
compile ”org.apache.wicket:wicket core:$wicketVersion”
compile ”org. wicketstuff:wicketstuff core:$wicketVersion”
compile ”org. wicketstuff:wicketstuff javaeeinject:$wicketVersion”
compile ”org.apache.wicket:wicket authroles:$wicketVersion”
compile ”org. wicketstuff:wicketstuff servlet3 auth:$wicketVersion”
compile ”org. wicketstuff:wicketstuff dropdown menu:$wicketVersion”
compile ”org.apache.wicket:wicket extensions:$wicketVersion”
compile ”org. wicketstuff:wicketstuff datatables:$wicketVersion”
compile ”org.apache.wicket:wicket datetime:$wicketVersion”
compile ”com.googlecode.wicket jqueryui:wicket jqueryui:$wicketVersion”
compile ”com.googlecode.wicket jqueryui:wicket kendoui:$wicketVersion”
compile ”com.googlecode.wicket jqueryui:wicket kendouithemedefault:$
wicketVersion”
compile ”com.googlecode.wicket jqueryui:wicket kendouiculture:$
wicketVersion”
compile ”org.apache.pdfbox:pdfbox:$pdfBoxVersion”
compile ”com.github. dhorions:boxable:$pdfBoxableVersion”
compile ”commons beanutils:commons beanutils:$apacheCommonsVersion”
compile ”org. webjars:bootstrap: $bootstrapVersion”
providedCompile”com.google.guava:guava:$guavaVersion”
providedCompile”org.apache.poi:poi ooxml:$apachePoiVersion”
providedCompile fileTree(dir: ”${System.env.WILDFLY_HOME}/modules”,
include:’**/*.jar’)
providedCompile project(’:ocupamasa_ejb’)
testImplementation ” junit:junit: $junitVersion”
}
La fel ca data trecută, specificăm faptul că acesta este un proiect de tip war și că folosim

18 Capitolul 3. Prezentarea proiectului
Eclipsecașimediudedezvoltareșidependințeledecareavemnevoieînacestproiect. Versiunile
librăriilorfolositesuntdeclarateînfișierulgradle.properties:
guavaVersion=25.1 jre
junitVersion=4.12
wicketVersion=8.0.0
apacheCommonsVersion=1.9.3
bootstrapVersion=3.3.7 1
pdfBoxVersion=2.0.4
pdfBoxableVersion=1.5
apachePoiVersion=3.17
Observăm totuși că în acest caz am suprascris valorile inițiale pentru directoarele fișiere-
lorsursă,șianumeamspecificatfaptulcășicaleadedirectoaresrc/main/javasăfiefolosităla
arhivarea resurselor. Acest lucru este necesar pentru că librăria Wicket pe care o vom folosi
specificăfaptulcăarhitecturaaplicațieitrebuiesăconținăfișiereleHTMLînacelașipachetcu
claseleJavașisăaibăacelașinumecașiclaseleJava. Așadar,dacănuspecificămfaptulcăsrc/-
main/javaesteundirectorderesurse,fișiereleHTMLnuvoifiadăugateînarhivafinală. Înacest
fișierbuild.gradlemaiobservămșifaptulcăamdeclaratodependințăfațădeproiectulocupa-
masa_ejb. DesigurcăavemnevoiedeacestproiectpentruaapelainterfețeleEJBcareasigură
accesulcubazadedate. Vomspecificalocațiaacestuiproiectadăugândunfișiersettings.gradle
înacelașidirector,carevaconțineurmătoarele:
include ’:ocupamasa_ejb’
project(’:ocupamasa_ejb’). projectDir = new File(’ ../ ocupamasa_ejb’)
Înfinalvomaveanevoiedefișierulbuild.gradledinproiectulocupamasa_earcarevaarhiva
acestedouăproiecteîmpreunășivaadăugalibrăriilenecesareînarhivă. Acestfișierconține:
apply plugin: ’ear’
apply plugin: ’eclipse’
ear {
baseName=’ocupamasa_ear’
version = ’1.0’
deploymentDescriptor {
webModule(project(’:ocupamasa_web’).getName()+’.war’, ”/”)

3.1. Configurarea spațiului de lucru 19
}
}
dependencies {
deploy project(path: ’:ocupamasa_web’, configuration: ’archives’)
deploy project(’:ocupamasa_ejb’)
earlib ”org.apache.logging. log4j:log4j api:$log4jVersion”
earlib ”org.apache.logging. log4j:log4j core:$log4jVersion”
earlib ”org.apache.logging. log4j:log4j slf4jimpl:$log4jVersion”
earlib ”com.google.guava:guava:$guavaVersion”
earlib ”org.apache.poi:poi ooxml:$apachePoiVersion”
}
După cum se observă, în această arhivă am adăugat cele două proiecte ejb și war și libră-
riile care sunt folosite de acestea, și nu au fost adăugate deja în arhiva war. La fel ca și în
fișierele precedente, versiunile librăriilor au fost declarate într-un fișier separat de proprietăți
gradle.properties:
guavaVersion=25.1 jre
log4jVersion=2.11.0
apachePoiVersion=3.17
PentruautomatizărileGradlecarefolosescunsingurproiectfișierulsettings.gradleesteop-
țional, însă pentru automatizările multi-proiect acest fișier este obligatoriu. Așadar trebuie să
maiadăugămșiunfișiersettings.gradleîncarespecificămcareproiectevorfifolosite,pelângă
celcurent,șicareesteproiectuldebază. Înacestcazfișierulsettings.gradleconține:
include ’ocupamasa_web’,ocupamasa_ejb’
rootProject .name=’ocupamasa_ear’
project(’:ocupamasa_web’).projectDir = new File( settingsDir , ’ ../ ocupamasa_web’)
project(’:ocupamasa_ejb’). projectDir = new File( settingsDir , ’ ../ ocupamasa_ejb’)

20 Capitolul 3. Prezentarea proiectului
3.2Autentificareșiautorizare
PentruautentificareautilizatoriloramfolosittehnologiadeautentificareoferitădecătreJavaEE.
Aceasta constă în securizarea metodelor care vor fi apelate din exterior. Acest lucru se face
cuajutorulanotațiilor. Așadarsăîncepemcuunexempluînacestsens. Avemmetodapersist-
NewArtisticEventcarepoatefiapelatădinexterior. Aceastămetodăprimeșteunevenimentcași
argumentpecareîlvasalvaînbazadedate. Noidorimcaaceastămetodăsăpoatăfiapelatădoar
decătreutilizatoriicareaurolulcreate_events,rolcareledăpermisiuneadeacreaevenimente.
Acestlucruesterealizatfoartesimpluprinadăugareauneianotațiideasupraacesteimetodecare
arată în felul următor: @RolesAllowed(“create_events”). Anotația @RolesAllowed specifică
rolurilecareaupermisiuneadeaaccesametodaasupracăreiaaufostadăugate. Înacestfelam
reușitsăsecurizămaplicațiaadăugânddoaroliniedecod. Darîntr-oaplicațierealămaiavem
câtevalucrurideadăugat. Înacestmoment,dacăunutilizatorcarenuesteautentificatvaîncerca
să creeze un eveniment, va fi aruncată o excepție de permisiune. Noi nu dorim să aruncăm o
excepție în acest caz, ci dorim ca utilizatorul să fie redirecționat la pagina de login de unde se
va putea autentifica. Din nou, acest lucru este ușor de realizat deorece am folosit librăria Wi-
cketcareestecompatibilăcuautentificareaEJB,iarpentruaredirecționautilizatorullapagina
de login, tot ce avem de făcut este să anotăm pagina unde se crează evenimentele cu anotația
@AuthorizeInstantiation(“create_events”). Așadar dacă utilizatorul nu este autentificat, va fi
redirecționatlapaginadelogincareestespecificatădecătremetodagetSignInPageClassaapli-
cației. Euamsuprascrisaceastămetodăpentruareturnapropriapaginădeloginpersonalizată.
Un alt caz pe care îl putem întâmpina este atunci când un utilizator este autentificat, însă nu
arerolulnecesarpentruaaccesaoanumităresursă. Înacestcaz,utilizatorulvafiredirecționat
automatdecătrelibrăriaWicketlaopaginăîncareesteexplicatfaptulcănuareacceslaresursa
pecaredoreștesăoacceseze. Înaplicațiameaamevitatcazurileîncareutilizatorulesteredi-
recționat la această pagină de acces nepermis prin ascunderea butoanelor și a paginilor la care
utilizatorulnuaredreptuldeacces.
Dupăcuma-țipututobserva,pentrusecurizareauneimetodetotceatrebuitsăadăugămafost
rolulnecesarpentruaaccesaacearesursă. Nuamspecificatînschimbnicăierirolurilepecare
leareunutilizator,șiniciînpaginadeloginnuamspecificatutilizatoriicaresuntînregistrațiîn
sistemsaurolurilepecareleauaceștia. AutentificareaEJBpermitecatoateacestelucruri,adică
utilizatorii,paroleleacestorașirolurileutilizatorilor,săfiespecificateînfișieruldeconfigurații.
Acestlucruesteunavantajdeoarecenepermitecaînmomentuldezvoltăriiaplicațieisănuavem
nevoiesăștimundevorfistocațiutilizatoriișicumstabilimrolurileutilizatorilor. Deexemplu
putem să salvăm datele de securitate ale utilizatorilor într-o bază de date, sau într-un fișier de

3.3. Structura bazei de date 21
pe sistem, sau putem să salvăm inițial datele într-unfișier, ca apoi să le transferăm într-obază
de date, și toate aceste lucruri pot fi făcute fără a necesita modificări ale aplicației. În cazul
aplicațieimeledateledesecuritatedespreutilizatorișirolurileacestorasuntsalvateînbazade
date,așadaramadăugaturmătoareleconfigurațiiînfișieruldeconfigurațiealserverului:
<authentication>
<login modulecode=”Database”flag=”required”>
<module optionname=”dsJndiName”value=”java:jboss/datasources/ocupamasa_db
”/>
<module optionname=”principalsQuery”value=”SELECTuser_schema.
get_principal(?)AS principal”/>
<module optionname=”rolesQuery”value=”SELECTget_permissionsas
role_name,’Roles’FROMuser_schema.get_permissions(?)”/>
<module optionname=”password stacking”value=”useFirstPass”/>
<module optionname=”hashAlgorithm”value=”SHA 256”/>
<module optionname=”hashEncoding”value=”base64”/>
</login module>
</ authentication >
Așacumsepoateobservadinacesteconfigurații,paroleleutilizatorilorsuntcriptateînbaza
dedatecualgoritmulSHA-256.
3.3Structurabazeidedate
Pânăacumamvorbitdesprecumamsetatspațiuldelucrușicumamimplementatautentificarea
șiautorizareaînaceastăaplicație. Acumcăampusbazeleaplicațieișiutilizatoriisepotînregistra
șilogapeaplicație,credcăestetimpulsădiscutdespreparteaceamaiimportantăaaplicației,și
anumeparteadebackend. Structurabazeidedateaaplicațieiesteprezentatăînfigura 3.1. După
cumseobservăstructuraestedestuldecomplexă,așadarpentruaputeavedeatoatetabeleledin
bazadedateamalesoorientarelandscapeafiguriipeoîntreagăpagină.
Cașiorganizareabazeidedateșiatabelelor,amîncercatoaranjarecâtmailogicăadatelor
și a relațiilor dintre tabele. Ca și tabelă de bază am creat tabela care conține datele despre o
companie. Companiapoateaveaapoirelațiicutabelarestaurant,însensulcăocompaniepoate
aveaunulsaumaimulterestaurante. Restaurantulpoatesăconținăapoimaimultesăli,carela
rândul lor pot să conțină mese, iar mesele pot să conțină scaune. Un restaurant mai poate să
conținăevenimente,rolurișievenimentedeauditcarereprezintădefaptistoriculmodificărilor
pentruacelrestaurant. Observămșitabelautilizatorilor,carepoatesăaparținădeunrestaurant,

22 Capitolul 3. Prezentarea proiectului
Figura3.1: Structurabazeidedate

3.4. Structura paginilor 23
încazulîncareutilizatorulesteangajatalaceluirestaurant,șicareconțineșirelațiicualtetabele,
cum ar fi evenimentele utilizatorului, invitații utilizatorului pentru un anumit eveniment sau
rolurileutilizatorului,încazulîncareacestaesteangajatalunuirestaurant. Încolțuldinstânga
sus al figurii se observă două tabele care nu au relații cu alte tabele. Aceastea sunt doar două
tabeleutilitarepecarele-amutilizatpentruastocaemail-urilecarenuaureușitsăfietransmise
serveruluismtp,respectivotabelăpecareamfolosit-opentruastocaanumiteproprietățicheie-
valoareutileînîntregulaplicației.
3.4Structurapaginilor
Structurapaginiloresteprezentatăînfigura 3.2. Dupăcumsepoatevedeaînfigurăoriceutili-
zatorcareacceseazăocupamasa.rovaajungeinițiallapaginaprincipală. Dinpaginaprincipală
areapoiopțiuneadeaaccesapaginadelogin. Dinpaginadeloginsepoateapoiaccesapagina
deundesepoatecreauncontnou,încazulîncareutilizatorulnus-aînregistratdeja,saupagina
pentruresetareaparolei,încazulîncareutilizatorularedejauncontcreat,darauitatparola. În
cazulîncareutilizatorulseloghează,vafiredirecționatcătrepagina“Evenimentelemele”care
areculoareaverdeînfigură. Aceastăpaginăesteopaginăintermediarăcareaparedoarîncazul
încareutilizatorularemaimulteevenimentedincarefaceparte. Încazulîncareutilizatorulare
doarunsingureveniment,acestavafiredirecționatautomatlapagina“Aranjareinvitați”. Pagi-
niledinfigurăcareauculoarearoșie,respectiv“Configurațiisală”,“Evenimente”,“Angajați”,
“Roluri”și“Istoricmodificări”,s-arputeasănufievizibilepentrutoțiutilizatorii. Aceastepa-
ginivorfivizibiledacăsuntîndeplinitedouăcondițiidecătreutilizatorullogat. Înprimulrând
utilizatorultrebuiesăfieadăugatcașiangajatalunuirestaurant,deoareceacestepaginiarface
senssăfievizibiledoarpentruunrestaurant. Deexemplu,“Configurațiisală”sereferălaconfi-
gurațiilesăliiunuianumitrestaurant,lafelcașipagina“Angajați”caresereferălaangajațiiunui
anumit restaurant, și la fel și pentru celelalte pagini; “Evenimente” în cazul acesta se referă la
evenimentelerestaurantului,nuautilizatoruluilogat,“Roluri”suntroluriledisponibilecarepot
fiadăugateangajațilorrestaurantuluirespectiv,iar“Istoricmodificări”sereferălamodificările
careaufostfăcutepentruunrestaurant. Adouacondițiecaretrebuieîndeplinităpentrucaaceste
paginisăfievizibileutilizatoruluiestecautilizatorulsăaibărolulnecesarpentruaaveadreptul
deacceslaacestepagini. Acesterolurisuntstabilitedecătreadministratorulrestaurantului.
3.5Generareaplanului2Dalmeselor
Amalessăafișezplanul2DalmeselorînformatSVG.Amalesacestformatînmarepartede-
oareceimaginileSVGnuîșipierdclaritateacândsuntmărite. Totodatăesteunformatușorde

24 Capitolul 3. Prezentarea proiectului
Figura3.2: Structurapaginilor
generatcarepoateapoifisalvatîntr-unfișierpecalculatorulutilizatorulșipoatefiafișatdecătre
aproapetoatebrowserele. PentrugenerareacoduluiSVGamfolositlibrăriaJavaScriptSVG.js.
Aceastălibrărieesteușordefolositașacănuosaintruîndetaliireferitoarelasecvențeledecod
care trebuie apelate, deoarece există o documentație vastă pe website-ul lor oficial svgjs.com.
OfacînschimboprezentarelanivelmacroadocumentuluiSVGgeneratcarereprezintăplanul
meselor. CașiobiecteSVGamfolositdreptunghiulpentruareprezentameseledreptunghiulare
șipătrateșicerculpentruareprezentameselerotunde. Totodatăamfolositcerculșipentruare-
prezentascaunele. Îninterioruldreptunghiurilorșiacercurilorpoateexistatextcarereprezintă
numelemesei, încazulmeselor, saunumeleinvitatuluicareafostașezatpescaunulrespectiv,
încazulscaunelor. Pentruareprezentaundreptunghi,librăriaSVG.jsarenevoiedoardedouă
numere care reprezintă lungimea și lățimea dreptunghiului. Pentru a reprezenta un cerc este
necesardoarunnumărcarereprezintădiametrulcercului. Obiectelesuntgenerateîncolțuldin
dreapta sus a imaginii, iar apoi pot fi mutate la altă locație prin specificarea coordonatelor x,
pe orizontală, și y, pe verticală, a obiectului. Obiectele pot fi mutate prin specificarea coordo-
natelor absolute, care au ca bază colțul din dreapta sus de coordonată 0, 0 față de părinte, sau
prinspecificareacoordonatelorrelative,carevormișcaobiectulcuvaloareaprecizatăînfuncție
de locația sa curentă. Pentru a înțelege mai bine sistemul de coordonate SVG.js o să dau un
exemplu. Săpresupunemcăamdesenatuncerclalocația10,10. Dacăvomspecificacercului

3.5. Generarea planului 2D al meselor 25
cașicoordonateabsolutevalorile20,20,cerculvafiplasatînfinallalocația20,20. Înschimb,
dacăspecificămvalorile20,20cașicoordonaterelative,cerculsevaaflaînfinallalocația30,
30.
TotsistemuldecoordonatealimaginiiSVGsebazeazăpecoordonatelerelativelapărinte.
Inițial părintele obiectelor este chiar imaginea SVG, așadar obiectele adăugate vor avea ca și
punctdeorigine0,0chiarcolțuldinstângasusalimaginiiSVG.Totuși,esteposibilcautiliza-
torul care crează imaginea SVG să adauge obiecte imbricate, caz în care punctul de origine 0,
0 nu va fi colțul din stânga sus al imaginii SVG, ci locația containerului în care este imbricat
obiectul. De exemplu, dacă adaug un container la locația 10, 10 și în acel container adaug un
cerclalocația0,0,cerculvaapăreaînimaginelalocația10,10,deoareceorigineaesterelativă
lacontainer. Desigurcăourmareaacestuifaptvaficăatuncicândcontainerulvafimutat,toate
obiecteledininteriorulcontaineruluivorfimutatecorespunzător.
În continuare o să prezint modul de gestionare a coordonatelor meselor și scaunelor în ca-
drul aplicației. Pentru fiecare masă adăugată de către un utilizator este generat un container
SVG.Acestcontainerconținecercurilecarevorreprezentascauneleșicerculsaupătratulcare
reprezintămasa. Coordonatelemeseișiascaunelorsuntgeneratedecătreaplicațieînmomentul
generării și nu mai pot fi apoi modificate. Utilizatorul poate modifica doar coordonatele con-
tainerului, care va duce la o mișcare uniformă a mesei împreună cu scaunele. Scaunele au un
diametruprestabilit. Dimensiunilemeseidreptunghiularesuntcalculatedupăformula:
dimX =Math:max (RECT_TABLE_MIN_SIZE;
Math:max (topChairsNumber (CHAIR_DEFAULT _DIAMETER
+GAP_BETWEEN _CHAIRS )GAP_BETWEEN _CHAIRS;
bottomChairsNumber (CHAIR_DEFAULT _DIAMETER
+GAP_BETWEEN _CHAIRS )GAP_BETWEEN _CHAIRS ))
dimY =Math:max (RECT_TABLE_MIN_SIZE;
Math:max (leftChairsNumber (CHAIR_DEFAULT _DIAMETER
+GAP_BETWEEN _CHAIRS )GAP_BETWEEN _CHAIRS;
rightChairsNumber (CHAIR_DEFAULT _DIAMETER
+GAP_BETWEEN _CHAIRS )GAP_BETWEEN _CHAIRS ))(3.1)
unde

26 Capitolul 3. Prezentarea proiectului
CHAIR_DEFAULT _DIAMETER : diametrulprestabilitalunuiscaun
GAP_BETWEEN _CHAIRS : golulprestabilitdintrescaune
RECT_TABLE_MIN_SIZE : dimensiuneaminimăprestabilităauneimese
topChairsNumber : numărultotaldescaunedinparteadesusamesei
bottomChairsNumber : numărultotaldescaunedinparteadejosamesei
leftChairsNumber : numărultotaldescaunedinparteastângăamesei
rightChairsNumber : numărultotaldescaunedinparteadreaptăamesei
Coordonatelemeseiîncadrulcontaineruluisunt:
x=CHAIR_DEFAULT _DIAMETER
y=CHAIR_DEFAULT _DIAMETER(3.2)
unde
CHAIR_DEFAULT _DIAMETER : diametrulprestabilitalunuiscaun
Încazulmeselordreptunghiulare,coordonatelescaunelorsuntrelativușordecalculat. Așa-
darvomaveapentruscauneledinparteadesusameseiurmătoareaformulă:
x=i(CHAIR_DEFAULT _DIAMETER +GAP_BETWEEN _CHAIRS )
y=CHAIR_DEFAULT _DIAMETER(3.3)
unde
CHAIR_DEFAULT _DIAMETER : diametrulprestabilitalunuiscaun
GAP_BETWEEN _CHAIRS : golulprestabilitdintrescaune
i : indexulscaunuluidesusavândbaza0
Pentruscauneledinparteadejosvomaveaformula:

3.5. Generarea planului 2D al meselor 27
x=i(CHAIR_DEFAULT _DIAMETER +GAP_BETWEEN _CHAIRS )
calculatedMaxY =Math:max (chairNumberLeft (CHAIR_DEFAULT _DIAMETER
+GAP_BETWEEN _CHAIRS )GAP_BETWEEN _CHAIRS;
chairNumberRight (CHAIR_DEFAULT _DIAMETER
+GAP_BETWEEN _CHAIRS )GAP_BETWEEN _CHAIRS )
y=Math:max (calculatedMaxY; RECT _TABLE_MIN_SIZE )
(3.4)
unde
CHAIR_DEFAULT _DIAMETER : diametrulprestabilitalunuiscaun
GAP_BETWEEN _CHAIRS : golulprestabilitdintrescaune
i : indexulscaunuluidejosavândbaza0
RECT_TABLE_MIN_SIZE : dimensiuneaminimăprestabilităauneimese
chairNumberLeft : numărultotaldescaunedinparteastângăamesei
chairNumberRight : numărultotaldescaunedinparteadreaptăamesei
Pentruscauneledinstângameseiavemformula:
x=CHAIR_DEFAULT _DIAMETER
y=i(CHAIR_DEFAULT _DIAMETER +GAP_BETWEEN _CHAIRS )(3.5)
unde
CHAIR_DEFAULT _DIAMETER : diametrulprestabilitalunuiscaun
GAP_BETWEEN _CHAIRS : golulprestabilitdintrescaune
i : indexulscaunuluidinstângaavândbaza0
Pentruscauneledindreaptameseiavemformula:

28 Capitolul 3. Prezentarea proiectului
calculatedMaxX =Math:max (chairNumberUp (CHAIR_DEFAULT _DIAMETER
+GAP_BETWEEN _CHAIRS )GAP_BETWEEN _CHAIRS;
chairNumberDown (CHAIR_DEFAULT _DIAMETER
+GAP_BETWEEN _CHAIRS )GAP_BETWEEN _CHAIRS )
x=Math:max (calculatedMaxX; RECT _TABLE_MIN_SIZE )
y=i(CHAIR_DEFAULT _DIAMETER +GAP_BETWEEN _CHAIRS )
(3.6)
unde
CHAIR_DEFAULT _DIAMETER : diametrulprestabilitalunuiscaun
GAP_BETWEEN _CHAIRS : golulprestabilitdintrescaune
i : indexulscaunuluidejosavândbaza0
RECT_TABLE_MIN_SIZE : dimensiuneaminimăprestabilităauneimese
chairNumberUp : numărultotaldescaunedinparteadesusamesei
chairNumberDown : numărultotaldescaunedinparteadejosamesei
Pentruacalculadiametruluneimeserotundeînfuncțiedenumăruldescaunedelamasăam
pornitdelaurmătoareaformulăscrisădecătreParclyTaxelîncadrulunuirăspunspewebsite-ul
math.stackexchange.com, care calculează raza cercului mare dintr-un inel de cercuri distanțat
uniform. [15]Formulaeste:
R=r(1 +1
sin(/n)) (3.7)
unde
r: razacercurilorcareformeazăinelul
n: număruldecercuridininel
Porninddelaformula 3.7,amaplicat-oastfelîncâtsăaflurazacerculuiînscrisîninelulde
cercuridistanțatuniform. Așadarformuladevine:
R=ROUND_TABLE_MIN_RADIUS; n 3
R=r(1 +1
sin(/n))r2; n > 3(3.8)

3.6. Descrierea paginilor 29
unde
ROUND_TABLE_MIN_RADIUS : razaminimăauneimese
r : razaprestabilităaunuiscaun
n : numărultotaldescaune
Astfeldiametruluneimeseseaflăînmulțindrezultatulformuleiprecendentecudoi. Pentru
a afla coordonatele scaunelor din jurul unei mese rotunde am folosit o formulă de pe site-ul
stackoverflow.com. [ 5]Astfelformulaadaptatăaplicațieieste:
dividedAngle = 360/ noOfDividingPoints
circleRadius =tableRadius +CHAIR_DEFAULT _RADIUS
x(i) =tableRadius +circleRadius Math:cos (Math:toRadians (idividedAngle ))
y(i) =tableRadius +circleRadius Math:sin (Math:toRadians (idividedAngle ))
(3.9)
unde
noOfDividingPoints : număruldescaune
tableRadius : razamesei
CHAIR_DEFAULT _RADIUS : razaprestabilităaunuiscaun
i : indexulscaunuluiîncepânddela0
3.6Descriereapaginilor
3.6.1Paginapentrucreareaunuicont
O să prezint paginile în ordinea în care ar fi ele accesate în mod normal de către un utilizator,
aceastafiindșiordinealogicăîncareartrebuiaccesate. Așadarprimapaginăestepaginapentru
creareaunuicontnou. Arhitecturaaplicațieifacenecesarcreareaunuicontpentrufiecareutili-
zator. Acestcontesteutilizatpentruaidentificaunutilizatorșia-iconferidrepturideaccesla
paginilenecesare. Uncontesteidentificatprintr-oadresădeemailcaretrebuiesăfieunicăpen-
truaceastăaplicație. Euamalessăcreezuncontnoucuadresameadeemailșiamcompletatși
numele,dupăcumsevedeînfigura 3.3. Înmomentulîncaresecreazăuncontnou,utilizatorul
vaprimilaadresadeemailintrodusăparolacucaresepoatelogapewebsite.

30 Capitolul 3. Prezentarea proiectului
Figura3.3: Paginapentrucreareaunuicont
3.6.2Paginadelogin
Paginadeloginesteunasimplăîncareutilizatorultrebuiesăintroducădoaradresadeemailcu
care s-a înregistrat și parola. Opțional are o căsuță numită “Vreau să rămân logat” care, dacă
estebifată,vamențineutilizatorullogatînaplicațiepentrumaimulttimp,chiardacăînchideși
deschidebrowser-ul,peacelașidispozitiv. Pentruamălogaînaplicațievoiintroduceadresade
emailcucarem-amînregistratanteriorșiparolaprimităpeemail.
Figura3.4: Paginadelogin

3.6. Descrierea paginilor 31
3.6.3Paginapentrucreareauneicompanii
Nu este obligatoriu ca fiecare utilizator să aparțină unei companii, însă pentru a avea acces
la toate paginile o să creez o companie pentru noul utilizator înregistrat. Compania nu o să
fie una reală, ci voi crea o companie de test cu denumirea “Universitatea Oradea”, voi lăsa
codul unic de identificare și numărul de înregistrare la Registrul Comerțului necompletate, un
capital social de 200 de lei, numărul de telefon și adresa de contact a Universității Oradea, iar
ca și administrator al companiei am completat adresa de email înregistrată precedent. Adresa
companieiamcompletat-ocuadresaUniversitățiiOradea.
Figura3.5: Paginapentrucreareauneicompanii

32 Capitolul 3. Prezentarea proiectului
3.6.4Paginapentrucreareaunuirestaurant
Cumocompaniepoatesăadministrezemaimulterestaurante, următorulpasestecreareaunui
restaurantcareaparținedecompaniacreată. Dupăcumsevedeînfigura 3.6,amselectatcom-
pania creată anterior pentru care am să creez un restaurant cu numele Select UO, am adăugat
adresadecontactdelacantinaSelectșiamadăugattotadresameadeemailcașiadministrator
alrestaurantului. Adresarestaurantuluiesteaceeașicuadresacompaniei.
Figura3.6: Paginapentrucreareaunuirestaurant

3.6. Descrierea paginilor 33
3.6.5Paginaangajaților
Așadar în pașii precedenți am creat cu succes o companie și un restaurant. După cum se ob-
servăînpaginaangajațilorprezentăînfigura 3.7,pentrurestaurantulSelectUOavemunsingur
angajat cu rolul de Super Administrator. O să vedem în pagina următoare ce permisiuni are
acest rol. Din această pagină se pot adăuga, modifica și șterge angajații restaurantului pe care
tocmail-amcreat. Modificareaunuiangajatconstădefaptînmodificarearoluluipecareîlareîn
acestrestaurant. Numele,adresadeemailsauparolaunuiangajatnupotfimodificatedecătre
administratorulrestaurantului,doarunutilizatorîșipoatemodificapropriiledatereferitoarela
contulsău.
Figura3.7: Paginaangajaților
3.6.6Paginarolurilor
Paginarolurilorconținetoaterolurilecarepotfiadăugatunuiangajat. Înaceastăpaginăputem
modificarolurile,crearolurinoisauștergerolurileprezente. Fiecarerolareanumitepermisiuni
care reprezintă dreptul de acces la o anumită pagină sau modificarea conținutului paginilor.
Dupăcumvedemîn figura 3.8, existădejacinci roluricareaufost createautomatde aplicație
la crearea restaurantului. Acestea au fost create pentru a ușura munca administratorului resta-
urantului. Fiecare dintre cele trei roluri pentru manageri au drepturi de creare, modificare și
ștergerelapaginapecareoadministreazășidoardreptdevizualizareacelorlaltepagini. Rolul

34 Capitolul 3. Prezentarea proiectului
Administrator are toate permisiunile, respectiv creare, modificare și ștergere pentru toate pa-
ginile. În pagina precedentă, respectiv pagina utilizatorilor, am observat că utilizatorul Groza
DănuțareroluldeSuperAdministrator. SepoateobservaînaceastăpaginăcărolulSuperAd-
ministrator nu poate fi modificat sau șters. Acest lucru este o cauză a faptului că rolul Super
Administratoresteunrolspecialpentrucăesteobligatoriucalaoricemomentdetimpsăexiste
unadministratoralrestaurantului. Totodatăacestrolîiconferăutilizatoruluianumiteavantaje.
Înprimulrând, unangajatcareareroluldeSuperAdministratorîntr-unrestaurant, nupoatefi
concediatdinacelrestaurantdecătrealtangajat,chiardacăangajatulrespectivarepermisiunea
deconcediere. Înaldoilearând,unuiangajatcareareroluldeSuperAdministratornuîipoate
fi modificat acest rol de către alt angajat, chiar dacă angajatul respectiv are permisiunea de a
modificarolurileangajaților.
Figura3.8: Paginarolurilor
3.6.7Paginapentruconfigurațiasălilor
Paginapentruconfigurațiasăliloresteunadinpaginileimportantealeacesteiaplicațiifiindpri-
mulpascaretrebuieurmatpentruîndeplinireascopuluiaplicației. Aceastăpaginăconținecon-
figurațiilemeselorpentruoanumităsală. Unrestaurantpoateaveamaimultesăli,astfelvacrea
oconfigurațiepentrufiecaresală, saupoatecreamaimulteconfigurațiipentruaceeașisală, în
cazul în care mesele se rearanjează în funcție de numărul de persoane participante la un eve-
nimentîn salarespectivă. Observăm că afost dejacreată o salănumită “Sala Principală”care

3.6. Descrierea paginilor 35
conține o masă rotundă cu 12 locuri. Pentru scopul acestei prezentări nu o să modific această
sală,însăosăprezintoconfigurațieposibilăînfigura 3.10.
Figura3.9: Paginapentruconfigurațiasălilor
3.6.8Paginaevenimentelor
Pagina evenimentelor este a doua pagină importantă a acestei aplicații. După ce a fost creată
configurațiasălii,sepotadăugaevenimentepentruaceasală. Momentannuexistăevenimente
create,așadarvoicreaunevenimentdetestcarevaavealocînSalaPrincipalăîndatade7iulie
șiîmivoiadăugapropriaadresădeemailcașiclientalacestuieveniment. Creareaevenimen-
tuluiestearătatăînfigura 3.12. Încazulîncareexistăevenimentecreatepentruunrestaurant,
angajații care au permisiunile necesare vor putea vedea invitații pe care clientul i-a așezat la
meseșinumărullocurilorocupate.
3.6.9Paginacuistoriculmodificărilor
Înaintesătreclaaranjareainvitațilorpentruevenimentulcreat,osăprezintopaginăutilăînad-
ministrareauneicompaniicumaimulțiangajați,șianumepaginacuistoriculmodificărilor. În
aceastăpaginăputemvedeamodificărileadusedecătretoțiangajațiirestaurantuluiasupradate-
lor. Încazuldefațăexistădoardouămodificări,șianumecrearearestaurantuluicarevaapărea

36 Capitolul 3. Prezentarea proiectului
Figura3.10: Exemplurealdesală

3.6. Descrierea paginilor 37
Figura3.11: Paginaevenimentelor
Figura3.12: Creareaunuieveniment

38 Capitolul 3. Prezentarea proiectului
doarodatălaînceputulistoricului,șimodificareaadusăanterioradicăcreareaunuieveniment.
Esteafișatșiutilizatorulcareafăcutmodificareașidatalacareaavutlocmodificarea.
Figura3.13: Paginacuistoriculmodificărilor
3.6.10Paginaaranjareinvitați
Aceastaesteceamaiimportantăpaginăaaplicațieideoareceaceastaestepaginapecareovaac-
cesautilizatorulfinal,adicăclientulunuirestaurantcaredoreștesăîșiaranjezeinvitațiiîncadrul
unui eveniment pe care îl va susține la unul din restaurantele înregistrate pe această aplicație.
Clientulîșivaadăugalistacuinvitațipecareîivaaranjalameselecreatedecătrerestaurant. El
poateapoidescărcaprintr-unsimpluclicklistelecuinvitațiîntreiformatediferite,respectivo
listăcuuntabelcareconțineinvitațiiînordinealfabeticășimasalacareesterepartizatfiecare
invitat, o listă care conține fiecare masă cu invitații de la acea masă pe o pagină separată, și o
listăcuuntabelcareconținemeseleînordinealfabeticăcuinvitațiidelamasarespectivă. Orice
modificareainvitațilorlamesepoatefifăcutăcudoarcătevaclickuri,iarapoilistelepotfides-
cărcatedinnoucunoileinformații. Pentruevenimentulcreat, amadăugat14invitați, dincare
12i-amașezatlamasă,dupăcumsepoatevedeaînfigura 3.14. Persoanelecarenuaufostîncă
așezate sunt vizibile în partea stângă. O altă pagină utilă pe care o voi prezenta în următoarea
secțiuneestepaginaculistainvitațilorînordinealfabeticăpentruunanumiteveniment. Această
paginăpoatefiaccesatăpentruacestevenimentprinapăsareabutonuluidindreaptacunumele
de“Arată-milistacuinvitați”.

3.6. Descrierea paginilor 39
Figura3.14: Aranjareainvitaților
3.6.11Paginaculistainvitațilorpentruuneveniment
În figura3.15se pot observa invitații pe care i-am aranjat la masă în secțiunea precedentă.
Această pagină conține aceleași informații pe care le-am putea afla dacă descărcăm lista cu
invitații în ordine alfabetică. Totuși această pagină este foarte utilă pentru persoanele care vor
așteptainvitațiilaintrareaînsalăînziuaevenimentuluișiîivorconducelamese. Înlocsăcaute
numele unei persoane într-o listă printată care poate conține chiar câteva sute de persoane, în
aceastăpaginăcăutareasepoatefaceîncâtevasecunde. Înplus,dupăcumsevedeînfigura 3.16
numeledupă carefiltrăm poatesă fiescris culitere miciși sănu conținădiacritice șiaplicația
totvagăsipersoanarespectivă. Unaltlucruutillacăutareaînaceastăpaginăestefaptulcănu
avem nevoie să știm care este numele de familie și care este prenumele unei persoane, pentru
că o căutare după Groza Dănuț are aceleași rezultate ca și o căutare după Dănuț Groza. Acest
lucruesteutilîncazulpersoanelorpentrucarenusepotdistingeușornumeledeprenume,astfel
încazullistelorprintatesuntnecesaredouăcăutari.
3.6.12Paginiledeprofil
Utilizatorul poate accesa pagina de profil unde va găsi informațiile referitoare la propriul cont
pecarelepoatemodifica. Înpaginadeprofilgeneralăvaputeamodificanumeleșinumărulde

40 Capitolul 3. Prezentarea proiectului
Figura3.15: Listainvitațilorpentruuneveniment
Figura3.16: Căutareaunuiinvitat

3.7. Testarea aplicației cu un eveniment real 41
telefon, iar în cazul în care este angajat în mai multe restaurante, va putea selecta restaurantul
activ. Înpaginadesecuritateutilizatorulîșivaputeamodificaparola.
Figura3.17: Paginadeprofilgenerală
Figura3.18: Paginacusetăridesecuritate
3.7Testareaaplicațieicuunevenimentreal
Aplicațiaafosttestatăîntr-uncadrureal,fiindfolosităpentruaranjareainvitațilorîncadrulunui
eveniment cu scopul de a afla o părere reală despre utilitatea aplicației. Clientul care a testat
ocupamasa.roaavutunnumărde50deinvitațilaevenimentșiunnumărde5mesecu10locuri
fiecare. Restaurantul la care a avut loc evenimentul nu a fost înregistrat pe website, așadar
clientulaconfiguratșiaranjareameselorînsală. Dupăfolosireaaplicațieiclientulacompletat
unchestionaralecăruirezultatesuntafișateîncontinuare. Răspunsurileclientuluisuntmarcate
cuun“(R)”îndreptulopțiuniiselectate.
1.V-afostaplicațiaocupamasa.rofolositoare?

42 Capitolul 3. Prezentarea proiectului
•Da(R)
•Nu
•Unelepărțida
•M-așfidescurcatșifără,darnuafostoexperiențăneplăcută
2.Credețicăaceastăaplicațiearputeafifolositoarealtorpersoane?
•Da(R)
•Nu
•Poate
•Da,incazulîncarelaevenimentparticipăpesteosutădepersoane
3.Cuma-țievaluavitezaaplicației?
•Destulderapidă
•Nuamobservatproblemedeviteză
•Uneori înceată, dar în general satisfăcătoare (R)
•Destuldelentă
4.Carecredețicăesteceamaifolositoareparteaaplicației?
•Aranjareainvitațilorfărăanecesitadesenepehârtie
•Descărcarearapidăalistelorcuinvitațiiîndiferiteformate
•Căutarearapidăînlistacuinvitați
•Modificarea ușoară a invitaților după ce au fost deja aranjați la mese (R)
5.Credețicăofuncționalitatedearanjareautomatăaleatorieainvitațilorlameseprintr-un
clickarfiutilă?
•Da
•Nu(R)
•Da,darnualeatorie,dacăașputeaspecificaanumiteregulidearanjare
6.Ațifolosiocupamasa.rodinnou?
•Da(R)

3.7. Testarea aplicației cu un eveniment real 43
•Nu
•Nucredcăașaveanevoie
•Da,dacaașaveaunevenimentcupersoanenumeroase
7.Afostaplicațiaintuitivășiușordefolosit?
•Oricinearputeasăofolosească
•A fost ușor de folosit (R)
•M-amdescurcatpuținmaigreulaînceput
8.Oimpresiegeneralăasupraaplicației.
•Este o aplicație interesantă, folositoare, pe care aș utiliza-o și la următorul eve-
niment mai mare pe care îl voi avea.

45
4 Concluzii
Dupăcumamobservatînprimelecapitole,dezvoltareaacesteiaplicațiiaapărutdelaonecesitate
realădeaaveaunmecanismeficientprincareserezolvăproblemeledearanjareșigestionarea
unuinumărmaredepersoane. Înprimelecapitoleamprezentattehnologiilefolositeîndezvol-
tareaaplicației,acestetehnologiiaufăcutposibilădezvoltareauneiaplicațiidinamicecarearată
informații diferite în funcție de utilizatorul care o accesează, și ascunde informațiile care nu
sunt folositoare utilizatorului. Aplicația rulează pe un server care conține partea de backend a
acesteiașiobazădedatecareconținetoateinformațiilenecesaredesprerestauranteleșiutiliza-
toriiînregistrați,despreconfigurațiasălilorșievenimentelecreate,și,nuînultimulrând,despre
invitațiifiecăruievenimentșilocațiaacestoralamese.
Înparteaadouaalucrăriiamvorbitdespreaplicațiapropriu-zisășiimplementareaacesteia.
Am adăugat și o scurtă prezentare asupra calculelor realizate pentru a genera dinamic imagi-
neameselorculocațiafiecăreimeseșiafiecăruiscaunîncadrulimaginiiSVG.Totînaceastă
parte am prezentat și partea de frontend a aplicației, având o scurtă descriere a fiecărei pagini
dincadrulwebsite-uluișiampututobservafaptulcăunelepaginisuntascunsecompletpentru
anumițiutilizatori, sauunelepaginifuncționeazăcaopuntedelegăturăîntrealtedouăpagini,
fărăaaveaunconținutnecesardesinestătător.
La sfârșitul lucrării au fost prezentate rezultatele folosirii aplicației ocupamasa.ro într-un
cadru real. Rezultatele obținute au fost în general pozitive, lucru care demonstrează utilitatea
aplicației,însă,caoricealtăaplicație,existăîntotdeaunalucruricarepotfiîmbunătățite.
Într-o lume ideală, modul cel mai eficient de utilizare al aplicației este înregistrarea res-
taurantelor pe website, care își vor crea configurații pentru săli, din care clienții pot alege o
configurație,fiindapoinecesarădoaradăugareainvitațilorșiaranjareaacestoralamese. Desi-
gur am observat că în realitate nu se întamplă acest lucru întotdeauna, fiind necesar ca uneori
clientulsăîșicreezeșiconfigurațiasălii.

47
Bibliografie
[1] ACID.url: https://en.wikipedia.org/wiki/ACID .Consultatla16.05.2018.
[2] Apache Wicket . url: https://en.wikipedia.org/wiki/Apache_Wicket . Consultat
la16.05.2018.
[3] Bootstrap. url: https : / / en . wikipedia . org / wiki / Bootstrap _ (front – end _
framework) .Consultatla25.05.2018.
[4]James Gosling; Bill Joy; Guy Steele; Gilad Bracha; Alex Buckley. The Java Language
Specification . 2014. url: https : / / docs . oracle . com / javase / specs / jls / se8 /
jls8.pdf.
[5] Dividing points StackOverflow . url: https : / / stackoverflow . com / questions /
18610350/android- dividing- circle- into- n- equal- parts- and- know- the-
coordinates-of-each-divi .Consultatla05.06.2018.
[6] Enterprise Java Beans . url: https://www.tutorialspoint.com/ejb/ejb_quick_
guide.htm .Consultatla05.05.2018.
[7] Git.url: https://en.wikipedia.org/wiki/Git .Consultatla26.05.2018.
[8] Gradle.url: https://en.wikipedia.org/wiki/Gradle .Consultatla26.05.2018.
[9] Hibernate. url: https : / / en . wikipedia . org / wiki / Hibernate _ (framework) .
Consultatla16.05.2018.
[10] Java Persistence API .url: https://en.wikipedia.org/wiki/Java_Persistence_
API.Consultatla05.05.2018.
[11] Java Persistence Query Language . url: https : / / en . wikipedia . org / wiki / Java _
Persistence_Query_Language .Consultatla05.05.2018.
[12] Java Platform, Enterprise Edition . url: https : / / en . wikipedia . org / wiki / Java _
Platform,_Enterprise_Edition .Consultatla13.04.2018.
[13] Java (programming language) . url: https : / / en . wikipedia . org / wiki / Java _
(programming_language) .Consultatla13.04.2018.
[14] Listă cu servere de aplicație . url: https : / / en . wikipedia . org / wiki / List _ of _
application_servers#Java .Consultatla16.05.2018.

48 Bibliografie
[15] Mathematics StackExchange .url: https://math.stackexchange.com/questions/
2438719/is- there- a- formula- for- the- big- radius- of- an- evenly- spaced-
ring-of-circles?rq=1 .Consultatla04.06.2018.
[16] PostgreSQL . url: https : / / en . wikipedia . org / wiki / PostgreSQL . Consultat la
16.05.2018.
[17] Stateful EJB .url: https://www.tutorialspoint.com/ejb/ejb_stateful_beans.
htm.Consultatla05.05.2018.
[18] Stateless EJB . url: https : / / www . tutorialspoint . com / ejb / ejb _ stateless _
beans.htm .Consultatla05.05.2018.
[19] SVG.js.url: http://svgjs.com/ .Consultatla26.05.2018.
[20] The Java EE 6 Tutorial .url: https://docs.oracle.com/javaee/6/tutorial/doc/
bnbyl.html .Consultatla05.05.2018.
[21] WildFly.url: https://en.wikipedia.org/wiki/WildFly .Consultatla16.05.2018.

49
Listă de abrevieri
JEE(sau) JavaEE JavaEnterprise Edition
HTML Hyper TextMarkup Language
CSS Cascading StyleSheet
SVG Scalable Vector Graphics
WAR WebApplication Resource(sau) Webapplication ARchive
EJB Enterprise JavaBeans
API Application Programming Interface
JPA JavaPersistence API
SQL Structured Query Language
JPQL JavaPersistence Query Language
GUI Graphical UserInterface
HTTP HypertextTransfer Protocol
XHTML EXtensible Hyper TextMarkup Language

51
Listă de figuri
3.1 Structurabazeidedate . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 22
3.2 Structurapaginilor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 24
3.3 Paginapentrucreareaunuicont . . . . . . . . . . . . . . . . . . . . . . . . . . 30
3.4 Paginadelogin . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30
3.5 Paginapentrucreareauneicompanii . . . . . . . . . . . . . . . . . . . . . . . 31
3.6 Paginapentrucreareaunuirestaurant . . . . . . . . . . . . . . . . . . . . . . . 32
3.7 Paginaangajaților . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
3.8 Paginarolurilor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34
3.9 Paginapentruconfigurațiasălilor . . . . . . . . . . . . . . . . . . . . . . . . . 35
3.10 Exemplurealdesală . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 36
3.11 Paginaevenimentelor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 37
3.12 Creareaunuieveniment . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 37
3.13 Paginacuistoriculmodificărilor . . . . . . . . . . . . . . . . . . . . . . . . . 38
3.14 Aranjareainvitaților . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39
3.15 Listainvitațilorpentruuneveniment . . . . . . . . . . . . . . . . . . . . . . . 40
3.16 Căutareaunuiinvitat . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 40
3.17 Paginadeprofilgenerală . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 41
3.18 Paginacusetăridesecuritate . . . . . . . . . . . . . . . . . . . . . . . . . . . 41

Similar Posts