From 1cc4abc24eb82e129c6599d025b70713cf8853b3 Mon Sep 17 00:00:00 2001 From: Florian THIERRY Date: Tue, 10 Sep 2024 09:40:45 +0200 Subject: [PATCH] Add default picture and factorization of title in publication edition. --- frontend/src/app/app.routes.ts | 4 + .../publication-edition.component.html | 9 ++- .../publication-edition.component.ts | 2 + .../publications/publication.rest-service.ts | 4 + .../publication-creation.component.html | 1 + .../publication-creation.component.scss | 0 .../publication-creation.component.ts | 76 ++++++++++++++++++ .../publication-creation.routes.ts | 7 ++ .../publication-update.component.html | 2 +- .../src/assets/images/default-picture.png | Bin 0 -> 5937 bytes 10 files changed, 102 insertions(+), 3 deletions(-) create mode 100644 frontend/src/app/pages/publication-creation/publication-creation.component.html create mode 100644 frontend/src/app/pages/publication-creation/publication-creation.component.scss create mode 100644 frontend/src/app/pages/publication-creation/publication-creation.component.ts create mode 100644 frontend/src/app/pages/publication-creation/publication-creation.routes.ts create mode 100644 frontend/src/assets/images/default-picture.png diff --git a/frontend/src/app/app.routes.ts b/frontend/src/app/app.routes.ts index 1010752..631dc29 100644 --- a/frontend/src/app/app.routes.ts +++ b/frontend/src/app/app.routes.ts @@ -13,6 +13,10 @@ export const routes: Routes = [ path: 'disconnect', loadComponent: () => import('./pages/disconnection/disconnection.component').then(module => module.DisconnectionComponent) }, + { + path: 'publications/new', + loadChildren: () => import('./pages/publication-creation/publication-creation.routes').then(module => module.ROUTES) + }, { path: 'publications/:publicationId', loadComponent: () => import('./pages/publication/publication.component').then(module => module.PublicationComponent) diff --git a/frontend/src/app/components/publication-edition/publication-edition.component.html b/frontend/src/app/components/publication-edition/publication-edition.component.html index 990332a..e4e2e01 100644 --- a/frontend/src/app/components/publication-edition/publication-edition.component.html +++ b/frontend/src/app/components/publication-edition/publication-edition.component.html @@ -1,6 +1,6 @@
-

Modification de l'article {{ publication.title }}

+

{{title}}

@@ -19,7 +19,12 @@
- + @if (publication.illustrationId.length) { + + } @else { + + } +
diff --git a/frontend/src/app/components/publication-edition/publication-edition.component.ts b/frontend/src/app/components/publication-edition/publication-edition.component.ts index b20fb6f..af690d4 100644 --- a/frontend/src/app/components/publication-edition/publication-edition.component.ts +++ b/frontend/src/app/components/publication-edition/publication-edition.component.ts @@ -36,6 +36,8 @@ export class PublicationEditionComponent implements OnChanges, OnDestroy { @Input() publication!: Publication; @Input() + title!: string; + @Input() isSaving$: Observable = of(false); @Output() publicationSave = new EventEmitter(); diff --git a/frontend/src/app/core/rest-services/publications/publication.rest-service.ts b/frontend/src/app/core/rest-services/publications/publication.rest-service.ts index 8c47858..91e94ec 100644 --- a/frontend/src/app/core/rest-services/publications/publication.rest-service.ts +++ b/frontend/src/app/core/rest-services/publications/publication.rest-service.ts @@ -17,6 +17,10 @@ export class PublicationRestService { return lastValueFrom(this.httpClient.get(`/api/publications/${publicationId}`)); } + create(publication: Publication): Promise { + return lastValueFrom(this.httpClient.post('/api/publications', publication)); + } + update(publication: Publication): Promise { return lastValueFrom(this.httpClient.put(`/api/publications/${publication.id}`, publication)); } diff --git a/frontend/src/app/pages/publication-creation/publication-creation.component.html b/frontend/src/app/pages/publication-creation/publication-creation.component.html new file mode 100644 index 0000000..18365be --- /dev/null +++ b/frontend/src/app/pages/publication-creation/publication-creation.component.html @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/frontend/src/app/pages/publication-creation/publication-creation.component.scss b/frontend/src/app/pages/publication-creation/publication-creation.component.scss new file mode 100644 index 0000000..e69de29 diff --git a/frontend/src/app/pages/publication-creation/publication-creation.component.ts b/frontend/src/app/pages/publication-creation/publication-creation.component.ts new file mode 100644 index 0000000..b0deeb2 --- /dev/null +++ b/frontend/src/app/pages/publication-creation/publication-creation.component.ts @@ -0,0 +1,76 @@ +import { Component, inject, OnInit } from "@angular/core"; +import { PublicationEditionComponent } from "../../components/publication-edition/publication-edition.component"; +import { PublicationRestService } from "../../core/rest-services/publications/publication.rest-service"; +import { ActivatedRoute, Router } from "@angular/router"; +import { MatSnackBar } from "@angular/material/snack-bar"; +import { BehaviorSubject, Observable, Subscription } from "rxjs"; +import { Publication } from "../../core/rest-services/publications/model/publication"; +import { AuthenticationService } from "../../core/service/authentication.service"; +import { Author } from "../../core/rest-services/publications/model/author"; +import { CommonModule } from "@angular/common"; + +@Component({ + selector: 'app-publication-creation', + standalone: true, + templateUrl: './publication-creation.component.html', + styleUrl: './publication-creation.component.scss', + imports: [ + CommonModule, + PublicationEditionComponent + ] +}) +export class PublicationCreationComponent implements OnInit { + private readonly authenticationService = inject(AuthenticationService); + private readonly publicationRestService = inject(PublicationRestService); + private readonly router = inject(Router); + private readonly snackBar = inject(MatSnackBar); + private isSavingSubject = new BehaviorSubject(false); + private subscriptions: Subscription[] = []; + publication!: Publication; + + get isSaving$(): Observable { + return this.isSavingSubject.asObservable(); + } + + ngOnInit(): void { + const authenticatedUser = this.authenticationService.getAuthenticatedUser(); + if (authenticatedUser) { + const author: Author = { + id: authenticatedUser.id, + name: authenticatedUser.pseudo, + image: authenticatedUser.photoId ?? '' + }; + this.publication = { + id: '', + key: '', + title: '', + text: '', + parsedText: '', + description: '', + creationDate: new Date(), + illustrationId: '', + categoryId: '', + author + }; + } + } + + ngOnDestroy(): void { + this.subscriptions.forEach(subscription => subscription?.unsubscribe()); + } + + onPublicationSave(publication: Publication): void { + this.isSavingSubject.next(true); + this.publicationRestService.create(publication) + .then(() => { + this.snackBar.open('Publication created succesfully!', 'Close', { duration: 5000 }); + this.router.navigate(['/my-publications']); + }) + .catch(error => { + const errorMessage = 'An error occured while saving new publication.'; + console.error(errorMessage, error); + this.snackBar.open(errorMessage, 'Close', { duration: 5000 }); + }) + .finally(() => this.isSavingSubject.next(false)); + } +} \ No newline at end of file diff --git a/frontend/src/app/pages/publication-creation/publication-creation.routes.ts b/frontend/src/app/pages/publication-creation/publication-creation.routes.ts new file mode 100644 index 0000000..5df6af3 --- /dev/null +++ b/frontend/src/app/pages/publication-creation/publication-creation.routes.ts @@ -0,0 +1,7 @@ +import { Route } from "@angular/router"; +import { authenticationGuard } from "../../core/guard/authentication.guard"; +import { PublicationCreationComponent } from "./publication-creation.component"; + +export const ROUTES: Route[] = [ + { path: '', component: PublicationCreationComponent, canActivate: [authenticationGuard] } +] \ No newline at end of file diff --git a/frontend/src/app/pages/publication-update/publication-update.component.html b/frontend/src/app/pages/publication-update/publication-update.component.html index b690b72..f6f275d 100644 --- a/frontend/src/app/pages/publication-update/publication-update.component.html +++ b/frontend/src/app/pages/publication-update/publication-update.component.html @@ -3,7 +3,7 @@ } @else { @if (publication) { - + } @else {
diff --git a/frontend/src/assets/images/default-picture.png b/frontend/src/assets/images/default-picture.png new file mode 100644 index 0000000000000000000000000000000000000000..5f313f005da49580a44e1177ab60b9af3ae06da8 GIT binary patch literal 5937 zcmd^DX;hO}8vX(b4rQ$rAVNI1!WNwP#Bg*QN+rkEJ0;62m!+q%2-iEwki}H zs4!L(MwBRv0TLvvfdphH8xq2vpv4l9ZSKWwwCBt@^J{*XbME2Z_kG^wdET3k4=#W2 zbU;DwD>(!~6zmRKA3~7T9Jtm<1B=o`KdO9kF|C6 zGCR6k+B%-rH?capYa5yyTUgxZLp^L>FNaU1H}D39^$ccrKewZo-POnG;|_H8aX8P1 znpw|=$3--dL^#^Z9eCE=_pGPCp@r4W<}unjI(ymuyyrZ@Fkdj-)z2Lq9^(uMTAy{* z)Hij2?uJI_O)a&Jj9xCkv9+zPxz&awzXw6qjoVpUxkPwO(hN}uB47LKoNJY-%!QiO zK(EjDWBK_~hs;-f*7RxepVBv@gg@x8M%$j8o!_|Uv7_wW)2S|p@1>+|W07q0^Vu9_T5;@Eq9%8V0|Zo41x2n4E|X&Oc5Y z5`?7Krfm z8?@MFjx-b6eX)nUL*qeIZr90n+ji1KevvXOYX>@{-S@i5PLoP$)A%CQ1A-l@57PfQ z2+n+5}W=||21>YjN9G~G?cSk-}Tn?gIStw=K_ zv2l?L4G31|qzsyG&N<1o{hG8`DIJ`zOf!m&XW0FWib#*8UD_cPk`h}}n)D^IJyNM9 z525{&K^!oXL!z2xy)dtpOjxo5x)+rEW#*8Lwo@p~w2FV;6e-d|iVuFUqgFZPjgWko z$hqLbqkM0(%CJD>71%L7{U{;em0dGQPCesY^K( zHyXG756mXRmm^CUyX0Md)I&-$Y%`X5OLogm2N%T%&*L*n(*+xqlF53{9$}3K4zG_4 z@LrWkZP8J}8hfQ}t!^-B( zrn$LO#O&B|u0GQhyZM|feesn)K4ba3afM0JJ(x#S_q!hP=1xq1!9~zzb-x3-@zuF? zyOcpqik9R0vp3x3{{b8^VZWF@sl2iY_LIBKQ5=L{8^0AaTa262BZtYSLr7&S&eY@@ z>PrCG%fc&>iw%ti6%&ZWG~%A!Nmh`>NKZxC#1Z)ffaW<)@68N<_zhiSwvJadSsJzl zg%+0_{Anmf_3OXg@L||ap0K@qvZdDpT`iB_Z;)6MkS2-E@Nu<7HeasmnCw`nzBH>A z_S!{Zy=201vTm4vTLl!G_xXzW?LSoMRZ_|l-9Tr@PIsU(HK$(FQ9ZK-(xo^~cKNv~ zIsh|Y{}gL|GQ;XJFq5-;DV|4#DNwOkI+Bwi4Ovi=t)e^?Z2{KvzPEC=?`~BnpojcW zAzm96Q!~uW5NgAi?Gxyh*LJ&C0e`fnbXJBm)UWu|_hq*&V2GRixZ7PPShJ26e)~IU z`c`JjIA6)?D%Cl~r7Y>Z=?%@$&`POAod#&jns2On#d0T^mq!Z=yZ##&PIV!!{)zN`!EX z?%cgj9XP@Kw6G0{O_%!01t7DX%XIF;N6}y9w%Tfdk_2pPkWpZA(fkhRjC7gyHwt7u zN&YK{qh3AZaqYIqO_Ev<5*uS%vr`|LPgrz=3vZ{UDI*kW0 zzv9^waG;5`<7HJb(DZv*44W(-C$Ep!GGGS&jaV-%uW)S@4Qf>EF#xMwNEs&^-Np(lI^0Gdctx8zJ{ z9gb$71nmFS0EUTIkuD!C0i3$w{3f@}i2b^8z?lS{CGPZ`ouyT!AZ-LpyYh|d34Z6s zSM{uNDkcWO=GBowkDWhu*zs4&9MKl9`?dgN^@F-q@aP@^*Sxl+hXtDfS{YO8AIc_j z4I#0WwCwD1a<=H)`!hMQJU_ATAw2tovd*}P^7ud8cIN=@KftjFU!IOC=@4Qe!7~s* zy)Q^F^1QzJEYNfgXzJnQ5w&l_9e&P6Pta>CytL=THpF%akL<380w#eZW3jAdTdg~+ zU`8tB7XtIJS!ypc^ep%{1c4xv5M;{nOJ_JPTy7Qm9EI%!KvZGVLhehfCv$t@p?57i zvkxf69;a*RIcY5sen5u^j4A@2fzh>0^427X?nPf<$;oD58||Z;3_l zAs1=g?arS1UJ?$!yJk8Q_eF#PqA7@v)=UlSnKA9Gg1^x$l79|!hL4H;V16v1?BhjD zk2@zWo!@&mKmCD}_8L-T7Aeb8`&g1=Z>;egM`}iJ&HJ|mw=7~1OB^&s$RLt92ZG;k zad2C_V!Z^n!7JN4aEn>lHmqR7Vc5vWTdwH6weHRKK=2fS^=50#&EeLHULF>&PMPP3 z`nV$eRNP8}iQo)VZ3)L?QXF1kY$={D!x73DRkHY8syPKibr+L3p+xHZf(S1=l*2CM za`h#ejnPXp5H4APORCBk8Yx6TCHEbi!WQzRD_H!T5Af>A@Cs=>OSA|otiX#2{4fd! zRWULXBbj3h6&uaVB$VKaw*^5452Rv>Voqtm#X^`8FNZ7Occg<}YuMyBZVYf!+##cq z|6(eBV$P%HpjP@%o%hoQ^fXdHf@-Zspn~iWATlM3C%_^g*?b&_t52{L2W8C1{J)_n z*uWwJn~g!iX7{dv-D<6Z-6~1Jc4c9^lK7Q=tybW=D{!sG#U)5?Y4PS}z=ojk>mgy41NpY0qtSfI|%V@*jotE`9o$1 znQHow8A8lIWd5|ch5i2)x>d3~*=c3J-%8o0UAK;uwh*=DOq=DwRoF&{HT!;J-Yj44 zO890pD?F6BUUN!DTO57s(e965b>TbQU{L7F>n?od{f|ZGw%2`Rc;h@*wmZQTJPAHo zgW}OY8-3UowoeanmgCC#^#^C0O2b|$WR{4`WuCg0YUBsgaHY|7%U)mh{;Nu6(OKT; zN}rk^UMZOP)m%`C_p^1oYNUnGP*K4aM|&I9d)hizJVuww z@_tmaBcx25v-a?EpBvmd(V}r|WM|0QdBunuWi-`!#o089*W@WaimOAQ<@d(Y&WTA! zCii+Z2O211kr$iFXp#bC_T~=*F)m0;{onBz2U`5!@%bld>4vvBzWO0q%Qb}sQs~!u zva7dwU0=?bCOaHFa9YQtI$@(tbe(A9Ob9hXT;3c z@#@3XnvCad@#5jg<;K=n+Jc^XUGb)7sT&!6TbPs`^62{|R#8_6N!bAkiSav>GG7PC zWvBZi29#`(SEV>lfp$JMX<*DO3w0hdAAn4Joh2n7%q%g9(XtLDiJ#voN_;tsd-RuM z9>rvx`uwu}M)DEV3o((I7Y%}(JkO(ET+%SHMjYwC>)_?kk{AYF6{;b&kiLBJ0ET5CX3;Z|t alh2D>*)#PCt9{&{-Ok3z`u;wzAO8&nvQ(h} literal 0 HcmV?d00001