From fb71b0b3a157940f92f22227fe8fa97ae0bb67e7 Mon Sep 17 00:00:00 2001 From: Alexandre Date: Tue, 12 Dec 2023 11:04:57 +0100 Subject: [PATCH 01/44] j'ai rien compris --- backend/package-lock.json | 72 +++++++++++++++++++++++++++++++++++++++ backend/package.json | 2 ++ backend/src/app.js | 46 +++++++++++++++++-------- 3 files changed, 106 insertions(+), 14 deletions(-) diff --git a/backend/package-lock.json b/backend/package-lock.json index 996593d..b158b4d 100644 --- a/backend/package-lock.json +++ b/backend/package-lock.json @@ -5,6 +5,8 @@ "packages": { "": { "dependencies": { + "cookie-parser": "^1.4.6", + "cors": "^2.8.5", "dotenv": "^16.3.1", "express": "^4.18.2", "mysql2": "^3.5.2" @@ -2192,6 +2194,26 @@ "node": ">= 0.6" } }, + "node_modules/cookie-parser": { + "version": "1.4.6", + "resolved": "https://registry.npmjs.org/cookie-parser/-/cookie-parser-1.4.6.tgz", + "integrity": "sha512-z3IzaNjdwUC2olLIB5/ITd0/setiaFMLYiZJle7xg5Fe9KWAceil7xszYfHHBtDFYLSgJduS2Ty0P1uJdPDJeA==", + "dependencies": { + "cookie": "0.4.1", + "cookie-signature": "1.0.6" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/cookie-parser/node_modules/cookie": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.1.tgz", + "integrity": "sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA==", + "engines": { + "node": ">= 0.6" + } + }, "node_modules/cookie-signature": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", @@ -2203,6 +2225,18 @@ "integrity": "sha512-LDx6oHrK+PhzLKJU9j5S7/Y3jM/mUHvD/DeI1WQmJn652iPC5Y4TBzC9l+5OMOXlyTTA+SmVUPm0HQUwpD5Jqw==", "dev": true }, + "node_modules/cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "dependencies": { + "object-assign": "^4", + "vary": "^1" + }, + "engines": { + "node": ">= 0.10" + } + }, "node_modules/create-jest": { "version": "29.7.0", "resolved": "https://registry.npmjs.org/create-jest/-/create-jest-29.7.0.tgz", @@ -5375,6 +5409,14 @@ "node": ">=8" } }, + "node_modules/object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/object-inspect": { "version": "1.13.1", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz", @@ -8774,6 +8816,22 @@ "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.5.0.tgz", "integrity": "sha512-YZ3GUyn/o8gfKJlnlX7g7xq4gyO6OSuhGPKaaGssGB2qgDUS0gPgtTvoyZLTt9Ab6dC4hfc9dV5arkvc/OCmrw==" }, + "cookie-parser": { + "version": "1.4.6", + "resolved": "https://registry.npmjs.org/cookie-parser/-/cookie-parser-1.4.6.tgz", + "integrity": "sha512-z3IzaNjdwUC2olLIB5/ITd0/setiaFMLYiZJle7xg5Fe9KWAceil7xszYfHHBtDFYLSgJduS2Ty0P1uJdPDJeA==", + "requires": { + "cookie": "0.4.1", + "cookie-signature": "1.0.6" + }, + "dependencies": { + "cookie": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.1.tgz", + "integrity": "sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA==" + } + } + }, "cookie-signature": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", @@ -8785,6 +8843,15 @@ "integrity": "sha512-LDx6oHrK+PhzLKJU9j5S7/Y3jM/mUHvD/DeI1WQmJn652iPC5Y4TBzC9l+5OMOXlyTTA+SmVUPm0HQUwpD5Jqw==", "dev": true }, + "cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "requires": { + "object-assign": "^4", + "vary": "^1" + } + }, "create-jest": { "version": "29.7.0", "resolved": "https://registry.npmjs.org/create-jest/-/create-jest-29.7.0.tgz", @@ -11120,6 +11187,11 @@ "path-key": "^3.0.0" } }, + "object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==" + }, "object-inspect": { "version": "1.13.1", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz", diff --git a/backend/package.json b/backend/package.json index 292e378..830b576 100644 --- a/backend/package.json +++ b/backend/package.json @@ -8,6 +8,8 @@ "test": "jest" }, "dependencies": { + "cookie-parser": "^1.4.6", + "cors": "^2.8.5", "dotenv": "^16.3.1", "express": "^4.18.2", "mysql2": "^3.5.2" diff --git a/backend/src/app.js b/backend/src/app.js index 22be9ab..b2c59ed 100644 --- a/backend/src/app.js +++ b/backend/src/app.js @@ -3,6 +3,26 @@ const express = require("express"); const app = express(); +const cors = require("cors"); + +app.use( + cors({ + origin: [ + process.env.FRONTEND_URL, // keep this one, after checking the value in `backend/.env` + "http://mysite.com", + "http://another-domain.com", + ], + }) +); +app.use(express.json()); + +const cookieParser = require("cookie-parser"); + +app.use(cookieParser()); + +const router = require("./router"); + +app.use("/api", router); // Configure it @@ -25,19 +45,17 @@ const app = express(); // 4. Be sure to only have URLs in the array with domains from which you want to allow requests. // For example: ["http://mysite.com", "http://another-domain.com"] -/* -const cors = require("cors"); +// const cors = require("cors"); -app.use( - cors({ - origin: [ - process.env.FRONTEND_URL, // keep this one, after checking the value in `backend/.env` - "http://mysite.com", - "http://another-domain.com", - ] - }) -); -*/ +// app.use( +// cors({ +// origin: [ +// process.env.FRONTEND_URL, // keep this one, after checking the value in `backend/.env` +// "http://mysite.com", +// "http://another-domain.com", +// ], +// }) +// ); /* ************************************************************************* */ @@ -85,10 +103,10 @@ app.use( /* ************************************************************************* */ // Import the API routes from the router module -const router = require("./router"); +// const router = require("./router"); // Mount the API routes under the "/api" endpoint -app.use("/api", router); +// app.use("/api", router); /* ************************************************************************* */ From 2bef70d94d0a348f75be36a5b8cf3b1486a2481e Mon Sep 17 00:00:00 2001 From: Alexandre Date: Tue, 12 Dec 2023 11:30:03 +0100 Subject: [PATCH 02/44] cest nul --- backend/public/assets/images/favicon.png | Bin 7120 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 backend/public/assets/images/favicon.png diff --git a/backend/public/assets/images/favicon.png b/backend/public/assets/images/favicon.png deleted file mode 100644 index 184eb511378913962fbba2d21016dcf58b289979..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 7120 zcmZ{p2T)VZx4=Vh0>OY(=}iQZfDnqI_g)1Hy@oD?-a|*}B3*h59aNBB1(h14N(Tj` z2C33szW=5N zmB1-N2YGFI0H7g>;>wB$*T(ZQP*nibjk0RY|* z0N}SJ03ekK0ML8nw(38|8HlYlRh0m@|2zd9ADyl2V z8~M%u%=7ol8}PoB6+H-q?NzzXiG2JS+}B2lho6ZWx!bFwi2)!mdfAxMjFP=HqHH3y zCYtQh2YYE7>WY(*0IN8T>OvR$hJ>D;j{x^nyXTjl-pyy7ULm2w=|VpmkvxkJvyLw_ z*p_`i9%M;+{mK>P8c-+45l%S2AOLbrEY6*5c3FC|}9? zW+}?YT&_)bB^stLz6XpG2DPl5LVwx}6RyB7lu0uXQfJdE1ET|H!h`4K9QK^CqGiQ0 zB0=(%I&VTie21hu9t4GJzF0We?hH?PygSTWdXWlJ;+^f`;WwoTd;i=}~YTR{POmH5V zXEVhFU7WxRNn+!X!Oc)_#d#VKFOLK58 z1G-m>$Ku}S;5n}``XsD*RTL;dHNJ=x-aePL#yD`?WpJK9B9xbw_E7Mp5x(YWn0BlE z%ZMiy@K>b+|1nMbr8{AYfz;XJ>zP36&gRpk*dRa@b~8;UD9!J3k5IGhn-KZI_5|B6 z6&{6y^w5ZzTaeC$oY0qdq20QRVVP@K`-fe6tU4>|_$fa!Uykygx~Fz4FEjbOatUo+ z@BdM|CjS0j^jFI35Tdl!-6WT3YGV1e91kvw0{aU?oxJe|>?K zg6wo1M6%u^=l)<_PX>3&%B3F_PYpCL-5#fKyt?xMaDWX}8tF2naqUb+9vQ|)4hH5* z#uyZM(MCg-luL?2Rjuqel9og^HY3Qp1NV2vTS0TD-Q<|KF^-TaKd*Fp2@d{jOCspA zSi(a?7|^*ZRg%p>@gkAf0?#Z#4_ZYIK4pB}?APx9l|qT#G*SS~;qW6nQv(y%7sjP9dyHr!7_1&L4E( zxt2%&rBt>%aMz1qTI6ul%kiNR_|D{~OYq_3dYUlg$v73dh1fuUXrtv072aMEuaNxM zB@pd-k3ZohYUtyooK}~vHqrKm1zJ_+n)AzkG+vJEsVwF;knjC&*jD%?*3cwu;^09%#S{vxmozGQ)9 z`Gg4u^49V9zOqQdIuGU)wJQ+PRn`meFNtk5(;5}go5z_43DFv{Uble=_wE=8zs_$@ zjCj7IcEWP@M<4&tqLmpDOuyz@1zjRqAJM%jEU+${y2YM?f^4Qz(b)-2N9$XX^a=$l z=VMp247Y^F=dZALGoaTIe@&Z?`SCIn;T4q+xk^AY)>4G z36#3Y3d{22%ugPC-=O1rT(92VM{ZRBSK^L6FjMdQJa1#tV}+NAylY)E{zGIeKr#lA z+Of=z63B^0XGb9Sql|VPkCY1P$ve)Sa_!g@)2WIQ2IR&#Alvet>R{fy7vKJz&2oRZ zlSsOfRacO)T%lertaOFIjU$9(C0cKCG*S)^^K3ckaYN4Uej#?)%IUdPF3CRfD#XEaSt1#q(?8@+Vz(7N3EO4hB-g3wrm z5q@Amn!!oZ%-QfnuRz0jLi3g-_;-F$Jg>clgGuosLG%$%TvjA@RNwjL*~I~z$d=IZ z*^a)Ku+L#f6OAEsiRC9HC-8wPxE){2N~V84`SXn21EW2r1B`yU;(p+=CGv^m$x7^w$2FFDG2P zZ~3Bk$8bl`GdXc{GW!*kG&c&h)bwlTIUpd?JHqugpCp{~qfWm*?l* zzunG`yk6f5wk&I8jr;xfG_iRVu4cv}8Za~^lx z-0Mz<$?Pr6pYRG=AY~S{cZ}3)roA`k4PUxb%qhnb15wx%M^UsVFS?#7x4@V}2e>_J zquoJ6#-Z41Af9Y4HWN*_X%Ss(78U=7O&f`x(cy*Vw!H_1nNs}PTb8SK-AGfH4pge7 z6wdE5n`|sjMfO5Zl2&Pr3Nw~1y?xi6xpEpb;mYY#@7y+6|dJ8nLTsx#%5k1kUr&+lOtCFYHd z6V$>rMVJ7_RyA2VxOrX`Y-4qp8-(x}LJr_IJd3I>AAu2%x)S>5^#;;*Zzbi87N0$g zbnW`Mf3O~#%;mZbh>XWs_Q=uM1a^}yw9W-vAp8cO;m(ZY>$+lxx`@t?J*^b|pYc>) zE74=>p-u6s9DsHD)LpVq+-+jkm3jA z_*x;_&y(R}9IgjNPA0`pZ|6heHQSdGxn;!h9~nB znc=n|4*>_R$|bIx5|9#6?}|$G{E&S#Pb(y5N$Ipb?EU_Gw{$(SfO*EOgitn2J7q2~ z;5VZ92Zez?Zhl-2?Y~Dyk{22cDF+QS^!S%1@AF>aN*I(L7af&19#J+PZTKcZr);3# zc4weD!jr4QG9|CaEt$h13!`W13fo>)AiR733H?DJ8KO#7A>Ke-yJVHl?|^X&f%@&g zrED_SnShUZmh{MdZ0hCbp7X?4Q_O?RTN+P;|4!Exw2_IODHvgGNtM`vjEpafqp&GU z_8Z;IYU@=#VgcB`5;m1a=DF+K`zm_^xkMTAwr|XRz|p(GWXzKzafF1W13adL<_jzn zd)EcDCF_}Hy2VmwMVr;CQ-Vzj44Qt>DvfOM9{>&CG|DhG%`0fIiJ0cN=FJ^)zSr++ zrUQlxVP2AG+Gl~nDV`De8msy2rT9dgYR>QwT~NT0=l9o5HU4wU?cc<%Xz#jyym=e( zyk-nO;cwf;U>&LlqJK*5irttv8+c`d+rKD_HUz_ADpHJI6H*D8i5wLCcCbSDSYM&* zR(9z$rXrK9uxJ4(n5SedG~UTPc}3z_(+qvSERBf~6t@?92@Tj*jY0O>jTnEU+E|&+ z{qD^$AGb;fs{IqLdwH{-f52X4zkG`mI6UBWT- zN{L#2kX36(XKNPspCl5h{1u-rL^MvDju;$QhQ1X&!dho`faQv$XY{*#@KZ8(ZjWpf z5Uv!-#Eoq`KW0*FlNN#0t`T~1@Y1*1QK=6qPy(cMY*4;|*{s~eAD#{3TauP}&nE2K zKHV3ajPcs~b{<()+w&ADc89M(#%OBfM-2?NnfPL{dZD*O(@Km#7+9Lx*XdG28%%P4 z?Y^2tm_pk$tvBk_V~P)uM!f#CD1oF599h};1Wb_1CeS$A@`+x)MbMX}GyocyA7iVV z=+Jfd&3xV1P0Sljb{C?s-*}7{@Gu#xFgUYcgVx8nhUJq>)mxE16<&uX7c^z7mYHa~ zOSH=~$0d6c-&%(*&L~eN%vtUO;jegmtdZa4*<&sW1gO7#OkxbT#B=&8;LMbv{jH{r zk$ujFGSOCde@8`iVqeA>NWF&Om6wlXE~Q>2W(GWRBNe`I18a2Q-4Shld@ot60vd)pb(wqKA4R~5%k#2eN9sr` zpWB1O#{1C(d*7=(<~Z}L5 zD5#R2hsti5W!=|s`m?hyQTq^un9anVZEic|`uKqOXA^xqbgw6015nEKo1e^i1%vLD z)-t7SlJ*0>Ml)(U=}rC71L-QK>o$|L1kpfDGg_Hz=)K=h)PfYkL4HruXT&DF07KlH z#KM2Ym#$%9p5{Ggr(wh2#z;lqxx*p_axIOAOAHH(+>#;d3>;}QZz4<&;tG-UQs-~x zuxbY2R;H~`-B~h4_C^ZX6VA>rg@C`utpq9LMn46SBL)@OIbSj*B+aGLel;c-ct?*3}b3iVl95(U(=TPX`?dQN1&`JwPO(ir@Jzuu*tw=u! zguK3^@K(1lxj-$)#0PaV4-&Vy1Vfhlg;e)? z27JZ5ZWGS9ZWv?lfSbW-M}_E3+}R;2yJg6&f)Bg?4ATnwvoxv7>Ea)b4?8CuNL&6) z$;Qi;NF%qBdawo`CvbBl;Jw!84z~9xu9q@5o-X`7UBp)xcKGGxJ7!v}&v2ru%Ue|$ zYTtPTx85NIlX-mAMaKP;NvtGOk3wdsI+y#^nt8v4%!U9kT#Yf{^IQevW>Gw!r^wiO z-=SfqZ@vOmNBU;khr0{o#c01HXF|@Fhi;F5&#b@kTuBX$f*pVsh7|cXqd+FPp8)z| z%nm>K#wqH)+IDwP50Tj3mc9P1p48dcv(nN=dhhm4bjG>}V*8~mb^Al&SF3SstlebS zBpS_>X9q&LDdwcY#n)3U53$t z+Zl$ffEaihx7XWPIX?M4g847U{1@(i+oAjp){eukXKWXh{Pu%=L*X?Wc|m(0fr3{{ zdGsM(%>sEM>=$>YC=OD(!m~@`JHRh=rLgzk7}h#igqiy(-vnVV6r|$jE}jpc#&qja zi5*YKZ$IkkZF^AHmab&tQr{&jy7h(su<)SgMq8o&JY?Z8w6e0i^rW4-<8}y!7~bE6 zoG^=Q3;Vyj*4bj@q+2fc(j7MQ-7Ltb3VxIqD%rZ9%PMB~(>GVy~hooPA3S$UFcb(jrZ5CU7cRRHkZ}&X3tMpiUMZ5so#l=LV#f0!bTK=&>?bM2i#M{re_*Vvh8=Nc9V^X z71nxC3QVCr^kSz9BFfCm*SC*bx;MPPT#Qn#klc|Y+5N`1w#i3TxJZRkUM}{-_+r=Y zhrjBC7dfc}*$8nFQdcEP)hn0|%ytcjzdumGosR_a6QzD4Jy2@Zi=DQa)Dq#usDWiY z9>Wk$b9Z;k>#o-=XnixbG14BAcK|9p3w&YX&%7D^XS*Lt%SI~ZjZgm?Sy;+0*)QXd zYzOI~nCG=xj-Am?`^0e{%JAtIplBx5;80mELcArw4e>1A6;W~<_jP#kR_|^A@%HSi zcTJ<6>kIk2?;^xMKuoTj`J$QqGu19&rXEwwjc5L3)g9i)Q@@JbH7YwtK9QX>9nN&W zn$=|c6va?-4Zj+Z?b*E&YW0a4$(8;+VH|-Jdw0(BV>Lm?19dwB(Y|dQNb)V>n z;Xdryy*0pC4sBl+WK97{SOFjL^8qsW8^35gz|oIf`oGIYBgJR^{>aVfPLh>WSsmAv zI5soGt{7G^2ZoY?T-a0O)~}K7Qpt6}P3rgdPf)Q#ZL{K%0 zJ7RIXQ2Z-Nk9&PIN@#jS5Ru_++i*lc)}~W`!NPD8@nF#=KqS>M!*i`AyoQiGRK8?Q zzT;P!ivO8gGhHTrhZ%Tcd#w@X1guVZ=4Y z6(zcWVCqB$MBpIb)Xpklz=RITSAo{l9U31++b;=U^_4!f%NDOY5hP<%FSNvLHO+F|u z&9Qa1F{;PWokn@fb_ur(B_{f$gu7SaK`NUfZLN@YQZ}A;I0X=aKw&~qh!9l52r424 z6_tWWK7>G|Adq1|AnxksUkZL#n~N^NDnD6*w@!r81WB{6C5q4f4 z{$FwamoY)uA|3xhCaXC}aR}qT5N(939n#;!4)C9HNgo_<+_+VEzq>H-)*xt$q zVdL)R1^&Me1BTdI*}x#S5J{-WBMEUaaZxdAD|<<(sLdmoowc`OjH}NP2Hn7A O0H`bLDAg)hqW%X4C2eK^ From c5a99aa2b5165e4eb4cf9bca879e4fb1d36a9984 Mon Sep 17 00:00:00 2001 From: Aurelien Date: Tue, 12 Dec 2023 12:31:05 +0100 Subject: [PATCH 03/44] structure database --- backend/database/schema.sql | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 7b934a6..48368b7 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -84,7 +84,7 @@ CREATE TABLE DROP TABLE IF EXISTS ` En_tendance_serie`; CREATE TABLE - `en_tendance_serie` ( + `En_tendance_serie` ( `user_id` INT NOT NULL, `serie_id` INT NOT NULL, CONSTRAINT FK_En_tendance_Serie_user_id FOREIGN KEY (`user_id`) REFERENCES `User`(`id`), From cad74ff1268c75a9a66f9c5c0f0a94d0df32bcff Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Tue, 12 Dec 2023 13:51:45 +0100 Subject: [PATCH 04/44] working on backend... --- backend/database/client.js | 1 + backend/package-lock.json | 72 ++++++++++++++++++++++++++++++++++++++ backend/package.json | 2 ++ backend/src/app.js | 13 +++---- 4 files changed, 82 insertions(+), 6 deletions(-) diff --git a/backend/database/client.js b/backend/database/client.js index 3a4ad5b..95e3a41 100644 --- a/backend/database/client.js +++ b/backend/database/client.js @@ -1,3 +1,4 @@ +require("dotenv").config(); // Get variables from .env file for database connection const { DB_HOST, DB_PORT, DB_USER, DB_PASSWORD, DB_NAME } = process.env; diff --git a/backend/package-lock.json b/backend/package-lock.json index 996593d..b158b4d 100644 --- a/backend/package-lock.json +++ b/backend/package-lock.json @@ -5,6 +5,8 @@ "packages": { "": { "dependencies": { + "cookie-parser": "^1.4.6", + "cors": "^2.8.5", "dotenv": "^16.3.1", "express": "^4.18.2", "mysql2": "^3.5.2" @@ -2192,6 +2194,26 @@ "node": ">= 0.6" } }, + "node_modules/cookie-parser": { + "version": "1.4.6", + "resolved": "https://registry.npmjs.org/cookie-parser/-/cookie-parser-1.4.6.tgz", + "integrity": "sha512-z3IzaNjdwUC2olLIB5/ITd0/setiaFMLYiZJle7xg5Fe9KWAceil7xszYfHHBtDFYLSgJduS2Ty0P1uJdPDJeA==", + "dependencies": { + "cookie": "0.4.1", + "cookie-signature": "1.0.6" + }, + "engines": { + "node": ">= 0.8.0" + } + }, + "node_modules/cookie-parser/node_modules/cookie": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.1.tgz", + "integrity": "sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA==", + "engines": { + "node": ">= 0.6" + } + }, "node_modules/cookie-signature": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", @@ -2203,6 +2225,18 @@ "integrity": "sha512-LDx6oHrK+PhzLKJU9j5S7/Y3jM/mUHvD/DeI1WQmJn652iPC5Y4TBzC9l+5OMOXlyTTA+SmVUPm0HQUwpD5Jqw==", "dev": true }, + "node_modules/cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "dependencies": { + "object-assign": "^4", + "vary": "^1" + }, + "engines": { + "node": ">= 0.10" + } + }, "node_modules/create-jest": { "version": "29.7.0", "resolved": "https://registry.npmjs.org/create-jest/-/create-jest-29.7.0.tgz", @@ -5375,6 +5409,14 @@ "node": ">=8" } }, + "node_modules/object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/object-inspect": { "version": "1.13.1", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz", @@ -8774,6 +8816,22 @@ "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.5.0.tgz", "integrity": "sha512-YZ3GUyn/o8gfKJlnlX7g7xq4gyO6OSuhGPKaaGssGB2qgDUS0gPgtTvoyZLTt9Ab6dC4hfc9dV5arkvc/OCmrw==" }, + "cookie-parser": { + "version": "1.4.6", + "resolved": "https://registry.npmjs.org/cookie-parser/-/cookie-parser-1.4.6.tgz", + "integrity": "sha512-z3IzaNjdwUC2olLIB5/ITd0/setiaFMLYiZJle7xg5Fe9KWAceil7xszYfHHBtDFYLSgJduS2Ty0P1uJdPDJeA==", + "requires": { + "cookie": "0.4.1", + "cookie-signature": "1.0.6" + }, + "dependencies": { + "cookie": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.1.tgz", + "integrity": "sha512-ZwrFkGJxUR3EIoXtO+yVE69Eb7KlixbaeAWfBQB9vVsNn/o+Yw69gBWSSDK825hQNdN+wF8zELf3dFNl/kxkUA==" + } + } + }, "cookie-signature": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", @@ -8785,6 +8843,15 @@ "integrity": "sha512-LDx6oHrK+PhzLKJU9j5S7/Y3jM/mUHvD/DeI1WQmJn652iPC5Y4TBzC9l+5OMOXlyTTA+SmVUPm0HQUwpD5Jqw==", "dev": true }, + "cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "requires": { + "object-assign": "^4", + "vary": "^1" + } + }, "create-jest": { "version": "29.7.0", "resolved": "https://registry.npmjs.org/create-jest/-/create-jest-29.7.0.tgz", @@ -11120,6 +11187,11 @@ "path-key": "^3.0.0" } }, + "object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==" + }, "object-inspect": { "version": "1.13.1", "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz", diff --git a/backend/package.json b/backend/package.json index 292e378..830b576 100644 --- a/backend/package.json +++ b/backend/package.json @@ -8,6 +8,8 @@ "test": "jest" }, "dependencies": { + "cookie-parser": "^1.4.6", + "cors": "^2.8.5", "dotenv": "^16.3.1", "express": "^4.18.2", "mysql2": "^3.5.2" diff --git a/backend/src/app.js b/backend/src/app.js index 22be9ab..2ac11c4 100644 --- a/backend/src/app.js +++ b/backend/src/app.js @@ -25,8 +25,7 @@ const app = express(); // 4. Be sure to only have URLs in the array with domains from which you want to allow requests. // For example: ["http://mysite.com", "http://another-domain.com"] -/* -const cors = require("cors"); +const cors = require("cors"); // eslint-disable-line app.use( cors({ @@ -34,10 +33,11 @@ app.use( process.env.FRONTEND_URL, // keep this one, after checking the value in `backend/.env` "http://mysite.com", "http://another-domain.com", - ] + "http://wildtube.com", + ], }) ); -*/ +/**/ /* ************************************************************************* */ @@ -54,7 +54,7 @@ app.use( // Uncomment one or more of these options depending on the format of the data sent by your client: -// app.use(express.json()); +app.use(express.json()); // app.use(express.urlencoded()); // app.use(express.text()); // app.use(express.raw()); @@ -72,7 +72,8 @@ app.use( // Then, require the module and use it as middleware in your Express application: -// const cookieParser = require("cookie-parser"); +// const cookieParser = require("cookie-parser"); // eslint-disable-line + // app.use(cookieParser()); // Once `cookie-parser` is set up, you can read and set cookies in your routes. From 60e85f6f01833bef3cfe2d4ee31dfc03ed462193 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Tue, 12 Dec 2023 14:57:41 +0100 Subject: [PATCH 05/44] pending... --- backend/database/schema.sql | 38 ++++++++++++++++++++++++++++++++++++- 1 file changed, 37 insertions(+), 1 deletion(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 2d52bc0..b803edd 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -134,4 +134,40 @@ CREATE TABLE CONSTRAINT FK_Categorie_Par_Film_film_id FOREIGN KEY (`film_id`) REFERENCES `Film`(`id`), CONSTRAINT FK_Categorie_Par_Film_categorie_id FOREIGN KEY (`categorie_id`) REFERENCES `Categorie`(`id`), PRIMARY KEY (`film_id`, `categorie_id`) - ); \ No newline at end of file + ); + +INSERT INTO + `Film` (`miniature`, `title`, `duration`, `year`, `description`, `is_available`) +VALUES + ( + 'https://m.media-amazon.com/images/M/MV5BMTc5MDE2ODcwNV5BMl5BanBnXkFtZTgwMzI2NzQ2NzM@._V1_.jpg', + 'Avengers: Endgame', + 181, + '2019-04-24', + 'After the devastating events of Avengers: Infinity War (2018), the universe is in ruins. With the help of remaining allies, the Avengers assemble once more in order to reverse Thanos actions and restore balance to the universe.', + 1 + ), + ( + 'https://m.media-amazon.com/images/M/MV5BMjMxNjY2MDU1OV5BMl5BanBnXkFtZTgwNzY1MTUwNTM@._V1_.jpg', + 'Avengers: Infinity War', + 149, + '2018-04-25', + 'The Avengers and their allies must be willing to sacrifice all in an attempt to defeat the powerful Thanos before his blitz of devastation and ruin puts an end to the universe.', + 0 + ), + ( + 'https://m.media-amazon.com/images/M/MV5BNDYxNjQyMjAtNTdiOS00NGYwLWFmNTAtNThmYjU5ZGI2YTI1XkEyXkFqcGdeQXVyMTMxODk2OTU@._V1_.jpg', + 'The Avengers', + 143, + '2012-04-25', + 'Earth mightiest heroes must come together and learn to fight as a team if they are going to stop the mischievous Loki and his alien army from enslaving humanity.', + 1 + ), + ( + 'https://static.wikia.nocookie.net/ironman/images/d/da/P170620_v_v8_ba.jpg/revision/latest?cb=20191202183622', + 'Iron man', + 126, + '2008-04-30', + 'After being held captive in an Afghan cave, billionaire engineer Tony Stark creates a unique weaponized suit of armor to fight evil.', + 0 + ); From 5c787ef4f1ba9cce73777ff14be54e29a20f0f44 Mon Sep 17 00:00:00 2001 From: Alexandre Date: Tue, 12 Dec 2023 15:16:23 +0100 Subject: [PATCH 06/44] pulling dev --- backend/src/app.js | 20 +------------------- 1 file changed, 1 insertion(+), 19 deletions(-) diff --git a/backend/src/app.js b/backend/src/app.js index b2c59ed..c667872 100644 --- a/backend/src/app.js +++ b/backend/src/app.js @@ -3,6 +3,7 @@ const express = require("express"); const app = express(); + const cors = require("cors"); app.use( @@ -16,10 +17,6 @@ app.use( ); app.use(express.json()); -const cookieParser = require("cookie-parser"); - -app.use(cookieParser()); - const router = require("./router"); app.use("/api", router); @@ -45,18 +42,6 @@ app.use("/api", router); // 4. Be sure to only have URLs in the array with domains from which you want to allow requests. // For example: ["http://mysite.com", "http://another-domain.com"] -// const cors = require("cors"); - -// app.use( -// cors({ -// origin: [ -// process.env.FRONTEND_URL, // keep this one, after checking the value in `backend/.env` -// "http://mysite.com", -// "http://another-domain.com", -// ], -// }) -// ); - /* ************************************************************************* */ // Request Parsing: Understanding the purpose of this part @@ -72,7 +57,6 @@ app.use("/api", router); // Uncomment one or more of these options depending on the format of the data sent by your client: -// app.use(express.json()); // app.use(express.urlencoded()); // app.use(express.text()); // app.use(express.raw()); @@ -103,10 +87,8 @@ app.use("/api", router); /* ************************************************************************* */ // Import the API routes from the router module -// const router = require("./router"); // Mount the API routes under the "/api" endpoint -// app.use("/api", router); /* ************************************************************************* */ From e025d597fec0b3ffc9ab14ff5802f2538b15981c Mon Sep 17 00:00:00 2001 From: Aurelien Date: Tue, 12 Dec 2023 15:27:34 +0100 Subject: [PATCH 07/44] config table User --- backend/database/schema.sql | 2 +- backend/src/models/UserManager.js | 70 +++++++++++++++++++++++++++++++ frontend/package-lock.json | 11 +++++ frontend/package.json | 1 + 4 files changed, 83 insertions(+), 1 deletion(-) create mode 100644 backend/src/models/UserManager.js diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 48368b7..6a10d98 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -23,7 +23,7 @@ CREATE TABLE `naissance` DATE NOT NULL, `civility` BOOLEAN NOT NULL, `password` varchar(50) not null, - `is_admin` bool not null + `IsAdmin` bool not null ); DROP TABLE IF EXISTS `Film`; diff --git a/backend/src/models/UserManager.js b/backend/src/models/UserManager.js new file mode 100644 index 0000000..a6d26fa --- /dev/null +++ b/backend/src/models/UserManager.js @@ -0,0 +1,70 @@ +const AbstractManager = require("./AbstractManager"); + +class UserManager extends AbstractManager { + constructor() { + // Call the constructor of the parent class (AbstractManager) + // and pass the table name "user" as configuration + super({ table: "user" }); + } + + // The C of CRUD - Create operation + + async create({ name, email, naissance, civility, password, IsAdmin }) { + // Execute the SQL INSERT query to add a new item to the "user" table + const [result] = await this.database.query( + `insert into ${this.table} (name, email, naissance, civility, password, IsAdmin) values (?, ?, ?, ?, ?, ?)`, + [name, email, naissance, civility, password, IsAdmin] + ); + + // Return the ID of the newly inserted item + return result; + } + // The Rs of CRUD - Read operations + + async read(id) { + // Execute the SQL SELECT query to retrieve a specific item by its ID + const [rows] = await this.database.query( + `select * from ${this.table} where id = ?`, + [id] + ); + + // Return the first row of the result, which represents the item + return rows; + } + + async readAll() { + // Execute the SQL SELECT query to retrieve all items from the "user" table + const [rows] = await this.database.query(`select * from ${this.table}`); + + // Return the array of items + return rows; + } + // The U of CRUD - Update operation + // TODO: Implement the update operation to modify an existing item + + async update({ name, email, naissance, civility, password, IsAdmin, id }) { + // Execute the SQL UPDATE query to update a item to the "user" table + const [result] = await this.database.query( + `UPDATE ${this.table} SET name=?, email=?, naissance=?, civilty=?, password=?, IsAdmin=? WHERE id=?`, + [name, email, naissance, civility, password, IsAdmin, id] + ); + + // Return the ID of the newly inserted item + return result; + } + + // The D of CRUD - Delete operation + // TODO: Implement the delete operation to remove an item by its ID + + async delete(id) { + const [rows] = await this.database.query( + `DELETE FROM * from ${this.table} where id = ?`, + [id] + ); + + // Return the first row of the result, which represents the item + return rows; + } +} + +module.exports = UserManager; diff --git a/frontend/package-lock.json b/frontend/package-lock.json index e2ed2dc..80a228b 100644 --- a/frontend/package-lock.json +++ b/frontend/package-lock.json @@ -9,6 +9,7 @@ "react": "^18.2.0", "react-dom": "^18.2.0", "react-router-dom": "^6.14.2", + "saas": "^1.0.0", "sass": "^1.69.5" }, "devDependencies": { @@ -4232,6 +4233,11 @@ "queue-microtask": "^1.2.2" } }, + "node_modules/saas": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/saas/-/saas-1.0.0.tgz", + "integrity": "sha512-FgayhFS18BlPfcyMcOqxD7PIyNyUjqyv8R+rsr3X2KRK2icEUL4uvWBF+lZ0IPqJIO2kUO0d20OXY+R+pdriqg==" + }, "node_modules/safe-array-concat": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.0.1.tgz", @@ -7820,6 +7826,11 @@ "queue-microtask": "^1.2.2" } }, + "saas": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/saas/-/saas-1.0.0.tgz", + "integrity": "sha512-FgayhFS18BlPfcyMcOqxD7PIyNyUjqyv8R+rsr3X2KRK2icEUL4uvWBF+lZ0IPqJIO2kUO0d20OXY+R+pdriqg==" + }, "safe-array-concat": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/safe-array-concat/-/safe-array-concat-1.0.1.tgz", diff --git a/frontend/package.json b/frontend/package.json index 758771a..c5df770 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -9,6 +9,7 @@ "react": "^18.2.0", "react-dom": "^18.2.0", "react-router-dom": "^6.14.2", + "saas": "^1.0.0", "sass": "^1.69.5" }, "devDependencies": { From bff7f8be2ec46fefc35887a1e1923262485c8fb4 Mon Sep 17 00:00:00 2001 From: Aurelien Date: Tue, 12 Dec 2023 15:31:47 +0100 Subject: [PATCH 08/44] import userManager --- backend/src/tables.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/backend/src/tables.js b/backend/src/tables.js index 66d032c..6c2efe2 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -4,9 +4,11 @@ // Import the manager modules responsible for handling data operations on the tables const ItemManager = require("./models/ItemManager"); +const UserManager = require("./models/UserManager"); const managers = [ ItemManager, + UserManager, // Add other managers here ]; From 880502db13ed0de5972b1c9648b23df1da87ed28 Mon Sep 17 00:00:00 2001 From: Alexandre Date: Tue, 12 Dec 2023 15:32:06 +0100 Subject: [PATCH 09/44] FilmManager creation --- backend/database/schema.sql | 2 +- backend/src/models/FilmManager.js | 45 +++++++++++++++++++++++++++++++ backend/src/tables.js | 2 ++ 3 files changed, 48 insertions(+), 1 deletion(-) create mode 100644 backend/src/models/FilmManager.js diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 48368b7..23a5f9f 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -36,7 +36,7 @@ CREATE TABLE `duration` INT not null, `year` DATE NOT NULL, `description` VARCHAR(500) not null, - `is_available` BOOLEAN NOT NULL + `IsAvailable` BOOLEAN NOT NULL ); DROP TABLE IF EXISTS `Categorie`; diff --git a/backend/src/models/FilmManager.js b/backend/src/models/FilmManager.js new file mode 100644 index 0000000..2e287e4 --- /dev/null +++ b/backend/src/models/FilmManager.js @@ -0,0 +1,45 @@ +const AbstractManager = require("./AbstractManager"); + +class FilmManager extends AbstractManager { + constructor() { + super({ table: "Film" }); + } + + async create(miniature, title, duration, year, description, IsAvailable) { + const [result] = await this.database.query( + `insert into ${this.table} (miniature, title, duration, year, description, is_available) values (?,?,?,?,?,?)`, + [miniature, title, duration, year, description, IsAvailable] + ); + return result; + } + + async read(id) { + const [result] = await this.database.query( + `select * from ${this.table} where id = ?`, + [id] + ); + return result; + } + + async readall() { + const [result] = await this.database.query(`select * from ${this.table}`); + return result; + } + + async update(id, miniature, title, duration, year, description, IsAvailable) { + const [result] = await this.database.query( + `update ${this.table} SET miniature=? title=? duration=? year=? description=? IsAvailable=? where id=?`, + [miniature, title, duration, year, description, IsAvailable] + ); + return result; + } + + async delete(id) { + const [result] = await this.database.query( + `delete * from ${this.table} where id = ?`, + [id] + ); + return result; + } +} +module.exports = FilmManager; diff --git a/backend/src/tables.js b/backend/src/tables.js index 66d032c..1bffb2a 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -4,9 +4,11 @@ // Import the manager modules responsible for handling data operations on the tables const ItemManager = require("./models/ItemManager"); +const FilmManager = require("./models/FilmManager"); const managers = [ ItemManager, + FilmManager, // Add other managers here ]; From 49912df165a1eb1e8b27ce89ae9637693547ba7d Mon Sep 17 00:00:00 2001 From: Techer Tony Date: Tue, 12 Dec 2023 15:50:32 +0100 Subject: [PATCH 10/44] SerieManager --- backend/database/schema.sql | 6 +-- backend/src/models/SerieManager.js | 83 ++++++++++++++++++++++++++++++ backend/src/tables.js | 2 + 3 files changed, 88 insertions(+), 3 deletions(-) create mode 100644 backend/src/models/SerieManager.js diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 48368b7..c22e8a4 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -8,9 +8,9 @@ CREATE TABLE `duration` INT not NULL, `year` DATE not NULL, `descripion` VARCHAR(500) not NULL, - `is_vailable` BOOLEAN not NULL, - `episodes_number` INT not NULL, - `seasons_number` INT not NULL + `IsVailable` BOOLEAN not NULL, + `EpisodesNumber` INT not NULL, + `SeasonsNumber` INT not NULL ); DROP TABLE IF EXISTS `User`; diff --git a/backend/src/models/SerieManager.js b/backend/src/models/SerieManager.js new file mode 100644 index 0000000..f68599c --- /dev/null +++ b/backend/src/models/SerieManager.js @@ -0,0 +1,83 @@ +/*eslint-disable*/ + +const AbstractManager = require("./AbstractManager"); + +class SerieManager extends AbstractManager { + constructor() { + super({ table: "Serie" }); + } + + async create({ + miniature, + title, + duration, + year, + description, + IsVailable, + EpisodesNumber, + SeasonsNumber, + }) { + const [result] = await this.database.query( + `INSERT INTO ${this.table} (miniature, title, duration, year, description, IsVailable, EpisodesNumber, SeasonsNumber) values (?, ?, ?, ?, ?, ?, ?, ?)`, + [ + miniature, + title, + duration, + year, + description, + IsVailable, + EpisodesNumber, + SeasonsNumber, + ] + ); + return result; + } + + async read(id) { + const [result] = await this.database.query( + `SELECT * FROM ${this.table} WHERE id = ?`, + [id] + ); + return result; + } + async readAll() { + const [result] = await this.database.query(`select * from ${this.table} `); + return result; + } + + async update({ + id, + miniature, + title, + duration, + year, + description, + IsVailable, + EpisodesNumber, + SeasonsNumber, + }) { + const [result] = await this.database.query( + `UPDATE ${this.table} SET miniature = ?, title = ?, duration = ?, year = ?, description = ?, IsVailable = ?, EpisodesNumber = ?, SeasonsNumber = ?, WHERE id = ?` + ); + [ + id, + miniature, + title, + duration, + year, + description, + IsVailable, + EpisodesNumber, + SeasonsNumber, + ]; + return result; + } + async delete(id) { + const [result] = await this.database.query( + `delete from ${this.table} where id = ?,` + )[id]; + return result; + } +} + +module.exports = SerieManager; diff --git a/backend/src/tables.js b/backend/src/tables.js index 66d032c..87d4f03 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -4,9 +4,11 @@ // Import the manager modules responsible for handling data operations on the tables const ItemManager = require("./models/ItemManager"); +const SerieManager = require("./models/SerieManager"); const managers = [ ItemManager, + SerieManager, // Add other managers here ]; From 0b0149dbe81a0380db16a7a051386c99158ca635 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Tue, 12 Dec 2023 16:46:05 +0100 Subject: [PATCH 11/44] working on backend --- backend/database/schema.sql | 24 ++++++ backend/seed.js | 30 ++++++-- backend/src/app.js | 10 +-- ...Controllers.js => categorieControllers.js} | 6 +- backend/src/models/CategorieManager.js | 73 +++++++++++++++++++ backend/src/models/ItemManager.js | 59 --------------- backend/src/router.js | 8 +- backend/src/tables.js | 6 +- 8 files changed, 136 insertions(+), 80 deletions(-) rename backend/src/controllers/{itemControllers.js => categorieControllers.js} (90%) create mode 100644 backend/src/models/CategorieManager.js delete mode 100644 backend/src/models/ItemManager.js diff --git a/backend/database/schema.sql b/backend/database/schema.sql index b803edd..90514cb 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -171,3 +171,27 @@ VALUES 'After being held captive in an Afghan cave, billionaire engineer Tony Stark creates a unique weaponized suit of armor to fight evil.', 0 ); + +INSERT INTO + `Categorie` (`name`, `position`) +VALUES + ('Action', 1), + ('Adventure', 2), + ('Sci-Fi', 3), + ('Drama', 4), + ('Thriller', 5), + ('Comedy', 6), + ('Crime', 7), + ('Fantasy', 8), + ('Mystery', 9), + ('Animation', 10), + ('Family', 11), + ('Biography', 12), + ('History', 13), + ('Horror', 14), + ('Music', 15), + ('Musical', 16), + ('Romance', 17), + ('Sport', 18), + ('War', 19), + ('Western', 20); diff --git a/backend/seed.js b/backend/seed.js index fdcf805..ceeb61e 100644 --- a/backend/seed.js +++ b/backend/seed.js @@ -19,15 +19,31 @@ const seed = async () => { // Generating Seed Data - // Optional: Truncate tables (remove existing data) - await database.query("truncate item"); + // // Optional: Truncate tables (remove existing data) + // await database.query("truncate item"); - // Insert fake data into the 'item' table - for (let i = 0; i < 10; i += 1) { + // // Insert fake data into the 'item' table + // for (let i = 0; i < 10; i += 1) { + // queries.push( + // database.query("insert into item(title) values (?)", [ + // faker.lorem.word(), + // ]) + // ); + // } + + for (let numberOfData = 0; numberOfData < 100; numberOfData += 1) { queries.push( - database.query("insert into item(title) values (?)", [ - faker.lorem.word(), - ]) + database.query( + "INSERT INTO `Film` (`miniature`, `title`, `duration`, `year`, `description`, `is_available`) VALUES (?, ?, ?, ?, ?, ?)", + [ + faker.image.imageUrl(), + faker.lorem.words(), + faker.datatype.number(), + faker.datatype.number(), + faker.lorem.paragraph(), + faker.datatype.boolean(), + ] + ) ); } diff --git a/backend/src/app.js b/backend/src/app.js index cecaa7a..dbd0129 100644 --- a/backend/src/app.js +++ b/backend/src/app.js @@ -109,17 +109,17 @@ app.use("/api", router); // 1. Uncomment the lines related to serving static files and redirecting unhandled requests. // 2. Ensure that the `reactBuildPath` points to the correct directory where your frontend's build artifacts are located. -const reactBuildPath = `${__dirname}/../../frontend/dist`; +// const reactBuildPath = `${__dirname}/../../frontend/dist`; // Serve react resources -app.use(express.static(reactBuildPath)); +// app.use(express.static(reactBuildPath)); // Redirect unhandled requests to the react index file -app.get("*", (req, res) => { - res.sendFile(`${reactBuildPath}/index.html`); -}); +// app.get("*", (req, res) => { +// res.sendFile(`${reactBuildPath}/index.html`); +// }); /* ************************************************************************* */ diff --git a/backend/src/controllers/itemControllers.js b/backend/src/controllers/categorieControllers.js similarity index 90% rename from backend/src/controllers/itemControllers.js rename to backend/src/controllers/categorieControllers.js index fca2dc2..79b1134 100644 --- a/backend/src/controllers/itemControllers.js +++ b/backend/src/controllers/categorieControllers.js @@ -5,7 +5,7 @@ const tables = require("../tables"); const browse = async (req, res, next) => { try { // Fetch all items from the database - const items = await tables.item.readAll(); + const items = await tables.categorie.readAll(); // Respond with the items in JSON format res.json(items); @@ -19,7 +19,7 @@ const browse = async (req, res, next) => { const read = async (req, res, next) => { try { // Fetch a specific item from the database based on the provided ID - const item = await tables.item.read(req.params.id); + const item = await tables.categorie.read(req.params.id); // If the item is not found, respond with HTTP 404 (Not Found) // Otherwise, respond with the item in JSON format @@ -44,7 +44,7 @@ const add = async (req, res, next) => { try { // Insert the item into the database - const insertId = await tables.item.create(item); + const insertId = await tables.categorie.create(item); // Respond with HTTP 201 (Created) and the ID of the newly inserted item res.status(201).json({ insertId }); diff --git a/backend/src/models/CategorieManager.js b/backend/src/models/CategorieManager.js new file mode 100644 index 0000000..d81fb51 --- /dev/null +++ b/backend/src/models/CategorieManager.js @@ -0,0 +1,73 @@ +const AbstractManager = require("./AbstractManager"); + +class CategorieManager extends AbstractManager { + constructor() { + // Call the constructor of the parent class (AbstractManager) + // and pass the table name "categorie" as configuration + super({ table: "categorie" }); + } + + // The C of CRUD - Create operation + + async create(categorie) { + // Execute the SQL INSERT query to add a new categorie to the "categorie" table + const [result] = await this.database.query( + `insert into ${this.table} (name, position) values (?, ?)`, + [categorie.name, categorie.position] + ); + + // Return the ID of the newly inserted categorie + return result.insertId; + } + + // The Rs of CRUD - Read operations + + async read(id) { + // Execute the SQL SELECT query to retrieve a specific categorie by its ID + const [rows] = await this.database.query( + `select * from ${this.table} where id = ?`, + [id] + ); + + // Return the first row of the result, which represents the categorie + return rows[0]; + } + + async readAll() { + // Execute the SQL SELECT query to retrieve all categories from the "categorie" table + const [rows] = await this.database.query(`select * from ${this.table}`); + + // Return the array of categories + return rows; + } + + // The U of CRUD - Update operation + // ^ Implemented the update operation to modify an existing categorie + + async update(categorie) { + // Execute the SQL UPDATE query to modify an existing categorie + const [result] = await this.database.query( + `update ${this.table} set name = ?, position = ? where id = ?`, + [categorie.name, categorie.position, categorie.id] + ); + + // Return the number of affected rows + return result.affectedRows; + } + + // The D of CRUD - Delete operation + // ^ Implemented the delete operation to remove an categorie by its ID + + async delete(id) { + // Execute the SQL DELETE query to remove the categorie from the "categorie" table + const [result] = await this.database.query( + `delete from ${this.table} where id = ?`, + [id] + ); + + // Return the number of affected rows + return result.affectedRows; + } +} + +module.exports = CategorieManager; diff --git a/backend/src/models/ItemManager.js b/backend/src/models/ItemManager.js deleted file mode 100644 index eeeae9f..0000000 --- a/backend/src/models/ItemManager.js +++ /dev/null @@ -1,59 +0,0 @@ -const AbstractManager = require("./AbstractManager"); - -class ItemManager extends AbstractManager { - constructor() { - // Call the constructor of the parent class (AbstractManager) - // and pass the table name "item" as configuration - super({ table: "item" }); - } - - // The C of CRUD - Create operation - - async create(item) { - // Execute the SQL INSERT query to add a new item to the "item" table - const [result] = await this.database.query( - `insert into ${this.table} (title) values (?)`, - [item.title] - ); - - // Return the ID of the newly inserted item - return result.insertId; - } - - // The Rs of CRUD - Read operations - - async read(id) { - // Execute the SQL SELECT query to retrieve a specific item by its ID - const [rows] = await this.database.query( - `select * from ${this.table} where id = ?`, - [id] - ); - - // Return the first row of the result, which represents the item - return rows[0]; - } - - async readAll() { - // Execute the SQL SELECT query to retrieve all items from the "item" table - const [rows] = await this.database.query(`select * from ${this.table}`); - - // Return the array of items - return rows; - } - - // The U of CRUD - Update operation - // TODO: Implement the update operation to modify an existing item - - // async update(item) { - // ... - // } - - // The D of CRUD - Delete operation - // TODO: Implement the delete operation to remove an item by its ID - - // async delete(id) { - // ... - // } -} - -module.exports = ItemManager; diff --git a/backend/src/router.js b/backend/src/router.js index 38f375d..6abefc8 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -7,16 +7,16 @@ const router = express.Router(); /* ************************************************************************* */ // Import itemControllers module for handling item-related operations -const itemControllers = require("./controllers/itemControllers"); +const categorieControllers = require("./controllers/categorieControllers"); // Route to get a list of items -router.get("/items", itemControllers.browse); +router.get("/categories", categorieControllers.browse); // Route to get a specific item by ID -router.get("/items/:id", itemControllers.read); +router.get("/categories/:id", categorieControllers.read); // Route to add a new item -router.post("/items", itemControllers.add); +router.post("/categories", categorieControllers.add); /* ************************************************************************* */ diff --git a/backend/src/tables.js b/backend/src/tables.js index 66d032c..7043017 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -3,10 +3,10 @@ /* ************************************************************************* */ // Import the manager modules responsible for handling data operations on the tables -const ItemManager = require("./models/ItemManager"); +const CategorieManager = require("./models/CategorieManager"); const managers = [ - ItemManager, + CategorieManager, // Add other managers here ]; @@ -20,6 +20,8 @@ managers.forEach((ManagerClass) => { tables[manager.table] = manager; }); +console.info("Registered tables:", Object.keys(tables)); + /* ************************************************************************* */ // Use a Proxy to customize error messages when trying to access a non-existing table From 7a350f57bb0212c90101e34148c36fb325d7c99a Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Tue, 12 Dec 2023 21:27:24 +0100 Subject: [PATCH 12/44] working on backend --- backend/database/schema.sql | 2 +- backend/src/controllers/filmControllers.js | 67 ++++++ backend/src/models/FilmManager.js | 14 +- backend/src/router.js | 4 + backend/src/tables.js | 2 +- frontend/package-lock.json | 152 +++++++++++++ frontend/package.json | 1 + frontend/src/App.jsx | 248 ++++----------------- 8 files changed, 282 insertions(+), 208 deletions(-) create mode 100644 backend/src/controllers/filmControllers.js diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 3d2520b..cee02a0 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -7,7 +7,7 @@ CREATE TABLE `title` VARCHAR(50) not NULL, `duration` INT not NULL, `year` DATE not NULL, - `descripion` VARCHAR(500) not NULL, + `description` VARCHAR(500) not NULL, `is_available` BOOLEAN not NULL, `episodes_number` INT not NULL, `seasons_number` INT not NULL diff --git a/backend/src/controllers/filmControllers.js b/backend/src/controllers/filmControllers.js new file mode 100644 index 0000000..188ee09 --- /dev/null +++ b/backend/src/controllers/filmControllers.js @@ -0,0 +1,67 @@ +// Import access to database tables +const tables = require("../tables"); + +// The B of BREAD - Browse (Read All) operation +const browse = async (req, res, next) => { + try { + // Fetch all items from the database + const items = await tables.film.readAll(); + + // Respond with the items in JSON format + res.json(items); + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The R of BREAD - Read operation +const read = async (req, res, next) => { + try { + // Fetch a specific item from the database based on the provided ID + const item = await tables.film.read(req.params.id); + + // If the item is not found, respond with HTTP 404 (Not Found) + // Otherwise, respond with the item in JSON format + if (item == null) { + res.sendStatus(404); + } else { + res.json(item); + } + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The E of BREAD - Edit (Update) operation +// This operation is not yet implemented + +// The A of BREAD - Add (Create) operation +const add = async (req, res, next) => { + // Extract the item data from the request body + const item = req.body; + + try { + // Insert the item into the database + const insertId = await tables.film.create(item); + + // Respond with HTTP 201 (Created) and the ID of the newly inserted item + res.status(201).json({ insertId }); + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The D of BREAD - Destroy (Delete) operation +// This operation is not yet implemented + +// Ready to export the controller functions +module.exports = { + browse, + read, + // edit, + add, + // destroy, +}; diff --git a/backend/src/models/FilmManager.js b/backend/src/models/FilmManager.js index 2e287e4..5728fb7 100644 --- a/backend/src/models/FilmManager.js +++ b/backend/src/models/FilmManager.js @@ -2,15 +2,15 @@ const AbstractManager = require("./AbstractManager"); class FilmManager extends AbstractManager { constructor() { - super({ table: "Film" }); + super({ table: "film" }); } - async create(miniature, title, duration, year, description, IsAvailable) { + async create({ miniature, title, duration, year, description, IsAvailable }) { const [result] = await this.database.query( `insert into ${this.table} (miniature, title, duration, year, description, is_available) values (?,?,?,?,?,?)`, [miniature, title, duration, year, description, IsAvailable] ); - return result; + return result.insertId; } async read(id) { @@ -18,10 +18,10 @@ class FilmManager extends AbstractManager { `select * from ${this.table} where id = ?`, [id] ); - return result; + return result[0]; } - async readall() { + async readAll() { const [result] = await this.database.query(`select * from ${this.table}`); return result; } @@ -29,9 +29,9 @@ class FilmManager extends AbstractManager { async update(id, miniature, title, duration, year, description, IsAvailable) { const [result] = await this.database.query( `update ${this.table} SET miniature=? title=? duration=? year=? description=? IsAvailable=? where id=?`, - [miniature, title, duration, year, description, IsAvailable] + [miniature, title, duration, year, description, IsAvailable, id] ); - return result; + return result.affectedRows; } async delete(id) { diff --git a/backend/src/router.js b/backend/src/router.js index 6abefc8..7a684a9 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -8,15 +8,19 @@ const router = express.Router(); // Import itemControllers module for handling item-related operations const categorieControllers = require("./controllers/categorieControllers"); +const filmControllers = require("./controllers/filmControllers"); // Route to get a list of items router.get("/categories", categorieControllers.browse); +router.get("/films", filmControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); +router.get("/films/:id", filmControllers.read); // Route to add a new item router.post("/categories", categorieControllers.add); +router.post("/films", filmControllers.add); /* ************************************************************************* */ diff --git a/backend/src/tables.js b/backend/src/tables.js index 873ef30..d6d1def 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -26,7 +26,7 @@ managers.forEach((ManagerClass) => { tables[manager.table] = manager; }); -// console.info("Registered tables:", Object.keys(tables)); +console.info("Registered tables:", Object.keys(tables)); /* ************************************************************************* */ diff --git a/frontend/package-lock.json b/frontend/package-lock.json index 80a228b..13481bf 100644 --- a/frontend/package-lock.json +++ b/frontend/package-lock.json @@ -5,6 +5,7 @@ "packages": { "": { "dependencies": { + "axios": "^1.6.2", "prop-types": "^15.8.1", "react": "^18.2.0", "react-dom": "^18.2.0", @@ -1247,6 +1248,11 @@ "has-symbols": "^1.0.3" } }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==" + }, "node_modules/available-typed-arrays": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.5.tgz", @@ -1268,6 +1274,16 @@ "node": ">=4" } }, + "node_modules/axios": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.6.2.tgz", + "integrity": "sha512-7i24Ri4pmDRfJTR7LDBhsOTtcm+9kjX5WiY1X3wIisx6G9So3pfMkEiU7emUBe46oceVImccTEM3k6C5dbVW8A==", + "dependencies": { + "follow-redirects": "^1.15.0", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, "node_modules/axobject-query": { "version": "3.2.1", "resolved": "https://registry.npmjs.org/axobject-query/-/axobject-query-3.2.1.tgz", @@ -1489,6 +1505,17 @@ "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==", "dev": true }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", @@ -1627,6 +1654,14 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/dequal": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", @@ -2492,6 +2527,25 @@ "integrity": "sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ==", "dev": true }, + "node_modules/follow-redirects": { + "version": "1.15.3", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.3.tgz", + "integrity": "sha512-1VzOtuEM8pC9SFU1E+8KfTjZyMztRsgEfwQl44z8A25uy13jSzTj6dyK2Df52iV0vgHCfBwLhDWevLn95w5v6Q==", + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, "node_modules/for-each": { "version": "0.3.3", "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", @@ -2501,6 +2555,19 @@ "is-callable": "^1.1.3" } }, + "node_modules/form-data": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", + "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", @@ -3443,6 +3510,25 @@ "node": ">=8.6" } }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/mimic-fn": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-4.0.0.tgz", @@ -3889,6 +3975,11 @@ "react-is": "^16.13.1" } }, + "node_modules/proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" + }, "node_modules/punycode": { "version": "2.3.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", @@ -5730,6 +5821,11 @@ "has-symbols": "^1.0.3" } }, + "asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==" + }, "available-typed-arrays": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/available-typed-arrays/-/available-typed-arrays-1.0.5.tgz", @@ -5742,6 +5838,16 @@ "integrity": "sha512-M0JtH+hlOL5pLQwHOLNYZaXuhqmvS8oExsqB1SBYgA4Dk7u/xx+YdGHXaK5pyUfed5mYXdlYiphWq3G8cRi5JQ==", "dev": true }, + "axios": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.6.2.tgz", + "integrity": "sha512-7i24Ri4pmDRfJTR7LDBhsOTtcm+9kjX5WiY1X3wIisx6G9So3pfMkEiU7emUBe46oceVImccTEM3k6C5dbVW8A==", + "requires": { + "follow-redirects": "^1.15.0", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, "axobject-query": { "version": "3.2.1", "resolved": "https://registry.npmjs.org/axobject-query/-/axobject-query-3.2.1.tgz", @@ -5890,6 +5996,14 @@ "integrity": "sha512-72fSenhMw2HZMTVHeCA9KCmpEIbzWiQsjN+BHcBbS9vr1mtt+vJjPdksIBNUmKAW8TFUDPJK5SUU3QhE9NEXDw==", "dev": true }, + "combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "requires": { + "delayed-stream": "~1.0.0" + } + }, "concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", @@ -5990,6 +6104,11 @@ "object-keys": "^1.1.1" } }, + "delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==" + }, "dequal": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", @@ -6650,6 +6769,11 @@ "integrity": "sha512-36yxDn5H7OFZQla0/jFJmbIKTdZAQHngCedGxiMmpNfEZM0sdEeT+WczLQrjK6D7o2aiyLYDnkw0R3JK0Qv1RQ==", "dev": true }, + "follow-redirects": { + "version": "1.15.3", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.3.tgz", + "integrity": "sha512-1VzOtuEM8pC9SFU1E+8KfTjZyMztRsgEfwQl44z8A25uy13jSzTj6dyK2Df52iV0vgHCfBwLhDWevLn95w5v6Q==" + }, "for-each": { "version": "0.3.3", "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", @@ -6659,6 +6783,16 @@ "is-callable": "^1.1.3" } }, + "form-data": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", + "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", + "requires": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + } + }, "fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", @@ -7311,6 +7445,19 @@ "picomatch": "^2.3.1" } }, + "mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==" + }, + "mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "requires": { + "mime-db": "1.52.0" + } + }, "mimic-fn": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-4.0.0.tgz", @@ -7610,6 +7757,11 @@ "react-is": "^16.13.1" } }, + "proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" + }, "punycode": { "version": "2.3.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", diff --git a/frontend/package.json b/frontend/package.json index c5df770..bcd760b 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -5,6 +5,7 @@ "preview": "vite preview" }, "dependencies": { + "axios": "^1.6.2", "prop-types": "^15.8.1", "react": "^18.2.0", "react-dom": "^18.2.0", diff --git a/frontend/src/App.jsx b/frontend/src/App.jsx index 539bb57..df4a6fe 100644 --- a/frontend/src/App.jsx +++ b/frontend/src/App.jsx @@ -1,4 +1,20 @@ +import { useEffect, useState } from "react"; +import axios from "axios"; // eslint-disable-line + function App() { + const [movies, setMovies] = useState([]); + + useEffect(() => { + axios + .get("http://localhost:3310/api/films") + .then((response) => { + setMovies(response.data); + console.info(response.data); + }) + .catch((error) => { + console.error(error); + }); + }, []); return (
@@ -9,33 +25,8 @@ function App() { alt="wildtube logo" />
-
- hero movie slide - hero movie slide - hero movie slide - hero movie slide - hero movie slide -
+ {/*
+
*/}
  • Toutes les catégories

    @@ -62,22 +53,9 @@ function App() {

    Voir tout

- movie slide - movie slide + movie slide
- movie slide + movie slide
- movie slide - movie slide - movie slide -
- -
-
-

Action

-

Voir tout

-
-
- movie slide - movie slide -
- movie slide -
-
- lock icon -
-
-
- movie slide - movie slide - movie slide -
-
-
-
-

Action

-

Voir tout

-
-
- movie slide - movie slide -
- movie slide -
-
+ {movies.map((movie) => { + if (movie.is_available) { + return ( lock icon -
-
-
- movie slide - movie slide - movie slide -
-
-
-
-

Action

-

Voir tout

-
-
- movie slide - movie slide -
- movie slide -
-
+ ); + } + + return ( +
lock icon +
+
+ lock icon +
+
-
-
- movie slide - movie slide - movie slide + ); + })}
From d49ad1b875ff8ad7484d04dccd02677edf5d812c Mon Sep 17 00:00:00 2001 From: Aurelien Date: Wed, 13 Dec 2023 09:29:30 +0100 Subject: [PATCH 13/44] modif usercontrollers --- backend/src/controllers/UserControllersjs | 113 ++++++++++++++++++++++ frontend/src/App.jsx | 2 +- 2 files changed, 114 insertions(+), 1 deletion(-) create mode 100644 backend/src/controllers/UserControllersjs diff --git a/backend/src/controllers/UserControllersjs b/backend/src/controllers/UserControllersjs new file mode 100644 index 0000000..c89a59d --- /dev/null +++ b/backend/src/controllers/UserControllersjs @@ -0,0 +1,113 @@ +// Import access to database tables +const tables = require("../tables"); + +// The B of BREAD - Browse (Read All) operation +const browse = async (req, res, next) => { + try { + // Fetch all items from the database + const users = await tables.user.readAll(); + + // Respond with the items in JSON format + res.json(users); + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The R of BREAD - Read operation +const read = async (req, res, next) => { + try { + // Fetch a specific item from the database based on the provided ID + const user = await tables.user.read(req.params.id); + + // If the item is not found, respond with HTTP 404 (Not Found) + // Otherwise, respond with the item in JSON format + if (user == null) { + res.sendStatus(404); + } else { + res.json(user); + } + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The E of BREAD - Edit (Update) operation +// This operation is not yet implemented + +// eslint-disable-next-line consistent-return +const edit = async (req, res, next) => { + try { + const { name, email, naissance, civility, password, IsAdmin } = req.body; + const { id } = req.params; + + if ( + !name || + !email || + !naissance || + !civility || + !password || + !IsAdmin || + !id + ) { + return res + .status(400) + .send( + "Name, email, naissance, civility, password, IsAdmin or id is missing" + ); + } + + const [results] = await tables.user.update( + "UPDATE user SET name=?, email=?, naissance=?, civility=?, password=?, IsAdmin=? WHERE id=?", + [name, email, naissance, civility, password, IsAdmin, id] + ); + + if (results.affectedRows > 0) { + const newUser = { + id, + name, + email, + naissance, + civility, + password, + IsAdmin, + }; + res.status(200).send(newUser); + } else { + return res.status(404).send("Not found"); + } + } catch (err) { + next(err); + } +}; + +// The A of BREAD - Add (Create) operation +const add = async (req, res, next) => { + // Extract the item data from the request body + const item = req.body; + + try { + // Insert the item into the database + const insertId = await tables.item.create(item); + + // Respond with HTTP 201 (Created) and the ID of the newly inserted item + res.status(201).json({ insertId }); + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The D of BREAD - Destroy (Delete) operation +// This operation is not yet implemented + +// Ready to export the controller functions +module.exports = { + browse, + read, + edit, + add, + // destroy, +}; diff --git a/frontend/src/App.jsx b/frontend/src/App.jsx index 539bb57..7acda2b 100644 --- a/frontend/src/App.jsx +++ b/frontend/src/App.jsx @@ -11,7 +11,7 @@ function App() {
hero movie slide From 083180ce97609f7691f56b629c5b0dd65c30ffe2 Mon Sep 17 00:00:00 2001 From: Alexandre Date: Wed, 13 Dec 2023 09:32:51 +0100 Subject: [PATCH 14/44] merging --- backend/database/schema.sql | 2 + backend/src/controllers/filmControllers.js | 72 ++++++++++++++++++++++ backend/src/models/FilmManager.js | 12 +++- 3 files changed, 84 insertions(+), 2 deletions(-) create mode 100644 backend/src/controllers/filmControllers.js diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 23a5f9f..e8d376e 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -5,6 +5,7 @@ CREATE TABLE `id` int primary key auto_increment not null, `miniature` varchar(255) not null, `title` VARCHAR(50) not NULL, + `video_url` VARCHAR(255) not null `duration` INT not NULL, `year` DATE not NULL, `descripion` VARCHAR(500) not NULL, @@ -33,6 +34,7 @@ CREATE TABLE `id` int primary key auto_increment not null, `miniature` VARCHAR(255) not null, `title` VARCHAR(255) not null, + `video_url` VARCHAR(255) not null `duration` INT not null, `year` DATE NOT NULL, `description` VARCHAR(500) not null, diff --git a/backend/src/controllers/filmControllers.js b/backend/src/controllers/filmControllers.js new file mode 100644 index 0000000..b8526c6 --- /dev/null +++ b/backend/src/controllers/filmControllers.js @@ -0,0 +1,72 @@ +const tables = require("../tables"); + +const browse = async (req, res, next) => { + try { + const films = await tables.film.readAll(); + res.json(films); + } catch (err) { + next(err); + } +}; + +const read = async (req, res, next) => { + try { + const film = await tables.item.read(req.params.id); + if (film == null) { + res.sendStatus(404); + } else { + res.json(film); + } + } catch (err) { + next(err); + } +}; + +const edit = async (req, res, next) => { + const { id } = req.params.id; + req.body.id = id; + try { + const result = await tables.film.update(req.body); + if (result.affectedRows) { + res.json(result); + res.sendStatus(204); + } else { + res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; + +const add = async (req, res, next) => { + const film = req.body; + + try { + const insertId = await tables.film.create(film); + res.status(201).json({ insertId }); + } catch (err) { + next(err); + } +}; + +const destroy = async (req, res, next) => { + const { id } = req.params.id; + try { + const result = await tables.film.delete(id); + if (result.affectedRows) { + res.sendStatus(200); + } else { + res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; + +module.exports = { + browse, + read, + edit, + add, + destroy, +}; diff --git a/backend/src/models/FilmManager.js b/backend/src/models/FilmManager.js index 2e287e4..40c3df5 100644 --- a/backend/src/models/FilmManager.js +++ b/backend/src/models/FilmManager.js @@ -26,10 +26,18 @@ class FilmManager extends AbstractManager { return result; } - async update(id, miniature, title, duration, year, description, IsAvailable) { + async update({ + id, + miniature, + title, + duration, + year, + description, + IsAvailable, + }) { const [result] = await this.database.query( `update ${this.table} SET miniature=? title=? duration=? year=? description=? IsAvailable=? where id=?`, - [miniature, title, duration, year, description, IsAvailable] + [miniature, title, duration, year, description, IsAvailable, id] ); return result; } From 0ee8f61f04cc44f52c9b28340525ae72971b14f6 Mon Sep 17 00:00:00 2001 From: Techer Tony Date: Wed, 13 Dec 2023 10:06:04 +0100 Subject: [PATCH 15/44] serieControllers --- backend/src/controllers/filmControllers.js | 2 +- backend/src/controllers/serieControllers.js | 72 +++++++++++++++++++++ 2 files changed, 73 insertions(+), 1 deletion(-) create mode 100644 backend/src/controllers/serieControllers.js diff --git a/backend/src/controllers/filmControllers.js b/backend/src/controllers/filmControllers.js index b8526c6..d3013bc 100644 --- a/backend/src/controllers/filmControllers.js +++ b/backend/src/controllers/filmControllers.js @@ -11,7 +11,7 @@ const browse = async (req, res, next) => { const read = async (req, res, next) => { try { - const film = await tables.item.read(req.params.id); + const film = await tables.film.read(req.params.id); if (film == null) { res.sendStatus(404); } else { diff --git a/backend/src/controllers/serieControllers.js b/backend/src/controllers/serieControllers.js new file mode 100644 index 0000000..e6d53b2 --- /dev/null +++ b/backend/src/controllers/serieControllers.js @@ -0,0 +1,72 @@ +const tables = require("../tables"); + +const browse = async (req, res, next) => { + try { + const series = await tables.serie.readAll(); + res.json(series); + } catch (err) { + next(err); + } +}; + +const read = async (req, res, next) => { + try { + const serie = await tables.serie.read(req.params.id); + if (serie == null) { + res.sendStatus(404); + } else { + res.json(serie); + } + } catch (err) { + next(err); + } +}; + +const edit = async (req, res, next) => { + const { id } = req.params.id; + req.body.id = id; + try { + const result = await tables.serie.update(req.body); + if (result.affectedRows) { + res.json(result); + res.sendStatus(204); + } else { + res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; + +const add = async (req, res, next) => { + const serie = req.body; + + try { + const insertId = await tables.serie.create(serie); + res.status(201).json({ insertId }); + } catch (err) { + next(err); + } +}; + +const destroy = async (req, res, next) => { + const { id } = req.params.id; + try { + const result = await tables.serie.delete(id); + if (result.affectedRows) { + res.sendStatus(200); + } else { + res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; + +module.exports = { + browse, + read, + edit, + add, + destroy, +}; From f0c306cb5cceb320f48905b1215943f5ce9573c1 Mon Sep 17 00:00:00 2001 From: Techer Tony Date: Wed, 13 Dec 2023 10:18:10 +0100 Subject: [PATCH 16/44] route for Controllers --- backend/src/router.js | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/backend/src/router.js b/backend/src/router.js index 7a684a9..8dd30c7 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -9,18 +9,30 @@ const router = express.Router(); // Import itemControllers module for handling item-related operations const categorieControllers = require("./controllers/categorieControllers"); const filmControllers = require("./controllers/filmControllers"); +const serieControllers = require("./controllers/serieControllers"); // Route to get a list of items router.get("/categories", categorieControllers.browse); router.get("/films", filmControllers.browse); +router.get("/serie", serieControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); +router.get("/serie/:id", serieControllers.read); // Route to add a new item router.post("/categories", categorieControllers.add); router.post("/films", filmControllers.add); +router.post("/serie", serieControllers.add); + +// Route to Update a new item + +router.update("/serie", serieControllers.edit); + +// Route to Delete a new item + +router.delete("/serie", serieControllers.destroy); /* ************************************************************************* */ From 4392f0d84bbec808b8596ef39facf89cfe165256 Mon Sep 17 00:00:00 2001 From: Aurelien Date: Wed, 13 Dec 2023 10:45:24 +0100 Subject: [PATCH 17/44] usercontrollers --- backend/database/schema.sql | 10 +- backend/src/controllers/filmControllers.js | 2 +- .../{UserControllersjs => userControllers.js} | 60 +++---- backend/src/models/FilmManager.js | 19 ++- backend/src/models/SerieManager.js | 16 +- backend/src/router.js | 4 + package-lock.json | 154 ++++++++++++++++++ 7 files changed, 210 insertions(+), 55 deletions(-) rename backend/src/controllers/{UserControllersjs => userControllers.js} (66%) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 4efc3e1..1098246 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -5,13 +5,13 @@ CREATE TABLE `id` int primary key auto_increment not null, `miniature` varchar(255) not null, `title` VARCHAR(50) not NULL, - `video_url` VARCHAR(255) not null + `videoUrl` VARCHAR(255) not null, `duration` INT not NULL, `year` DATE not NULL, `description` VARCHAR(500) not NULL, - `is_available` BOOLEAN not NULL, - `episodes_number` INT not NULL, - `seasons_number` INT not NULL + `IsAvailable` BOOLEAN not NULL, + `EpisodesNumber` INT not NULL, + `SeasonsNumber` INT not NULL ); DROP TABLE IF EXISTS `User`; @@ -34,7 +34,7 @@ CREATE TABLE `id` int primary key auto_increment not null, `miniature` VARCHAR(255) not null, `title` VARCHAR(255) not null, - `video_url` VARCHAR(255) not null + `VideoUrl` VARCHAR(255) not null, `duration` INT not null, `year` DATE NOT NULL, `description` VARCHAR(500) not null, diff --git a/backend/src/controllers/filmControllers.js b/backend/src/controllers/filmControllers.js index b8526c6..d3013bc 100644 --- a/backend/src/controllers/filmControllers.js +++ b/backend/src/controllers/filmControllers.js @@ -11,7 +11,7 @@ const browse = async (req, res, next) => { const read = async (req, res, next) => { try { - const film = await tables.item.read(req.params.id); + const film = await tables.film.read(req.params.id); if (film == null) { res.sendStatus(404); } else { diff --git a/backend/src/controllers/UserControllersjs b/backend/src/controllers/userControllers.js similarity index 66% rename from backend/src/controllers/UserControllersjs rename to backend/src/controllers/userControllers.js index c89a59d..18ebe92 100644 --- a/backend/src/controllers/UserControllersjs +++ b/backend/src/controllers/userControllers.js @@ -39,42 +39,13 @@ const read = async (req, res, next) => { // eslint-disable-next-line consistent-return const edit = async (req, res, next) => { + const { id } = req.params.id; + req.body.id = id; try { - const { name, email, naissance, civility, password, IsAdmin } = req.body; - const { id } = req.params; - - if ( - !name || - !email || - !naissance || - !civility || - !password || - !IsAdmin || - !id - ) { - return res - .status(400) - .send( - "Name, email, naissance, civility, password, IsAdmin or id is missing" - ); - } - - const [results] = await tables.user.update( - "UPDATE user SET name=?, email=?, naissance=?, civility=?, password=?, IsAdmin=? WHERE id=?", - [name, email, naissance, civility, password, IsAdmin, id] - ); - - if (results.affectedRows > 0) { - const newUser = { - id, - name, - email, - naissance, - civility, - password, - IsAdmin, - }; - res.status(200).send(newUser); + const result = await tables.user.update(req.body); + if (result.affectedRows > 0) { + res.json(result); + res.status(204); } else { return res.status(404).send("Not found"); } @@ -86,11 +57,11 @@ const edit = async (req, res, next) => { // The A of BREAD - Add (Create) operation const add = async (req, res, next) => { // Extract the item data from the request body - const item = req.body; + const user = req.body; try { // Insert the item into the database - const insertId = await tables.item.create(item); + const insertId = await tables.item.create(user); // Respond with HTTP 201 (Created) and the ID of the newly inserted item res.status(201).json({ insertId }); @@ -102,6 +73,19 @@ const add = async (req, res, next) => { // The D of BREAD - Destroy (Delete) operation // This operation is not yet implemented +const destroy = async (req, res, next) => { + const { id } = req.params.id; + try { + const result = await tables.user.delete(id); + if (result.affectedRows) { + res.sendStatus(200); + } else { + res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; // Ready to export the controller functions module.exports = { @@ -109,5 +93,5 @@ module.exports = { read, edit, add, - // destroy, + destroy, }; diff --git a/backend/src/models/FilmManager.js b/backend/src/models/FilmManager.js index aa61283..aceea2e 100644 --- a/backend/src/models/FilmManager.js +++ b/backend/src/models/FilmManager.js @@ -5,10 +5,18 @@ class FilmManager extends AbstractManager { super({ table: "film" }); } - async create({ miniature, title, duration, year, description, IsAvailable }) { + async create({ + miniature, + title, + VideoUrl, + duration, + year, + description, + IsAvailable, + }) { const [result] = await this.database.query( - `insert into ${this.table} (miniature, title, duration, year, description, is_available) values (?,?,?,?,?,?)`, - [miniature, title, duration, year, description, IsAvailable] + `insert into ${this.table} (miniature, title, VideoUrl, duration, year, description, IsAvailable) values (?,?,?,?,?,?,?)`, + [miniature, title, VideoUrl, duration, year, description, IsAvailable] ); return result.insertId; } @@ -30,14 +38,15 @@ class FilmManager extends AbstractManager { id, miniature, title, + VideoUrl, duration, year, description, IsAvailable, }) { const [result] = await this.database.query( - `update ${this.table} SET miniature=? title=? duration=? year=? description=? IsAvailable=? where id=?`, - [miniature, title, duration, year, description, IsAvailable, id] + `update ${this.table} SET miniature=? title=? VideoUrl=? duration=? year=? description=? IsAvailable=? where id=?`, + [miniature, title, VideoUrl, duration, year, description, IsAvailable, id] ); return result.affectedRows; } diff --git a/backend/src/models/SerieManager.js b/backend/src/models/SerieManager.js index f68599c..573b56b 100644 --- a/backend/src/models/SerieManager.js +++ b/backend/src/models/SerieManager.js @@ -10,22 +10,24 @@ class SerieManager extends AbstractManager { async create({ miniature, title, + VideoUrl, duration, year, description, - IsVailable, + IsAvailable, EpisodesNumber, SeasonsNumber, }) { const [result] = await this.database.query( - `INSERT INTO ${this.table} (miniature, title, duration, year, description, IsVailable, EpisodesNumber, SeasonsNumber) values (?, ?, ?, ?, ?, ?, ?, ?)`, + `INSERT INTO ${this.table} (miniature, title, VideoUrl, duration, year, description, IsAvailable, EpisodesNumber, SeasonsNumber) values (?, ?, ?, ?, ?, ?, ?, ?, ?)`, [ miniature, title, + VideoUrl, duration, year, description, - IsVailable, + IsAvailable, EpisodesNumber, SeasonsNumber, ] @@ -49,24 +51,26 @@ class SerieManager extends AbstractManager { id, miniature, title, + VideoUrl, duration, year, description, - IsVailable, + IsAvailable, EpisodesNumber, SeasonsNumber, }) { const [result] = await this.database.query( - `UPDATE ${this.table} SET miniature = ?, title = ?, duration = ?, year = ?, description = ?, IsVailable = ?, EpisodesNumber = ?, SeasonsNumber = ?, WHERE id = ?` + `UPDATE ${this.table} SET miniature = ?, title = ?, VideoUrl = ?, duration = ?, year = ?, description = ?, IsAvailable = ?, EpisodesNumber = ?, SeasonsNumber = ?, WHERE id = ?` ); [ id, miniature, title, + VideoUrl, duration, year, description, - IsVailable, + IsAvailable, EpisodesNumber, SeasonsNumber, ]; diff --git a/backend/src/router.js b/backend/src/router.js index 7a684a9..6678151 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -9,18 +9,22 @@ const router = express.Router(); // Import itemControllers module for handling item-related operations const categorieControllers = require("./controllers/categorieControllers"); const filmControllers = require("./controllers/filmControllers"); +const userControllers = require("./controllers/userControllers"); // Route to get a list of items router.get("/categories", categorieControllers.browse); router.get("/films", filmControllers.browse); +router.get("/users", userControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); +router.get("/users/:id", userControllers); // Route to add a new item router.post("/categories", categorieControllers.add); router.post("/films", filmControllers.add); +router.post("/users", userControllers.add); /* ************************************************************************* */ diff --git a/package-lock.json b/package-lock.json index d17005d..5ccc7ee 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,6 +9,9 @@ "version": "4.2.0", "hasInstallScript": true, "license": "MIT", + "dependencies": { + "axios": "^1.6.2" + }, "devDependencies": { "concurrently": "^8.2.0", "cross-env": "^7.0.3", @@ -70,6 +73,21 @@ "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==" + }, + "node_modules/axios": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.6.2.tgz", + "integrity": "sha512-7i24Ri4pmDRfJTR7LDBhsOTtcm+9kjX5WiY1X3wIisx6G9So3pfMkEiU7emUBe46oceVImccTEM3k6C5dbVW8A==", + "dependencies": { + "follow-redirects": "^1.15.0", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, "node_modules/braces": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", @@ -246,6 +264,17 @@ "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==", "dev": true }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/commander": { "version": "11.0.0", "resolved": "https://registry.npmjs.org/commander/-/commander-11.0.0.tgz", @@ -347,6 +376,14 @@ } } }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/eastasianwidth": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", @@ -409,6 +446,38 @@ "node": ">=8" } }, + "node_modules/follow-redirects": { + "version": "1.15.3", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.3.tgz", + "integrity": "sha512-1VzOtuEM8pC9SFU1E+8KfTjZyMztRsgEfwQl44z8A25uy13jSzTj6dyK2Df52iV0vgHCfBwLhDWevLn95w5v6Q==", + "funding": [ + { + "type": "individual", + "url": "https://github.com/sponsors/RubenVerborgh" + } + ], + "engines": { + "node": ">=4.0" + }, + "peerDependenciesMeta": { + "debug": { + "optional": true + } + } + }, + "node_modules/form-data": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", + "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/get-caller-file": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", @@ -619,6 +688,25 @@ "node": ">=8.6" } }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/mimic-fn": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-4.0.0.tgz", @@ -712,6 +800,11 @@ "node": ">=0.10" } }, + "node_modules/proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" + }, "node_modules/regenerator-runtime": { "version": "0.14.0", "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.0.tgz", @@ -1133,6 +1226,21 @@ "color-convert": "^2.0.1" } }, + "asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==" + }, + "axios": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/axios/-/axios-1.6.2.tgz", + "integrity": "sha512-7i24Ri4pmDRfJTR7LDBhsOTtcm+9kjX5WiY1X3wIisx6G9So3pfMkEiU7emUBe46oceVImccTEM3k6C5dbVW8A==", + "requires": { + "follow-redirects": "^1.15.0", + "form-data": "^4.0.0", + "proxy-from-env": "^1.1.0" + } + }, "braces": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/braces/-/braces-3.0.2.tgz", @@ -1265,6 +1373,14 @@ "integrity": "sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==", "dev": true }, + "combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "requires": { + "delayed-stream": "~1.0.0" + } + }, "commander": { "version": "11.0.0", "resolved": "https://registry.npmjs.org/commander/-/commander-11.0.0.tgz", @@ -1326,6 +1442,11 @@ "ms": "2.1.2" } }, + "delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==" + }, "eastasianwidth": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/eastasianwidth/-/eastasianwidth-0.2.0.tgz", @@ -1376,6 +1497,21 @@ "to-regex-range": "^5.0.1" } }, + "follow-redirects": { + "version": "1.15.3", + "resolved": "https://registry.npmjs.org/follow-redirects/-/follow-redirects-1.15.3.tgz", + "integrity": "sha512-1VzOtuEM8pC9SFU1E+8KfTjZyMztRsgEfwQl44z8A25uy13jSzTj6dyK2Df52iV0vgHCfBwLhDWevLn95w5v6Q==" + }, + "form-data": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.0.tgz", + "integrity": "sha512-ETEklSGi5t0QMZuiXoA/Q6vcnxcLQP5vdugSpuAyi6SVGi2clPPp+xgEhuMaHC+zGgn31Kd235W35f7Hykkaww==", + "requires": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + } + }, "get-caller-file": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-2.0.5.tgz", @@ -1511,6 +1647,19 @@ "picomatch": "^2.3.1" } }, + "mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==" + }, + "mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "requires": { + "mime-db": "1.52.0" + } + }, "mimic-fn": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-4.0.0.tgz", @@ -1567,6 +1716,11 @@ "integrity": "sha512-eG2dWTVw5bzqGRztnHExczNxt5VGsE6OwTeCG3fdUf9KBsZzO3R5OIIIzWR+iZA0NtZ+RDVdaoE2dK1cn6jH4g==", "dev": true }, + "proxy-from-env": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", + "integrity": "sha512-D+zkORCbA9f1tdWRK0RaCR3GPv50cMxcrz4X8k5LTSUD1Dkw47mKJEZQNunItRTkWwgtaUSo1RVFRIG9ZXiFYg==" + }, "regenerator-runtime": { "version": "0.14.0", "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.14.0.tgz", From 5d81c6a01146fdb05070e3ef8e8f8efcbc5a0b99 Mon Sep 17 00:00:00 2001 From: Alexandre Date: Wed, 13 Dec 2023 10:49:35 +0100 Subject: [PATCH 18/44] merging --- backend/database/schema.sql | 106 ++++++++++----------- backend/src/controllers/filmControllers.js | 6 +- backend/src/models/FilmManager.js | 21 ++-- backend/src/models/SerieManager.js | 14 ++- backend/src/router.js | 4 + 5 files changed, 84 insertions(+), 67 deletions(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 4efc3e1..e392bc9 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -5,13 +5,13 @@ CREATE TABLE `id` int primary key auto_increment not null, `miniature` varchar(255) not null, `title` VARCHAR(50) not NULL, - `video_url` VARCHAR(255) not null + `videoUrl` VARCHAR(255) , `duration` INT not NULL, - `year` DATE not NULL, + `year` VARCHAR(4) not NULL, `description` VARCHAR(500) not NULL, - `is_available` BOOLEAN not NULL, - `episodes_number` INT not NULL, - `seasons_number` INT not NULL + `isAvailable` BOOLEAN not NULL, + `episodesNumber` INT not NULL, + `seasonsNumber` INT not NULL ); DROP TABLE IF EXISTS `User`; @@ -21,7 +21,7 @@ CREATE TABLE `id` int primary key auto_increment not null, `name` varchar(50) not null, `email` varchar(50) not null, - `naissance` DATE NOT NULL, + `naissance` DATETIME NOT NULL, `civility` BOOLEAN NOT NULL, `password` varchar(50) not null, `IsAdmin` bool not null @@ -34,9 +34,9 @@ CREATE TABLE `id` int primary key auto_increment not null, `miniature` VARCHAR(255) not null, `title` VARCHAR(255) not null, - `video_url` VARCHAR(255) not null + `videoUrl` VARCHAR(255) , `duration` INT not null, - `year` DATE NOT NULL, + `year` VARCHAR(4) NOT NULL, `description` VARCHAR(500) not null, `IsAvailable` BOOLEAN NOT NULL ); @@ -54,98 +54,98 @@ DROP TABLE IF EXISTS `Favori_film`; CREATE TABLE `Favori_film` ( - `user_id` INT NOT NULL, - `film_id` INT NOT NULL, - CONSTRAINT FK_Favori_Film_user_id FOREIGN KEY (`user_id`) REFERENCES `User`(`id`), - CONSTRAINT FK_Favori_Film_film_id FOREIGN KEY (`film_id`) REFERENCES `Film`(`id`), - PRIMARY KEY(`user_id`, `film_id`) + `userId` INT NOT NULL, + `filmId` INT NOT NULL, + CONSTRAINT FK_Favori_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), + CONSTRAINT FK_Favori_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), + PRIMARY KEY(`userId`, `filmId`) ); DROP TABLE IF EXISTS `Favori_serie`; CREATE TABLE `Favori_serie` ( - `user_id` INT NOT NULL, - `serie_id` INT NOT NULL, - CONSTRAINT FK_Favori_Serie_user_id FOREIGN KEY (`user_id`) REFERENCES `User`(`id`), - CONSTRAINT FK_Favori_Serie_serie_id FOREIGN KEY (`serie_id`) REFERENCES `Serie`(`id`), - PRIMARY KEY (`user_id`, `serie_id`) + `userId` INT NOT NULL, + `serieId` INT NOT NULL, + CONSTRAINT FK_Favori_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), + CONSTRAINT FK_Favori_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie`(`id`), + PRIMARY KEY (`userId`, `serieId`) ); DROP TABLE IF EXISTS `En_tendance_film`; CREATE TABLE `En_tendance_film` ( - `user_id` INT NOT NULL, - `film_id` INT NOT NULL, - CONSTRAINT FK_En_tendance_Film_user_id FOREIGN KEY (`user_id`) REFERENCES `User`(`id`), - CONSTRAINT FK_En_tendance_Film_film_id FOREIGN KEY (`film_id`) REFERENCES `Film`(`id`), - PRIMARY KEY (`user_id`, `film_id`) + `userId` INT NOT NULL, + `filmId` INT NOT NULL, + CONSTRAINT FK_En_tendance_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), + CONSTRAINT FK_En_tendance_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), + PRIMARY KEY (`userId`, `filmId`) ); DROP TABLE IF EXISTS ` En_tendance_serie`; CREATE TABLE `En_tendance_serie` ( - `user_id` INT NOT NULL, - `serie_id` INT NOT NULL, - CONSTRAINT FK_En_tendance_Serie_user_id FOREIGN KEY (`user_id`) REFERENCES `User`(`id`), - CONSTRAINT FK_En_tendance_Serie_serie_id FOREIGN KEY (`serie_id`) REFERENCES `Serie`(`id`), - PRIMARY KEY (`user_id`, `serie_id`) + `userId` INT NOT NULL, + `serieId` INT NOT NULL, + CONSTRAINT FK_En_tendance_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), + CONSTRAINT FK_En_tendance_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie`(`id`), + PRIMARY KEY (`userId`, `serieId`) ); DROP TABLE IF EXISTS `Commentaire_serie`; CREATE TABLE `Commentaire_serie` ( - `user_id` INT NOT NULL, - `serie_id` INT NOT NULL, - CONSTRAINT FK_Commentaire_Serie_user_id FOREIGN KEY (`user_id`) REFERENCES `User`(`id`), - CONSTRAINT FK_Commentaire_serie_serie_id FOREIGN KEY (`serie_id`) REFERENCES `Serie`(`id`), - PRIMARY KEY (`user_id`, `serie_id`) + `userId` INT NOT NULL, + `serieId` INT NOT NULL, + CONSTRAINT FK_Commentaire_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), + CONSTRAINT FK_Commentaire_serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie`(`id`), + PRIMARY KEY (`userId`, `serieId`) ); DROP TABLE IF EXISTS `Commentaire_film`; CREATE TABLE `Commentaire_film` ( - `user_id` INT NOT NULL, - `film_id` INT NOT NULL, - CONSTRAINT FK_Commentaire_Film_user_id FOREIGN KEY (`user_id`) REFERENCES `User`(`id`), - CONSTRAINT FK_Commentaire_Film_film_id FOREIGN KEY (`film_id`) REFERENCES `Film`(`id`), - PRIMARY KEY (`user_id`, `film_id`) + `userId` INT NOT NULL, + `filmId` INT NOT NULL, + CONSTRAINT FK_Commentaire_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), + CONSTRAINT FK_Commentaire_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), + PRIMARY KEY (`userId`, `filmId`) ); DROP TABLE IF EXISTS `Categorie_par_serie`; CREATE TABLE `Categorie_par_serie` ( - `serie_id` INT NOT NULL, - `categorie_id` INT NOT NULL, - CONSTRAINT FK_Categorie_Par_Serie_serie_id FOREIGN KEY (`serie_id`) REFERENCES `Serie`(`id`), - CONSTRAINT FK_Categorie_Par_Serie_categorie_id FOREIGN KEY (`categorie_id`) REFERENCES `Categorie`(`id`), - PRIMARY KEY (`serie_id`, `categorie_id`) + `serieId` INT NOT NULL, + `categorieId` INT NOT NULL, + CONSTRAINT FK_Categorie_Par_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie`(`id`), + CONSTRAINT FK_Categorie_Par_Serie_categorie_id FOREIGN KEY (`categorieId`) REFERENCES `Categorie`(`id`), + PRIMARY KEY (`serieId`, `categorieId`) ); DROP TABLE IF EXISTS `Categorie_par_film`; CREATE TABLE `Categorie_par_film` ( - `film_id` INT NOT NULL, - `categorie_id` INT NOT NULL, - CONSTRAINT FK_Categorie_Par_Film_film_id FOREIGN KEY (`film_id`) REFERENCES `Film`(`id`), - CONSTRAINT FK_Categorie_Par_Film_categorie_id FOREIGN KEY (`categorie_id`) REFERENCES `Categorie`(`id`), - PRIMARY KEY (`film_id`, `categorie_id`) + `filmId` INT NOT NULL, + `categorieId` INT NOT NULL, + CONSTRAINT FK_Categorie_Par_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), + CONSTRAINT FK_Categorie_Par_Film_categorie_id FOREIGN KEY (`categorieId`) REFERENCES `Categorie`(`id`), + PRIMARY KEY (`filmId`, `categorieId`) ); INSERT INTO - `Film` (`miniature`, `title`, `duration`, `year`, `description`, `is_available`) + `Film` (`miniature`, `title`, `duration`, `year`, `description`, `isAvailable`) VALUES ( 'https://m.media-amazon.com/images/M/MV5BMTc5MDE2ODcwNV5BMl5BanBnXkFtZTgwMzI2NzQ2NzM@._V1_.jpg', 'Avengers: Endgame', 181, - '2019-04-24', + '2019', 'After the devastating events of Avengers: Infinity War (2018), the universe is in ruins. With the help of remaining allies, the Avengers assemble once more in order to reverse Thanos actions and restore balance to the universe.', 1 ), @@ -153,7 +153,7 @@ VALUES 'https://m.media-amazon.com/images/M/MV5BMjMxNjY2MDU1OV5BMl5BanBnXkFtZTgwNzY1MTUwNTM@._V1_.jpg', 'Avengers: Infinity War', 149, - '2018-04-25', + '2018', 'The Avengers and their allies must be willing to sacrifice all in an attempt to defeat the powerful Thanos before his blitz of devastation and ruin puts an end to the universe.', 0 ), @@ -161,7 +161,7 @@ VALUES 'https://m.media-amazon.com/images/M/MV5BNDYxNjQyMjAtNTdiOS00NGYwLWFmNTAtNThmYjU5ZGI2YTI1XkEyXkFqcGdeQXVyMTMxODk2OTU@._V1_.jpg', 'The Avengers', 143, - '2012-04-25', + '2012', 'Earth mightiest heroes must come together and learn to fight as a team if they are going to stop the mischievous Loki and his alien army from enslaving humanity.', 1 ), @@ -169,7 +169,7 @@ VALUES 'https://static.wikia.nocookie.net/ironman/images/d/da/P170620_v_v8_ba.jpg/revision/latest?cb=20191202183622', 'Iron man', 126, - '2008-04-30', + '2008', 'After being held captive in an Afghan cave, billionaire engineer Tony Stark creates a unique weaponized suit of armor to fight evil.', 0 ); diff --git a/backend/src/controllers/filmControllers.js b/backend/src/controllers/filmControllers.js index b8526c6..86cf61f 100644 --- a/backend/src/controllers/filmControllers.js +++ b/backend/src/controllers/filmControllers.js @@ -11,7 +11,7 @@ const browse = async (req, res, next) => { const read = async (req, res, next) => { try { - const film = await tables.item.read(req.params.id); + const film = await tables.film.read(req.params.id); if (film == null) { res.sendStatus(404); } else { @@ -23,11 +23,11 @@ const read = async (req, res, next) => { }; const edit = async (req, res, next) => { - const { id } = req.params.id; + const { id } = req.params; req.body.id = id; try { const result = await tables.film.update(req.body); - if (result.affectedRows) { + if (result) { res.json(result); res.sendStatus(204); } else { diff --git a/backend/src/models/FilmManager.js b/backend/src/models/FilmManager.js index aa61283..7d1cbe4 100644 --- a/backend/src/models/FilmManager.js +++ b/backend/src/models/FilmManager.js @@ -5,10 +5,18 @@ class FilmManager extends AbstractManager { super({ table: "film" }); } - async create({ miniature, title, duration, year, description, IsAvailable }) { + async create({ + miniature, + title, + videoUrl, + duration, + year, + description, + isAvailable, + }) { const [result] = await this.database.query( - `insert into ${this.table} (miniature, title, duration, year, description, is_available) values (?,?,?,?,?,?)`, - [miniature, title, duration, year, description, IsAvailable] + `insert into ${this.table} (miniature, title, videoUrl, duration, year, description, isAvailable) values (?,?,?,?,?,?)`, + [miniature, title, videoUrl, duration, year, description, isAvailable] ); return result.insertId; } @@ -30,14 +38,15 @@ class FilmManager extends AbstractManager { id, miniature, title, + videoUrl, duration, year, description, - IsAvailable, + isAvailable, }) { const [result] = await this.database.query( - `update ${this.table} SET miniature=? title=? duration=? year=? description=? IsAvailable=? where id=?`, - [miniature, title, duration, year, description, IsAvailable, id] + `update ${this.table} SET miniature=?, title=?, videoUrl=?, duration=?, year=?, description=?, isAvailable=? where id=?`, + [miniature, title, videoUrl, duration, year, description, isAvailable, id] ); return result.affectedRows; } diff --git a/backend/src/models/SerieManager.js b/backend/src/models/SerieManager.js index f68599c..b39c872 100644 --- a/backend/src/models/SerieManager.js +++ b/backend/src/models/SerieManager.js @@ -10,18 +10,20 @@ class SerieManager extends AbstractManager { async create({ miniature, title, + videoUrl, duration, year, description, - IsVailable, - EpisodesNumber, - SeasonsNumber, + isAvailable, + episodesNumber, + seasonsNumber, }) { const [result] = await this.database.query( - `INSERT INTO ${this.table} (miniature, title, duration, year, description, IsVailable, EpisodesNumber, SeasonsNumber) values (?, ?, ?, ?, ?, ?, ?, ?)`, + `INSERT INTO ${this.table} (miniature, title, videoUrl, duration, year, description, isAvailable, episodesNumber, seasonsNumber) values (?, ?, ?, ?, ?, ?, ?, ?)`, [ miniature, title, + videoUrl, duration, year, description, @@ -49,6 +51,7 @@ class SerieManager extends AbstractManager { id, miniature, title, + videoUrl, duration, year, description, @@ -57,12 +60,13 @@ class SerieManager extends AbstractManager { SeasonsNumber, }) { const [result] = await this.database.query( - `UPDATE ${this.table} SET miniature = ?, title = ?, duration = ?, year = ?, description = ?, IsVailable = ?, EpisodesNumber = ?, SeasonsNumber = ?, WHERE id = ?` + `UPDATE ${this.table} SET miniature = ?, title = ?, videoUrl = ?, duration = ?, year = ?, description = ?, IsVailable = ?, EpisodesNumber = ?, SeasonsNumber = ?, WHERE id = ?` ); [ id, miniature, title, + videoUrl, duration, year, description, diff --git a/backend/src/router.js b/backend/src/router.js index 7a684a9..18a57f7 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -18,10 +18,14 @@ router.get("/films", filmControllers.browse); router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); +// Route to edit a specific item by ID +router.put("/films/:id", filmControllers.edit); // Route to add a new item router.post("/categories", categorieControllers.add); router.post("/films", filmControllers.add); +// Route to detele a specific item by ID +router.delete("/films/:id", filmControllers.destroy); /* ************************************************************************* */ module.exports = router; From 154e055730ac1b138ecc94537a7929d7f31c260b Mon Sep 17 00:00:00 2001 From: Alexandre Date: Wed, 13 Dec 2023 10:51:14 +0100 Subject: [PATCH 19/44] update film ok --- backend/src/models/SerieManager.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/backend/src/models/SerieManager.js b/backend/src/models/SerieManager.js index b39c872..12bbf56 100644 --- a/backend/src/models/SerieManager.js +++ b/backend/src/models/SerieManager.js @@ -55,9 +55,9 @@ class SerieManager extends AbstractManager { duration, year, description, - IsVailable, - EpisodesNumber, - SeasonsNumber, + isAvailable, + episodesNumber, + seasonsNumber, }) { const [result] = await this.database.query( `UPDATE ${this.table} SET miniature = ?, title = ?, videoUrl = ?, duration = ?, year = ?, description = ?, IsVailable = ?, EpisodesNumber = ?, SeasonsNumber = ?, WHERE id = ?` From 24146bc695dfeb6af74b71a611e5f6c3d71cdb90 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Wed, 13 Dec 2023 10:54:29 +0100 Subject: [PATCH 20/44] pending... --- backend/database/schema.sql | 94 ++++------------------ backend/src/controllers/filmControllers.js | 2 +- 2 files changed, 18 insertions(+), 78 deletions(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 4efc3e1..6b32b84 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -2,29 +2,29 @@ DROP TABLE IF EXISTS `Serie`; CREATE TABLE `Serie` ( - `id` int primary key auto_increment not null, - `miniature` varchar(255) not null, - `title` VARCHAR(50) not NULL, - `video_url` VARCHAR(255) not null - `duration` INT not NULL, - `year` DATE not NULL, - `description` VARCHAR(500) not NULL, - `is_available` BOOLEAN not NULL, - `episodes_number` INT not NULL, - `seasons_number` INT not NULL + `id` INT PRIMARY KEY AUTO_INCREMENT NOT NULL, + `miniature` VARCHAR(255) NOT NULL, + `title` VARCHAR(50) NOT NULL, + `video_url` VARCHAR(255) NOT null, + `duration` INT NOT NULL, + `year` DATE NOT NULL, + `description` VARCHAR(500) NOT NULL, + `is_available` BOOLEAN NOT NULL, + `episodes_number` INT NOT NULL, + `seasons_number` INT NOT NULL ); DROP TABLE IF EXISTS `User`; CREATE TABLE `User` ( - `id` int primary key auto_increment not null, - `name` varchar(50) not null, - `email` varchar(50) not null, + `id` INT PRIMARY KEY AUTO_INCREMENT NOT NULL, + `name` VARCHAR(50) NOT NULL, + `email` VARCHAR(50) NOT NULL, `naissance` DATE NOT NULL, - `civility` BOOLEAN NOT NULL, - `password` varchar(50) not null, - `IsAdmin` bool not null + `civility` TINYINT(1) NOT NULL, + `password` VARCHAR(50) NOT NULL, + `is_admin` TINYINT(1) not null ); DROP TABLE IF EXISTS `Film`; @@ -136,64 +136,4 @@ CREATE TABLE CONSTRAINT FK_Categorie_Par_Film_film_id FOREIGN KEY (`film_id`) REFERENCES `Film`(`id`), CONSTRAINT FK_Categorie_Par_Film_categorie_id FOREIGN KEY (`categorie_id`) REFERENCES `Categorie`(`id`), PRIMARY KEY (`film_id`, `categorie_id`) - ); - -INSERT INTO - `Film` (`miniature`, `title`, `duration`, `year`, `description`, `is_available`) -VALUES - ( - 'https://m.media-amazon.com/images/M/MV5BMTc5MDE2ODcwNV5BMl5BanBnXkFtZTgwMzI2NzQ2NzM@._V1_.jpg', - 'Avengers: Endgame', - 181, - '2019-04-24', - 'After the devastating events of Avengers: Infinity War (2018), the universe is in ruins. With the help of remaining allies, the Avengers assemble once more in order to reverse Thanos actions and restore balance to the universe.', - 1 - ), - ( - 'https://m.media-amazon.com/images/M/MV5BMjMxNjY2MDU1OV5BMl5BanBnXkFtZTgwNzY1MTUwNTM@._V1_.jpg', - 'Avengers: Infinity War', - 149, - '2018-04-25', - 'The Avengers and their allies must be willing to sacrifice all in an attempt to defeat the powerful Thanos before his blitz of devastation and ruin puts an end to the universe.', - 0 - ), - ( - 'https://m.media-amazon.com/images/M/MV5BNDYxNjQyMjAtNTdiOS00NGYwLWFmNTAtNThmYjU5ZGI2YTI1XkEyXkFqcGdeQXVyMTMxODk2OTU@._V1_.jpg', - 'The Avengers', - 143, - '2012-04-25', - 'Earth mightiest heroes must come together and learn to fight as a team if they are going to stop the mischievous Loki and his alien army from enslaving humanity.', - 1 - ), - ( - 'https://static.wikia.nocookie.net/ironman/images/d/da/P170620_v_v8_ba.jpg/revision/latest?cb=20191202183622', - 'Iron man', - 126, - '2008-04-30', - 'After being held captive in an Afghan cave, billionaire engineer Tony Stark creates a unique weaponized suit of armor to fight evil.', - 0 - ); - -INSERT INTO - `Categorie` (`name`, `position`) -VALUES - ('Action', 1), - ('Adventure', 2), - ('Sci-Fi', 3), - ('Drama', 4), - ('Thriller', 5), - ('Comedy', 6), - ('Crime', 7), - ('Fantasy', 8), - ('Mystery', 9), - ('Animation', 10), - ('Family', 11), - ('Biography', 12), - ('History', 13), - ('Horror', 14), - ('Music', 15), - ('Musical', 16), - ('Romance', 17), - ('Sport', 18), - ('War', 19), - ('Western', 20); + ); \ No newline at end of file diff --git a/backend/src/controllers/filmControllers.js b/backend/src/controllers/filmControllers.js index b8526c6..d3013bc 100644 --- a/backend/src/controllers/filmControllers.js +++ b/backend/src/controllers/filmControllers.js @@ -11,7 +11,7 @@ const browse = async (req, res, next) => { const read = async (req, res, next) => { try { - const film = await tables.item.read(req.params.id); + const film = await tables.film.read(req.params.id); if (film == null) { res.sendStatus(404); } else { From 6f1f05bd6fad2a5a4b4beb91da9a7c36ba4802ee Mon Sep 17 00:00:00 2001 From: Alexandre Date: Wed, 13 Dec 2023 11:13:33 +0100 Subject: [PATCH 21/44] crud_film done --- backend/src/controllers/filmControllers.js | 2 +- backend/src/models/FilmManager.js | 6 +++--- backend/src/router.js | 17 ++++++----------- 3 files changed, 10 insertions(+), 15 deletions(-) diff --git a/backend/src/controllers/filmControllers.js b/backend/src/controllers/filmControllers.js index 86cf61f..89dc04c 100644 --- a/backend/src/controllers/filmControllers.js +++ b/backend/src/controllers/filmControllers.js @@ -50,7 +50,7 @@ const add = async (req, res, next) => { }; const destroy = async (req, res, next) => { - const { id } = req.params.id; + const { id } = req.params; try { const result = await tables.film.delete(id); if (result.affectedRows) { diff --git a/backend/src/models/FilmManager.js b/backend/src/models/FilmManager.js index 7d1cbe4..35d746a 100644 --- a/backend/src/models/FilmManager.js +++ b/backend/src/models/FilmManager.js @@ -15,7 +15,7 @@ class FilmManager extends AbstractManager { isAvailable, }) { const [result] = await this.database.query( - `insert into ${this.table} (miniature, title, videoUrl, duration, year, description, isAvailable) values (?,?,?,?,?,?)`, + `insert into ${this.table} (miniature, title, videoUrl, duration, year, description, isAvailable) values (?,?,?,?,?,?,?)`, [miniature, title, videoUrl, duration, year, description, isAvailable] ); return result.insertId; @@ -52,8 +52,8 @@ class FilmManager extends AbstractManager { } async delete(id) { - const [result] = await this.database.query( - `delete * from ${this.table} where id = ?`, + const result = await this.database.query( + `delete from ${this.table} where id = ?`, [id] ); return result; diff --git a/backend/src/router.js b/backend/src/router.js index e897190..93b68d8 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -14,30 +14,25 @@ const serieControllers = require("./controllers/serieControllers"); // Route to get a list of items router.get("/categories", categorieControllers.browse); router.get("/films", filmControllers.browse); -router.get("/serie", serieControllers.browse); +router.get("/series", serieControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); -router.get("/serie/:id", serieControllers.read); +router.get("/series/:id", serieControllers.read); // Route to edit a specific item by ID router.put("/films/:id", filmControllers.edit); +router.put("/series/:id", serieControllers.edit); + // Route to add a new item router.post("/categories", categorieControllers.add); router.post("/films", filmControllers.add); -router.post("/serie", serieControllers.add); - -// Route to Update a new item - -router.update("/serie", serieControllers.edit); - -// Route to Delete a new item - -router.delete("/serie", serieControllers.destroy); +router.post("/series", serieControllers.add); // Route to detele a specific item by ID router.delete("/films/:id", filmControllers.destroy); +router.delete("/series/:id", serieControllers.destroy); /* ************************************************************************* */ module.exports = router; From 8f26824bf8248483f74902cd6c8c66e7b48d0642 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Wed, 13 Dec 2023 11:45:42 +0100 Subject: [PATCH 22/44] working on backend controllers and managers --- .../src/controllers/categorieControllers.js | 82 ++++++++++++++----- .../categorieParFilmControllers.js | 0 backend/src/models/CategorieManager.js | 10 +-- backend/src/router.js | 12 ++- 4 files changed, 76 insertions(+), 28 deletions(-) create mode 100644 backend/src/controllers/categorieParFilmControllers.js diff --git a/backend/src/controllers/categorieControllers.js b/backend/src/controllers/categorieControllers.js index 79b1134..be0d6fc 100644 --- a/backend/src/controllers/categorieControllers.js +++ b/backend/src/controllers/categorieControllers.js @@ -2,52 +2,75 @@ const tables = require("../tables"); // The B of BREAD - Browse (Read All) operation -const browse = async (req, res, next) => { +const browse = async (request, response, next) => { try { // Fetch all items from the database - const items = await tables.categorie.readAll(); + const categories = await tables.categorie.readAll(); // Respond with the items in JSON format - res.json(items); - } catch (err) { + response.json(categories); + } catch (error) { // Pass any errors to the error-handling middleware - next(err); + next(error); } }; // The R of BREAD - Read operation -const read = async (req, res, next) => { +const read = async (request, response, next) => { try { // Fetch a specific item from the database based on the provided ID - const item = await tables.categorie.read(req.params.id); + const categorie = await tables.categorie.read(request.params.id); // If the item is not found, respond with HTTP 404 (Not Found) // Otherwise, respond with the item in JSON format - if (item == null) { - res.sendStatus(404); + if (categorie == null) { + response.sendStatus(404); } else { - res.json(item); + response.json(categorie); } - } catch (err) { + } catch (error) { // Pass any errors to the error-handling middleware - next(err); + next(error); } }; // The E of BREAD - Edit (Update) operation -// This operation is not yet implemented +const edit = async (request, response, next) => { + // Extract the ID of the item to be updated from the request parameters + const { id } = request.params; + + // Add the ID to the item data extracted from the request body + request.body.id = id; + + try { + // Update the item in the database + const result = await tables.categorie.update(request.body); + + // If the item is not found, respond with HTTP 404 (Not Found) + // Otherwise, respond with HTTP 204 (No Content) + if (result) { + response.json(result); + response.sendStatus(204); + } else { + response.sendStatus(404); + } + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; // The A of BREAD - Add (Create) operation -const add = async (req, res, next) => { +const add = async (request, response, next) => { // Extract the item data from the request body - const item = req.body; + const categorie = request.body; try { // Insert the item into the database - const insertId = await tables.categorie.create(item); + const insertId = await tables.categorie.create(categorie); // Respond with HTTP 201 (Created) and the ID of the newly inserted item - res.status(201).json({ insertId }); + response.status(201).json({ insertId }); } catch (err) { // Pass any errors to the error-handling middleware next(err); @@ -55,13 +78,32 @@ const add = async (req, res, next) => { }; // The D of BREAD - Destroy (Delete) operation -// This operation is not yet implemented +const destroy = async (request, response, next) => { + // Extract the ID of the item to be deleted from the request parameters + const { id } = request.params.id; + + try { + // Delete the item from the database + const result = await tables.categorie.delete(id); + + // If the item is not found, respond with HTTP 404 (Not Found) + // Otherwise, respond with HTTP 200 (OK) + if (result.affectedRows) { + response.sendStatus(200); + } else { + response.sendStatus(404); + } + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; // Ready to export the controller functions module.exports = { browse, read, - // edit, + edit, add, - // destroy, + destroy, }; diff --git a/backend/src/controllers/categorieParFilmControllers.js b/backend/src/controllers/categorieParFilmControllers.js new file mode 100644 index 0000000..e69de29 diff --git a/backend/src/models/CategorieManager.js b/backend/src/models/CategorieManager.js index d81fb51..8d9c4cf 100644 --- a/backend/src/models/CategorieManager.js +++ b/backend/src/models/CategorieManager.js @@ -9,11 +9,11 @@ class CategorieManager extends AbstractManager { // The C of CRUD - Create operation - async create(categorie) { + async create({ name, position }) { // Execute the SQL INSERT query to add a new categorie to the "categorie" table const [result] = await this.database.query( `insert into ${this.table} (name, position) values (?, ?)`, - [categorie.name, categorie.position] + [name, position] ); // Return the ID of the newly inserted categorie @@ -44,11 +44,11 @@ class CategorieManager extends AbstractManager { // The U of CRUD - Update operation // ^ Implemented the update operation to modify an existing categorie - async update(categorie) { + async update({ id, name, position }) { // Execute the SQL UPDATE query to modify an existing categorie const [result] = await this.database.query( `update ${this.table} set name = ?, position = ? where id = ?`, - [categorie.name, categorie.position, categorie.id] + [name, position, id] ); // Return the number of affected rows @@ -66,7 +66,7 @@ class CategorieManager extends AbstractManager { ); // Return the number of affected rows - return result.affectedRows; + return result; } } diff --git a/backend/src/router.js b/backend/src/router.js index e897190..eb12cdf 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -10,33 +10,39 @@ const router = express.Router(); const categorieControllers = require("./controllers/categorieControllers"); const filmControllers = require("./controllers/filmControllers"); const serieControllers = require("./controllers/serieControllers"); +const categorieParFilmControllers = require("./controllers/categorieParFilmControllers"); // Route to get a list of items router.get("/categories", categorieControllers.browse); router.get("/films", filmControllers.browse); router.get("/serie", serieControllers.browse); +router.get("/categorieParFilm", categorieParFilmControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); router.get("/serie/:id", serieControllers.read); +router.get("/categorieParFilm/:id", categorieParFilmControllers.read); // Route to edit a specific item by ID +router.put("/categories/:id", categorieControllers.edit); router.put("/films/:id", filmControllers.edit); + // Route to add a new item router.post("/categories", categorieControllers.add); router.post("/films", filmControllers.add); router.post("/serie", serieControllers.add); // Route to Update a new item - +router.update("/categories", categorieControllers.edit); router.update("/serie", serieControllers.edit); // Route to Delete a new item - +router.delete("/categories", categorieControllers.destroy); router.delete("/serie", serieControllers.destroy); -// Route to detele a specific item by ID +// Route to delete a specific item by ID +router.delete("/categories/:id", categorieControllers.destroy); router.delete("/films/:id", filmControllers.destroy); /* ************************************************************************* */ From 4bf25adea3d104eeadb3910d884788597aef642e Mon Sep 17 00:00:00 2001 From: Alexandre Date: Wed, 13 Dec 2023 11:59:59 +0100 Subject: [PATCH 23/44] merging --- backend/src/controllers/favoriFilmControllers.js | 0 backend/src/models/FavoriFilmManager.js | 8 ++++++++ 2 files changed, 8 insertions(+) create mode 100644 backend/src/controllers/favoriFilmControllers.js create mode 100644 backend/src/models/FavoriFilmManager.js diff --git a/backend/src/controllers/favoriFilmControllers.js b/backend/src/controllers/favoriFilmControllers.js new file mode 100644 index 0000000..e69de29 diff --git a/backend/src/models/FavoriFilmManager.js b/backend/src/models/FavoriFilmManager.js new file mode 100644 index 0000000..dc0e8e0 --- /dev/null +++ b/backend/src/models/FavoriFilmManager.js @@ -0,0 +1,8 @@ +const AbstractManager = require("./AbstractManager"); + +class FavoriFilmManager extends AbstractManager { + constructor() { + super({ table: "favori_film" }); + } +} +module.exports = FavoriFilmManager; From 026d91f9061fe27ad7ea30010549e5f73255fb26 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Wed, 13 Dec 2023 13:33:15 +0100 Subject: [PATCH 24/44] trying to do JOIN SQL request... --- .../categorieParFilmControllers.js | 81 +++++++++++++++++++ backend/src/models/CategorieParFilmManager.js | 60 ++++++++++++++ backend/src/router.js | 20 ++++- backend/src/tables.js | 2 + 4 files changed, 161 insertions(+), 2 deletions(-) create mode 100644 backend/src/models/CategorieParFilmManager.js diff --git a/backend/src/controllers/categorieParFilmControllers.js b/backend/src/controllers/categorieParFilmControllers.js index e69de29..61d62e6 100644 --- a/backend/src/controllers/categorieParFilmControllers.js +++ b/backend/src/controllers/categorieParFilmControllers.js @@ -0,0 +1,81 @@ +// Import access to database tables +const tables = require("../tables"); + +// The B of BREAD - Browse (Read All) operation +const browseCategoriesForSpecificFilm = async (request, response, next) => { + try { + // Fetch all items from the database + const categories = + await tables.categorieParFilm.readAllCategoriesForSpecificFilm( + request.params.id + ); + + // Respond with the items in JSON format + response.json(categories); + } catch (error) { + // Pass any errors to the error-handling middleware + next(error); + } +}; + +const browseFilmsForSpecificCategorie = async (request, response, next) => { + try { + // Fetch all items from the database + const films = + await tables.categorieParFilm.readAllFilmsForSpecificCategorie( + request.params.id + ); + + // Respond with the items in JSON format + response.json(films); + } catch (error) { + // Pass any errors to the error-handling middleware + next(error); + } +}; + +// The A of BREAD - Add operation +const add = async (request, response, next) => { + const { filmId, categorieId } = request.body; + + try { + // Insert the new item into the database + const id = await tables.categorieParFilm.create({ filmId, categorieId }); + + // Fetch the newly created item from the database + const categorieParFilm = await tables.categorieParFilm.read(id); + + // Respond with the newly created item in JSON format + response.json(categorieParFilm); + } catch (error) { + // Pass any errors to the error-handling middleware + next(error); + } +}; + +// The D of BREAD - Delete operation +const destroy = async (request, response, next) => { + try { + // Delete the item from the database + const result = await tables.categorieParFilm.delete(request.params.id); + + // If the item is not found, respond with HTTP 404 (Not Found) + // Otherwise, respond with HTTP 204 (No Content) + if (result) { + response.sendStatus(204); + } else { + response.sendStatus(404); + } + } catch (error) { + // Pass any errors to the error-handling middleware + next(error); + } +}; + +// Ready to export the controller functions +module.exports = { + browseCategoriesForSpecificFilm, + browseFilmsForSpecificCategorie, + add, + destroy, +}; diff --git a/backend/src/models/CategorieParFilmManager.js b/backend/src/models/CategorieParFilmManager.js new file mode 100644 index 0000000..036dcbb --- /dev/null +++ b/backend/src/models/CategorieParFilmManager.js @@ -0,0 +1,60 @@ +const AbstractManager = require("./AbstractManager"); + +class CategorieParFilmManager extends AbstractManager { + constructor() { + // Call the constructor of the parent class (AbstractManager) + // and pass the table name "categorieParFilm" as configuration + super({ table: "categorieParFilm" }); + } + + // The C of CRUD - Create operation + async create({ filmId, categorieId }) { + // Execute the SQL INSERT query to add a new categorieParFilm to the "categorieParFilm" table + const [result] = await this.database.query( + `insert into ${this.table} (filmId, categorieId) values (?, ?)`, + [filmId, categorieId] + ); + + // Return the ID of the newly inserted categorieParFilm + return result.insertId; + } + + // The Rs of CRUD - Read operations + // ? get all categories for a specific film + async readAllCategoriesForSpecificFilm(idFilm) { + // Execute the SQL SELECT query to retrieve all categories from the "categorie" table + const [rows] = await this.database.query( + `select categorie.name from categorie inner join ${this.table} on categorie.id = ${this.table}.categorieId where ${this.table}.filmId = ?`, + [idFilm] + ); + // Return the array of categories + return rows; + } + + // ? get all films for a specific categorie + async readAllFilmsForSpecificCategorie(idCategorie) { + // Execute the SQL SELECT query to retrieve all categories from the "categorie" table + const [rows] = await this.database.query( + `select film.title from film inner join ${this.table} on film.id = ${this.table}.filmId where ${this.table}.categorieId = ?`, + [idCategorie] + ); + // Return the array of categories + return rows; + } + + // The D of CRUD - Delete operation + + async delete({ filmId, categorieId }) { + // Execute the SQL DELETE query to remove an categorieParFilm by its ID + const [result] = await this.database.query( + `delete from ${this.table} where filmId = ? and categorieId = ?`, + [filmId, categorieId] + ); + + // Return the number of affected rows + return result.affectedRows; + } +} + +// Ready to export the manager +module.exports = CategorieParFilmManager; diff --git a/backend/src/router.js b/backend/src/router.js index 7507c68..9a6239a 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -16,13 +16,11 @@ const categorieParFilmControllers = require("./controllers/categorieParFilmContr router.get("/categories", categorieControllers.browse); router.get("/films", filmControllers.browse); router.get("/series", serieControllers.browse); -router.get("/categorieParFilm", categorieParFilmControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); router.get("/series/:id", serieControllers.read); -router.get("/categorieParFilm/:id", categorieParFilmControllers.read); // Route to edit a specific item by ID router.put("/categories/:id", categorieControllers.edit); @@ -38,6 +36,24 @@ router.post("/series", serieControllers.add); router.delete("/categories/:id", categorieControllers.destroy); router.delete("/films/:id", filmControllers.destroy); router.delete("/series/:id", serieControllers.destroy); + +// Route to get all categories for a specific film +router.get( + "/categoriesForFilm/", + categorieParFilmControllers.browseCategoriesForSpecificFilm +); + +// Route to get all films for a specific categorie +router.get( + "/filmsForCategorie/", + categorieParFilmControllers.browseFilmsForSpecificCategorie +); + +// Route to add a new categorieParFilm +router.post("/categoriesParFilm", categorieParFilmControllers.add); + +// Route to delete a specific categorieParFilm +router.delete("/categoriesParFilm/:id", categorieParFilmControllers.destroy); /* ************************************************************************* */ module.exports = router; diff --git a/backend/src/tables.js b/backend/src/tables.js index d6d1def..9e478ce 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -7,12 +7,14 @@ const CategorieManager = require("./models/CategorieManager"); const UserManager = require("./models/UserManager"); const FilmManager = require("./models/FilmManager"); const SerieManager = require("./models/SerieManager"); +const CategorieParFilmManager = require("./models/CategorieParFilmManager"); const managers = [ CategorieManager, UserManager, FilmManager, SerieManager, + CategorieParFilmManager, // Add other managers here ]; From b6cba8dd6721be55bd55625484504c545cbf56b9 Mon Sep 17 00:00:00 2001 From: Techer Tony Date: Wed, 13 Dec 2023 15:05:48 +0100 Subject: [PATCH 25/44] toutes les routes series fonctionnent :) --- backend/src/controllers/serieControllers.js | 6 +-- backend/src/models/SerieManager.js | 46 +++++++++++---------- 2 files changed, 27 insertions(+), 25 deletions(-) diff --git a/backend/src/controllers/serieControllers.js b/backend/src/controllers/serieControllers.js index e6d53b2..af24827 100644 --- a/backend/src/controllers/serieControllers.js +++ b/backend/src/controllers/serieControllers.js @@ -23,11 +23,11 @@ const read = async (req, res, next) => { }; const edit = async (req, res, next) => { - const { id } = req.params.id; + const { id } = req.params; req.body.id = id; try { const result = await tables.serie.update(req.body); - if (result.affectedRows) { + if (result) { res.json(result); res.sendStatus(204); } else { @@ -50,7 +50,7 @@ const add = async (req, res, next) => { }; const destroy = async (req, res, next) => { - const { id } = req.params.id; + const { id } = req.params; try { const result = await tables.serie.delete(id); if (result.affectedRows) { diff --git a/backend/src/models/SerieManager.js b/backend/src/models/SerieManager.js index 12bbf56..c0be0a7 100644 --- a/backend/src/models/SerieManager.js +++ b/backend/src/models/SerieManager.js @@ -4,7 +4,7 @@ const AbstractManager = require("./AbstractManager"); class SerieManager extends AbstractManager { constructor() { - super({ table: "Serie" }); + super({ table: "serie" }); } async create({ @@ -19,7 +19,7 @@ class SerieManager extends AbstractManager { seasonsNumber, }) { const [result] = await this.database.query( - `INSERT INTO ${this.table} (miniature, title, videoUrl, duration, year, description, isAvailable, episodesNumber, seasonsNumber) values (?, ?, ?, ?, ?, ?, ?, ?)`, + `INSERT INTO ${this.table} (miniature, title, videoUrl, duration, year, description, isAvailable, episodesNumber, seasonsNumber) values (?, ?, ?, ?, ?, ?, ?, ?, ?)`, [ miniature, title, @@ -27,9 +27,9 @@ class SerieManager extends AbstractManager { duration, year, description, - IsVailable, - EpisodesNumber, - SeasonsNumber, + isAvailable, + episodesNumber, + seasonsNumber, ] ); return result; @@ -42,6 +42,7 @@ class SerieManager extends AbstractManager { ); return result; } + async readAll() { const [result] = await this.database.query(`select * from ${this.table} `); return result; @@ -60,26 +61,27 @@ class SerieManager extends AbstractManager { seasonsNumber, }) { const [result] = await this.database.query( - `UPDATE ${this.table} SET miniature = ?, title = ?, videoUrl = ?, duration = ?, year = ?, description = ?, IsVailable = ?, EpisodesNumber = ?, SeasonsNumber = ?, WHERE id = ?` + `UPDATE ${this.table} SET miniature=?, title=?, videoUrl=?, duration=?, year=?, description=?, isAvailable=?, episodesNumber=?, seasonsNumber=? WHERE id=?`, + [ + miniature, + title, + videoUrl, + duration, + year, + description, + isAvailable, + episodesNumber, + seasonsNumber, + id, + ] ); - [ - id, - miniature, - title, - videoUrl, - duration, - year, - description, - IsVailable, - EpisodesNumber, - SeasonsNumber, - ]; - return result; + return result.affectedRows; } async delete(id) { - const [result] = await this.database.query( - `delete from ${this.table} where id = ?,` - )[id]; + const result = await this.database.query( + `delete from ${this.table} where id = ?`, + [id] + ); return result; } } From 358f9e1fc98d38c077c8af4189e62eb383002801 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Wed, 13 Dec 2023 16:00:36 +0100 Subject: [PATCH 26/44] creating react routes --- frontend/src/App.jsx | 121 ++-------------------- frontend/src/main.jsx | 16 +++ frontend/src/pages/Home.jsx | 97 ++++++++++++++++++ frontend/src/pages/Search.jsx | 21 ++++ frontend/src/sass/_app.scss | 171 +------------------------------ frontend/src/sass/_home.scss | 178 +++++++++++++++++++++++++++++++++ frontend/src/sass/_search.scss | 36 +++++++ frontend/src/sass/index.scss | 2 + frontend/vite.config.js | 4 +- 9 files changed, 364 insertions(+), 282 deletions(-) create mode 100644 frontend/src/pages/Home.jsx create mode 100644 frontend/src/pages/Search.jsx create mode 100644 frontend/src/sass/_home.scss create mode 100644 frontend/src/sass/_search.scss diff --git a/frontend/src/App.jsx b/frontend/src/App.jsx index df4a6fe..415f2eb 100644 --- a/frontend/src/App.jsx +++ b/frontend/src/App.jsx @@ -1,136 +1,37 @@ -import { useEffect, useState } from "react"; -import axios from "axios"; // eslint-disable-line +import { NavLink, Outlet } from "react-router-dom"; function App() { - const [movies, setMovies] = useState([]); - - useEffect(() => { - axios - .get("http://localhost:3310/api/films") - .then((response) => { - setMovies(response.data); - console.info(response.data); - }) - .catch((error) => { - console.error(error); - }); - }, []); return ( -
-
-
- wildtube logo -
- {/*
-
*/} -
    -
  • -

    Toutes les catégories

    -
  • -
  • -

    Action

    -
  • -
  • -

    Aventure

    -
  • -
  • -

    Comédie

    -
  • -
  • -

    Romance

    -
  • -
  • -

    Science-fiction

    -
  • -
-
-
-

Action

-

Voir tout

-
-
- movie slide -
- movie slide -
-
- lock icon -
-
-
- {movies.map((movie) => { - if (movie.is_available) { - return ( - {movie.title} - ); - } - - return ( -
- {movie.title} -
-
- lock icon -
-
-
- ); - })} -
-
-
+
+
-
+ home icon -
+
-
+ search icon -
+
-
-
+ {/*
+ profile icon -
-
+ +
*/}
); diff --git a/frontend/src/main.jsx b/frontend/src/main.jsx index ae981ac..997c47e 100644 --- a/frontend/src/main.jsx +++ b/frontend/src/main.jsx @@ -2,12 +2,28 @@ import React from "react"; import ReactDOM from "react-dom/client"; import { createBrowserRouter, RouterProvider } from "react-router-dom"; import App from "./App"; +import Home from "./pages/Home"; +import Search from "./pages/Search"; import "./sass/index.scss"; const router = createBrowserRouter([ { path: "/", element: , + children: [ + { + index: true, + element: , + }, + { + path: "search", + element: , + }, + // { + // path: "profile", + // element:

Profile

, + // }, + ], }, ]); diff --git a/frontend/src/pages/Home.jsx b/frontend/src/pages/Home.jsx new file mode 100644 index 0000000..c25e757 --- /dev/null +++ b/frontend/src/pages/Home.jsx @@ -0,0 +1,97 @@ +import { useEffect, useState } from "react"; +import axios from "axios"; // eslint-disable-line + +function Home() { + const [movies, setMovies] = useState([]); + + useEffect(() => { + axios + .get("http://localhost:3310/api/films") + .then((response) => { + setMovies(response.data); + console.info(response.data); + }) + .catch((error) => { + console.error(error); + }); + }, []); + return ( +
+
+
+ wildtube logo +
+ {/*
+
*/} + {/*
    +
  • +

    Toutes les catégories

    +
  • +
  • +

    Action

    +
  • +
  • +

    Aventure

    +
  • +
  • +

    Comédie

    +
  • +
  • +

    Romance

    +
  • +
  • +

    Science-fiction

    +
  • +
*/} +
+ {/*
+

Action

+

Voir tout

+
*/} +
+ {movies.map((movie) => { + if (movie.IsAvailable) { + return ( + {movie.title} + ); + } + + return ( +
+ {movie.title} +
+
+ lock icon +
+
+
+ ); + })} +
+
+
+
+ ); +} + +export default Home; diff --git a/frontend/src/pages/Search.jsx b/frontend/src/pages/Search.jsx new file mode 100644 index 0000000..be76370 --- /dev/null +++ b/frontend/src/pages/Search.jsx @@ -0,0 +1,21 @@ +// import { useEffect, useState } from "react"; +// import axios from "axios"; // eslint-disable-line + +function Search() { + return ( +
+
+

Search

+
+ +
+
+
+ ); +} + +export default Search; diff --git a/frontend/src/sass/_app.scss b/frontend/src/sass/_app.scss index b14e852..3982866 100644 --- a/frontend/src/sass/_app.scss +++ b/frontend/src/sass/_app.scss @@ -1,4 +1,4 @@ -.home { +.app { width: 100%; height: 100%; flex-direction: column; @@ -7,175 +7,6 @@ overflow-x: hidden; flex: 1; - .movies-display-section { - align-self: stretch; - flex: 1; - flex-direction: column; - gap: calc(var(--spacing-constant) * 1); - display: flex; - - .logo-container { - align-self: stretch; - display: flex; - justify-content: center; - align-items: center; - - .logo { - width: clamp( - var(--logo-min-width, 75px), - var(--logo-preferred-width, 25%), - var(--logo-max-width, 185px) - ); - height: clamp( - var(--logo-min-height, 45px), - var(--logo-preferred-height, 8vh), - var(--logo-max-height, 110px) - ); - object-fit: cover; - object-position: center; - position: relative; - } - } - - .dynamic-hero-slider-container { - align-self: stretch; - justify-content: center; - gap: calc(var(--spacing-constant) * 1); - display: flex; - overflow-x: scroll; - scroll-behavior: smooth; - - .hero-movie-slide { - width: clamp( - var(--hero-movie-slide-min-width, 255px), - var(--hero-movie-slide-preferred-width, 80%), - var(--hero-movie-slide-max-width, 1200px) - ); - height: clamp( - var(--hero-movie-slide-min-height, 140px), - var(--hero-movie-slide-preferred-height, 25vh), - var(--hero-movie-slide-max-height, 655px) - ); - object-fit: cover; - position: relative; - border-radius: var(--border-radius-constant, 10px); - } - } - - .movie-genre-tabs-container { - align-self: stretch; - padding: 0 calc(var(--spacing-constant) * 1); - align-items: center; - gap: calc(var(--spacing-constant) * 1); - display: flex; - overflow-x: scroll; - scroll-behavior: smooth; - list-style-type: none; - - .movie-genre-tab-container { - align-items: center; - gap: calc(var(--spacing-constant) * 1); - display: flex; - - .movie-genre { - color: var( - --not-selected-movie-genre-tab-color, - hsla(0, 0%, 100%, 0.6) - ); - font-size: calc(var(--font-size-constant) * 1.2); - font-weight: var(--font-weight-semi-bold); - text-wrap: nowrap; - } - - .selected-tab { - color: var(--selected-movie-genre-tab-color, hsla(0, 0%, 100%, 1)); - border-bottom: 1px solid - var(--selected-tab-border-bottom-color, hsla(335, 100%, 66%, 1)); - } - } - } - - .category-movie-display-container { - align-self: stretch; - flex-direction: column; - gap: calc(var(--spacing-constant) * 1); - display: flex; - - .category-title-container { - align-self: stretch; - padding: 0 calc(var(--spacing-constant) * 1); - justify-content: space-between; - align-items: center; - display: flex; - - .category-title { - color: var(--primary-font-color); - font-size: calc(var(--font-size-constant) * 1.4); - font-weight: var(--font-weight-semi-bold); - text-wrap: nowrap; - } - - .category-page-link { - color: var(--secondary-font-color); - font-size: calc(var(--font-size-constant) * 1.2); - font-weight: var(--font-weight-extra-light); - text-wrap: nowrap; - } - } - - .static-slider-container { - align-self: stretch; - padding: 0 calc(var(--spacing-constant) * 1); - align-items: center; - gap: calc(var(--spacing-constant) * 1); - display: flex; - overflow-x: scroll; - - .movie-slide { - width: var(--movie-slide-width, 70px); - height: var(--movie-slide-height, 90px); - border-radius: var(--border-radius-constant, 10px); - } - - .movie-slide-requiring-registration { - justify-content: center; - align-items: center; - gap: calc(var(--spacing-constant) * 1); - display: flex; - width: var(--movie-slide-width, 70px); - height: var(--movie-slide-height, 90px); - position: relative; - - .movie-slide { - border-radius: var(--border-radius-constant, 10px); - filter: blur(2px); - } - - .locked-overlay { - position: absolute; - top: 0; - left: 0; - right: 0; - bottom: 0; - padding: 0 calc(var(--spacing-constant) * 1); - justify-content: center; - align-items: center; - gap: calc(var(--spacing-constant) * 1); - display: flex; - - .lock-icon-container { - .lock-icon { - width: 30px; - height: 30px; - position: relative; - } - } - } - } - } - } - } - .navbar { align-self: stretch; padding: calc(var(--spacing-constant) * 0.7) diff --git a/frontend/src/sass/_home.scss b/frontend/src/sass/_home.scss new file mode 100644 index 0000000..4ed7543 --- /dev/null +++ b/frontend/src/sass/_home.scss @@ -0,0 +1,178 @@ +.home { + width: 100%; + height: 100%; + flex-direction: column; + justify-content: space-between; + display: flex; + overflow-x: hidden; + flex: 1; + + .movies-display-section { + align-self: stretch; + flex: 1; + flex-direction: column; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .logo-container { + align-self: stretch; + display: flex; + justify-content: center; + align-items: center; + + .logo { + width: clamp( + var(--logo-min-width, 75px), + var(--logo-preferred-width, 25%), + var(--logo-max-width, 185px) + ); + height: clamp( + var(--logo-min-height, 45px), + var(--logo-preferred-height, 8vh), + var(--logo-max-height, 110px) + ); + object-fit: cover; + object-position: center; + position: relative; + } + } + + .dynamic-hero-slider-container { + align-self: stretch; + justify-content: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + overflow-x: scroll; + scroll-behavior: smooth; + + .hero-movie-slide { + width: clamp( + var(--hero-movie-slide-min-width, 255px), + var(--hero-movie-slide-preferred-width, 80%), + var(--hero-movie-slide-max-width, 1200px) + ); + height: clamp( + var(--hero-movie-slide-min-height, 140px), + var(--hero-movie-slide-preferred-height, 25vh), + var(--hero-movie-slide-max-height, 655px) + ); + object-fit: cover; + position: relative; + border-radius: var(--border-radius-constant, 10px); + } + } + + .movie-genre-tabs-container { + align-self: stretch; + padding: 0 calc(var(--spacing-constant) * 1); + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + overflow-x: scroll; + scroll-behavior: smooth; + list-style-type: none; + + .movie-genre-tab-container { + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .movie-genre { + color: var( + --not-selected-movie-genre-tab-color, + hsla(0, 0%, 100%, 0.6) + ); + font-size: calc(var(--font-size-constant) * 1.2); + font-weight: var(--font-weight-semi-bold); + text-wrap: nowrap; + } + + .selected-tab { + color: var(--selected-movie-genre-tab-color, hsla(0, 0%, 100%, 1)); + border-bottom: 1px solid + var(--selected-tab-border-bottom-color, hsla(335, 100%, 66%, 1)); + } + } + } + + .category-movie-display-container { + align-self: stretch; + flex-direction: column; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .category-title-container { + align-self: stretch; + padding: 0 calc(var(--spacing-constant) * 1); + justify-content: space-between; + align-items: center; + display: flex; + + .category-title { + color: var(--primary-font-color); + font-size: calc(var(--font-size-constant) * 1.4); + font-weight: var(--font-weight-semi-bold); + text-wrap: nowrap; + } + + .category-page-link { + color: var(--secondary-font-color); + font-size: calc(var(--font-size-constant) * 1.2); + font-weight: var(--font-weight-extra-light); + text-wrap: nowrap; + } + } + + .static-slider-container { + align-self: stretch; + padding: 0 calc(var(--spacing-constant) * 1); + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + overflow-x: scroll; + + .movie-slide { + width: var(--movie-slide-width, 70px); + height: var(--movie-slide-height, 90px); + border-radius: var(--border-radius-constant, 10px); + } + + .movie-slide-requiring-registration { + justify-content: center; + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + width: var(--movie-slide-width, 70px); + height: var(--movie-slide-height, 90px); + position: relative; + + .movie-slide { + border-radius: var(--border-radius-constant, 10px); + filter: blur(2px); + } + + .locked-overlay { + position: absolute; + top: 0; + left: 0; + right: 0; + bottom: 0; + padding: 0 calc(var(--spacing-constant) * 1); + justify-content: center; + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .lock-icon-container { + .lock-icon { + width: 30px; + height: 30px; + position: relative; + } + } + } + } + } + } + } +} diff --git a/frontend/src/sass/_search.scss b/frontend/src/sass/_search.scss new file mode 100644 index 0000000..d672170 --- /dev/null +++ b/frontend/src/sass/_search.scss @@ -0,0 +1,36 @@ +.search { + width: 100%; + height: 100%; + flex-direction: column; + justify-content: space-between; + display: flex; + overflow-x: hidden; + flex: 1; + + .search-display-section { + align-self: stretch; + flex: 1; + flex-direction: column; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .search-bar-container { + align-self: stretch; + height: 45px; + padding: 0 calc(var(--spacing-constant) * 1); + display: flex; + + .search-bar { + flex: 1 1 auto; + align-self: stretch; + padding: 0 calc(var(--spacing-constant) * 1); + border-radius: var(--border-radius-constant, 10px); + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + width: 100%; + height: 100%; + } + } + } +} diff --git a/frontend/src/sass/index.scss b/frontend/src/sass/index.scss index b00299c..b8d45fb 100644 --- a/frontend/src/sass/index.scss +++ b/frontend/src/sass/index.scss @@ -1,2 +1,4 @@ @import "settings"; +@import "home"; @import "app"; +@import "search"; diff --git a/frontend/vite.config.js b/frontend/vite.config.js index f0078e4..012c62e 100644 --- a/frontend/vite.config.js +++ b/frontend/vite.config.js @@ -1,5 +1,5 @@ -import { defineConfig } from "vite"; -import react from "@vitejs/plugin-react"; +import { defineConfig } from "vite"; // eslint-disable-line +import react from "@vitejs/plugin-react"; // eslint-disable-line // https://vitejs.dev/config/ export default defineConfig({ From 6623fb1d21b12d2fba17ca8a80fabe46d9b0e4ff Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Wed, 13 Dec 2023 16:02:11 +0100 Subject: [PATCH 27/44] pending... --- backend/database/schema.sql | 25 ++++++++++++++++++++++++- 1 file changed, 24 insertions(+), 1 deletion(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index f77a857..0ba9f05 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -41,6 +41,29 @@ CREATE TABLE `IsAvailable` BOOLEAN NOT NULL ); +INSERT INTO + `Film` (`miniature`, `title`, `videoUrl`, `duration`, `year`, `description`, `IsAvailable`) +VALUES + ( + "https://m.media-amazon.com/images/M/MV5BMTkxM2FiYjctYjliYy00NjY2LWFmOTEtMWZiYWRjNjA4MGYxXkEyXkFqcGdeQXVyMTUzMTg2ODkz._V1_.jpg", + "Aquaman and the Lost Kingdom", + "https://www.youtube.com/watch?v=2wcj6SrX4zw", + 120, + "2023", + "The film is directed by James Wan from a screenplay written by David Leslie Johnson-McGoldrick and Will Beall and stars Jason Momoa as Aquaman, alongside Amber Heard, Patrick Wilson, Dolph Lundgren, Yahya Abdul-Mateen II, and Temuera Morrison. In the film, Aquaman must save the world from the threat of Ocean Master and Black Manta.", + 1 + ), + ( + "https://cdn.entries.clios.com/styles/clio_aotw_ems_image_details_retina/s3/entry_attachments/image/72/2297/22197/123544/xBckjuirX08J68hRmi7_Zgv4jhFeC3AbYX8REOHE770.jpeg/xBckjuirX08J68hRmi7_Zgv4jhFeC3AbYX8REOHE770.jpeg", + "The Batman", + "https://www.youtube.com/watch?v=mqqft2x_Aa4", + 120, + "2022", + "The film is directed by Matt Reeves, who wrote the screenplay with Peter Craig. It stars Robert Pattinson as Bruce Wayne / Batman, with Zoë Kravitz, Paul Dano, Jeffrey Wright, John Turturro, Peter Sarsgaard, Barry Keoghan, Jayme Lawson, Andy Serkis, and Colin Farrell rounding out the ensemble cast.", + 1 + ); + + DROP TABLE IF EXISTS `Categorie`; CREATE TABLE @@ -136,4 +159,4 @@ CREATE TABLE CONSTRAINT FK_Categorie_Par_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), CONSTRAINT FK_Categorie_Par_Film_categorie_id FOREIGN KEY (`categorieId`) REFERENCES `Categorie`(`id`), PRIMARY KEY (`filmId`, `categorieId`) - ); + ); \ No newline at end of file From e3eb072168a3ff0d1a0cb28edea8e2929b932125 Mon Sep 17 00:00:00 2001 From: Alexandre Date: Wed, 13 Dec 2023 16:34:03 +0100 Subject: [PATCH 28/44] merging --- backend/database/schema.sql | 6 ++ .../src/controllers/favoriFilmControllers.js | 56 +++++++++++++++++++ backend/src/controllers/filmControllers.js | 2 +- backend/src/models/FavoriFilmManager.js | 33 +++++++++++ backend/src/router.js | 8 ++- backend/src/tables.js | 2 + 6 files changed, 104 insertions(+), 3 deletions(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 690aff7..0264ba4 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -218,3 +218,9 @@ INSERT INTO '0' ); +INSERT INTO + `Favori_film` (`userId`, `filmId`) + VALUES + (1, 1), + (1, 2) + diff --git a/backend/src/controllers/favoriFilmControllers.js b/backend/src/controllers/favoriFilmControllers.js index e69de29..9467cbb 100644 --- a/backend/src/controllers/favoriFilmControllers.js +++ b/backend/src/controllers/favoriFilmControllers.js @@ -0,0 +1,56 @@ +const tables = require("../tables"); + +const browse = async (req, res, next) => { + try { + const favorites = await tables.favori_film.readAll(); + res.json(favorites); + } catch (err) { + next(err); + } +}; + +const read = async (req, res, next) => { + try { + const favorite = await tables.favori_film.read(req.params.id); + if (favorite == null) { + res.sendStatus(404); + } else { + res.json(favorite); + } + } catch (err) { + next(err); + } +}; + +const add = async (req, res, next) => { + const favorite = req.body; + + try { + const insertId = await tables.favori_film.create(favorite); + res.status(200).json({ insertId }); + } catch (err) { + next(err); + } +}; + +const destroy = async (req, res, next) => { + const { id: userId } = req.params; + const { filmId } = req.body; + + try { + const [result] = await tables.favori_film.delete(userId, filmId); + if (result.affectedRows) { + res.sendStatus(200); + } else { + res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; +module.exports = { + browse, + read, + add, + destroy, +}; diff --git a/backend/src/controllers/filmControllers.js b/backend/src/controllers/filmControllers.js index 89dc04c..0ee7e8a 100644 --- a/backend/src/controllers/filmControllers.js +++ b/backend/src/controllers/filmControllers.js @@ -52,7 +52,7 @@ const add = async (req, res, next) => { const destroy = async (req, res, next) => { const { id } = req.params; try { - const result = await tables.film.delete(id); + const [result] = await tables.film.delete(id); if (result.affectedRows) { res.sendStatus(200); } else { diff --git a/backend/src/models/FavoriFilmManager.js b/backend/src/models/FavoriFilmManager.js index dc0e8e0..aeca7e9 100644 --- a/backend/src/models/FavoriFilmManager.js +++ b/backend/src/models/FavoriFilmManager.js @@ -4,5 +4,38 @@ class FavoriFilmManager extends AbstractManager { constructor() { super({ table: "favori_film" }); } + + async create({ userId, filmId }) { + const [result] = await this.database.query( + `insert into ${this.table} (userId, filmId) values (?,?)`, + [userId, filmId] + ); + return result.insertId; + } + + async read(id) { + const [result] = await this.database.query( + `select u.id, f.id, f.title + from Favori_film ff + inner join user u on ff.userId = u.id + inner join film f on ff.filmId = f.id + where ff.userId = ?`, + [id] + ); + return result; + } + + async readAll() { + const [result] = await this.database.query(`select * from ${this.table}`); + return result; + } + + async delete(userId, filmId) { + const result = await this.database.query( + `delete from ${this.table} where userId = ? and filmId = ?`, + [userId, filmId] + ); + return result; + } } module.exports = FavoriFilmManager; diff --git a/backend/src/router.js b/backend/src/router.js index 2f2aaf7..5963146 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -11,18 +11,19 @@ const categorieControllers = require("./controllers/categorieControllers"); const filmControllers = require("./controllers/filmControllers"); const userControllers = require("./controllers/userControllers"); const serieControllers = require("./controllers/serieControllers"); - +const favoriFilmControllers = require("./controllers/favoriFilmControllers"); // Route to get a list of items router.get("/categories", categorieControllers.browse); router.get("/films", filmControllers.browse); router.get("/series", serieControllers.browse); router.get("/users", userControllers.browse); - +router.get("/favorites", favoriFilmControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); router.get("/series/:id", serieControllers.read); router.get("/users/:id", userControllers.read); +router.get("/favorites/:id", favoriFilmControllers.read); // Route to edit a specific item by ID router.put("/films/:id", filmControllers.edit); @@ -34,11 +35,14 @@ router.post("/categories", categorieControllers.add); router.post("/films", filmControllers.add); router.post("/series", serieControllers.add); router.post("/users", userControllers.add); +router.post("/favorites", favoriFilmControllers.add); // Route to detele a specific item by ID router.delete("/films/:id", filmControllers.destroy); router.delete("/series/:id", serieControllers.destroy); router.delete("/users/:id", userControllers.destroy); +router.delete("/favorites/:id", favoriFilmControllers.destroy); + /* ************************************************************************* */ module.exports = router; diff --git a/backend/src/tables.js b/backend/src/tables.js index d6d1def..a04a9dd 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -7,12 +7,14 @@ const CategorieManager = require("./models/CategorieManager"); const UserManager = require("./models/UserManager"); const FilmManager = require("./models/FilmManager"); const SerieManager = require("./models/SerieManager"); +const FavoriFilmManager = require("./models/FavoriFilmManager"); const managers = [ CategorieManager, UserManager, FilmManager, SerieManager, + FavoriFilmManager, // Add other managers here ]; From 0231cd79d11c579cab8c0ae03e423f8638388bf9 Mon Sep 17 00:00:00 2001 From: Aurelien Date: Wed, 13 Dec 2023 16:37:22 +0100 Subject: [PATCH 29/44] table films en tendance --- backend/database/schema.sql | 19 ++++ .../controllers/enTendanceFilmControllers.js | 97 +++++++++++++++++++ backend/src/models/EnTendanceFilmManager.js | 74 ++++++++++++++ backend/src/router.js | 6 ++ backend/src/tables.js | 2 + frontend/src/App.jsx | 2 +- 6 files changed, 199 insertions(+), 1 deletion(-) create mode 100644 backend/src/controllers/enTendanceFilmControllers.js create mode 100644 backend/src/models/EnTendanceFilmManager.js diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 690aff7..3235323 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -76,6 +76,7 @@ DROP TABLE IF EXISTS `En_tendance_film`; CREATE TABLE `En_tendance_film` ( + -- `id` int primary key auto_increment not null, `userId` INT NOT NULL, `filmId` INT NOT NULL, CONSTRAINT FK_En_tendance_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), @@ -218,3 +219,21 @@ INSERT INTO '0' ); +INSERT INTO + `En_tendance_film` (`userId`, `filmId`) + VALUES + ( + '1', + '1' + ); + + + -- CREATE TABLE + -- `En_tendance_film` ( + -- `userId` INT NOT NULL, + -- `filmId` INT NOT NULL, + -- CONSTRAINT FK_En_tendance_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), + -- CONSTRAINT FK_En_tendance_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), + -- PRIMARY KEY (`userId`, `filmId`) + -- ); + diff --git a/backend/src/controllers/enTendanceFilmControllers.js b/backend/src/controllers/enTendanceFilmControllers.js new file mode 100644 index 0000000..dc7bbab --- /dev/null +++ b/backend/src/controllers/enTendanceFilmControllers.js @@ -0,0 +1,97 @@ +// Import access to database tables +const tables = require("../tables"); + +// The B of BREAD - Browse (Read All) operation +const browse = async (req, res, next) => { + try { + // Fetch all items from the database + const users = await tables.En_Tendance_Film.readAll(); + + // Respond with the items in JSON format + res.json(users); + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The R of BREAD - Read operation +const read = async (req, res, next) => { + try { + // Fetch a specific item from the database based on the provided ID + const user = await tables.En_Tendance_Film.read(req.params.id); + + // If the item is not found, respond with HTTP 404 (Not Found) + // Otherwise, respond with the item in JSON format + if (user == null) { + res.sendStatus(404); + } else { + res.json(user); + } + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The E of BREAD - Edit (Update) operation +// This operation is not yet implemented + +// eslint-disable-next-line consistent-return +const edit = async (req, res, next) => { + const { id } = req.params; + req.body.id = id; + try { + const result = await tables.En_Tendance_Film.update(req.body); + if (result) { + res.json(result); + res.status(204); + } else { + return res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; + +// The A of BREAD - Add (Create) operation +const add = async (req, res, next) => { + // Extract the item data from the request body + const films = req.body; + + try { + // Insert the item into the database + const insertId = await tables.En_Tendance_Film.create(films); + + // Respond with HTTP 201 (Created) and the ID of the newly inserted item + res.status(201).json({ insertId }); + } catch (err) { + // Pass any errors to the error-handling middleware + next(err); + } +}; + +// The D of BREAD - Destroy (Delete) operation +// This operation is not yet implemented +const destroy = async (req, res, next) => { + const { id } = req.params; + try { + const result = await tables.En_Tendance_Film.delete(id); + if (result.affectedRows) { + res.sendStatus(200); + } else { + res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; + +// Ready to export the controller functions +module.exports = { + browse, + read, + edit, + add, + destroy, +}; diff --git a/backend/src/models/EnTendanceFilmManager.js b/backend/src/models/EnTendanceFilmManager.js new file mode 100644 index 0000000..0d09fdd --- /dev/null +++ b/backend/src/models/EnTendanceFilmManager.js @@ -0,0 +1,74 @@ +const AbstractManager = require("./AbstractManager"); + +class EnTendanceFilmManager extends AbstractManager { + constructor() { + // Call the constructor of the parent class (AbstractManager) + // and pass the table name "En_Tendance_Film" as configuration + super({ table: "En_Tendance_Film" }); + } + + // The C of CRUD - Create operation + + async create({ userId, filmId }) { + // Execute the SQL INSERT query to add a new item to the "user" table + const [result] = await this.database.query( + `insert into ${this.table} (userId, filmId) values (?, ?)`, + [userId, filmId] + ); + + // Return the ID of the newly inserted item + return result; + } + // The Rs of CRUD - Read operations + + async read(id) { + // Execute the SQL SELECT query to retrieve a specific item by its ID + const [rows] = await this.database.query( + `select * from ${this.table} where id = ?`, + [id] + ); + + // Return the first row of the result, which represents the item + return rows; + } + + async readAll() { + // Execute the SQL SELECT query to retrieve all items from the "user" table + const [rows] = await this.database.query(`select userId, filmId, Film.title + FROM En_Tendance_film + INNER JOIN User + INNER JOIN Film + WHERE`); + + // Return the array of items + return rows; + } + // The U of CRUD - Update operation + // TODO: Implement the update operation to modify an existing item + + async update({ userId, filmId }) { + // Execute the SQL UPDATE query to update a item to the "user" table + const [result] = await this.database.query( + `UPDATE ${this.table} SET userId=?, filmId=? WHERE id=?`, + [userId, filmId] + ); + + // Return the ID of the newly inserted item + return result; + } + + // The D of CRUD - Delete operation + // TODO: Implement the delete operation to remove an item by its ID + + async delete(id) { + const [rows] = await this.database.query( + `DELETE from ${this.table} where id = ?`, + [id] + ); + + // Return the first row of the result, which represents the item + return rows; + } +} + +module.exports = EnTendanceFilmManager; diff --git a/backend/src/router.js b/backend/src/router.js index 2f2aaf7..b5c7f14 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -11,34 +11,40 @@ const categorieControllers = require("./controllers/categorieControllers"); const filmControllers = require("./controllers/filmControllers"); const userControllers = require("./controllers/userControllers"); const serieControllers = require("./controllers/serieControllers"); +const enTendanceFilmControllers = require("./controllers/enTendanceFilmControllers"); // Route to get a list of items router.get("/categories", categorieControllers.browse); router.get("/films", filmControllers.browse); router.get("/series", serieControllers.browse); router.get("/users", userControllers.browse); +router.get("/FilmsEnTendance", enTendanceFilmControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); router.get("/series/:id", serieControllers.read); router.get("/users/:id", userControllers.read); +router.get("/FilmsEnTendance/:id", enTendanceFilmControllers.read); // Route to edit a specific item by ID router.put("/films/:id", filmControllers.edit); router.put("/series/:id", serieControllers.edit); router.put("/users/:id", userControllers.edit); +router.put("/FilmsEnTendance/:id", enTendanceFilmControllers.edit); // Route to add a new item router.post("/categories", categorieControllers.add); router.post("/films", filmControllers.add); router.post("/series", serieControllers.add); router.post("/users", userControllers.add); +router.post("/FilmsEnTendance", enTendanceFilmControllers.add); // Route to detele a specific item by ID router.delete("/films/:id", filmControllers.destroy); router.delete("/series/:id", serieControllers.destroy); router.delete("/users/:id", userControllers.destroy); +router.delete("/FilmsEnTendance", enTendanceFilmControllers.destroy); /* ************************************************************************* */ module.exports = router; diff --git a/backend/src/tables.js b/backend/src/tables.js index d6d1def..5eedb48 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -7,12 +7,14 @@ const CategorieManager = require("./models/CategorieManager"); const UserManager = require("./models/UserManager"); const FilmManager = require("./models/FilmManager"); const SerieManager = require("./models/SerieManager"); +const EnTendanceFilmManager = require("./models/EnTendanceFilmManager"); const managers = [ CategorieManager, UserManager, FilmManager, SerieManager, + EnTendanceFilmManager, // Add other managers here ]; diff --git a/frontend/src/App.jsx b/frontend/src/App.jsx index 76ce3bf..07c0997 100644 --- a/frontend/src/App.jsx +++ b/frontend/src/App.jsx @@ -67,7 +67,7 @@ function App() {
{movies.map((movie) => { - if (!movie.is_available) { + if (movie.isAvailable) { return ( Date: Wed, 13 Dec 2023 16:51:44 +0100 Subject: [PATCH 30/44] conflicts --- backend/database/schema.sql | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index f2d27ab..c7eceb6 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -240,13 +240,9 @@ INSERT INTO 'ggfd455', '0' ); -<<<<<<< HEAD INSERT INTO `Favori_film` (`userId`, `filmId`) VALUES (1, 1), - (1, 2) - -======= ->>>>>>> 6cd8201133e255c8babffa97c76bccf6c66fb495 + (1, 2) \ No newline at end of file From 240d627d89f699785481a497ed8f5283a201b6d0 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Wed, 13 Dec 2023 16:56:30 +0100 Subject: [PATCH 31/44] pending... --- frontend/src/pages/Search.jsx | 1 - 1 file changed, 1 deletion(-) diff --git a/frontend/src/pages/Search.jsx b/frontend/src/pages/Search.jsx index be76370..50e9189 100644 --- a/frontend/src/pages/Search.jsx +++ b/frontend/src/pages/Search.jsx @@ -5,7 +5,6 @@ function Search() { return (
-

Search

Date: Wed, 13 Dec 2023 16:57:52 +0100 Subject: [PATCH 32/44] pending... --- backend/database/schema.sql | 4 ---- 1 file changed, 4 deletions(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index f2d27ab..f249893 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -240,13 +240,9 @@ INSERT INTO 'ggfd455', '0' ); -<<<<<<< HEAD INSERT INTO `Favori_film` (`userId`, `filmId`) VALUES (1, 1), (1, 2) - -======= ->>>>>>> 6cd8201133e255c8babffa97c76bccf6c66fb495 From fd21da46e367e912bdb51b2aa7726f6064075124 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Wed, 13 Dec 2023 23:18:05 +0100 Subject: [PATCH 33/44] handling the context API --- frontend/src/App.jsx | 38 ++++------------------ frontend/src/assets/icons/sort_icon.svg | 10 ++++++ frontend/src/components/NavBar.jsx | 37 +++++++++++++++++++++ frontend/src/contexts/MovieContext.jsx | 43 +++++++++++++++++++++++++ frontend/src/main.jsx | 7 +++- frontend/src/pages/Home.jsx | 16 ++------- frontend/src/pages/Search.jsx | 11 +++++++ frontend/src/sass/_app.scss | 39 ---------------------- frontend/src/sass/_navbar.scss | 37 +++++++++++++++++++++ frontend/src/sass/_search.scss | 36 +++++++++++++++++++++ frontend/src/sass/index.scss | 3 +- 11 files changed, 191 insertions(+), 86 deletions(-) create mode 100644 frontend/src/assets/icons/sort_icon.svg create mode 100644 frontend/src/components/NavBar.jsx create mode 100644 frontend/src/contexts/MovieContext.jsx create mode 100644 frontend/src/sass/_navbar.scss diff --git a/frontend/src/App.jsx b/frontend/src/App.jsx index 415f2eb..2baf6ec 100644 --- a/frontend/src/App.jsx +++ b/frontend/src/App.jsx @@ -1,38 +1,14 @@ -import { NavLink, Outlet } from "react-router-dom"; +import { Outlet } from "react-router-dom"; +import NavBar from "./components/NavBar"; +import { MovieProvider } from "./contexts/MovieContext"; function App() { return (
- -
-
- - home icon - -
-
- - search icon - -
- {/*
- - profile icon - -
*/} -
+ + + +
); } diff --git a/frontend/src/assets/icons/sort_icon.svg b/frontend/src/assets/icons/sort_icon.svg new file mode 100644 index 0000000..1a62bd7 --- /dev/null +++ b/frontend/src/assets/icons/sort_icon.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/frontend/src/components/NavBar.jsx b/frontend/src/components/NavBar.jsx new file mode 100644 index 0000000..cb54f4c --- /dev/null +++ b/frontend/src/components/NavBar.jsx @@ -0,0 +1,37 @@ +import { NavLink } from "react-router-dom"; + +function NavBar() { + return ( +
+
+ + home icon + +
+
+ + search icon + +
+ {/*
+ + profile icon + +
*/} +
+ ); +} + +export default NavBar; diff --git a/frontend/src/contexts/MovieContext.jsx b/frontend/src/contexts/MovieContext.jsx new file mode 100644 index 0000000..1861cca --- /dev/null +++ b/frontend/src/contexts/MovieContext.jsx @@ -0,0 +1,43 @@ +import { createContext, useState, useEffect, useContext, useMemo } from "react"; +import axios from "axios"; +import PropTypes from "prop-types"; + +const MovieContext = createContext(); + +export function MovieProvider({ children }) { + const [movies, setMovies] = useState([]); + + useEffect(() => { + axios + .get("http://localhost:3310/api/films") + .then((response) => { + setMovies(response.data); + console.info(response.data); + }) + .catch((error) => { + console.error(error); + }); + }, []); + + const value = useMemo(() => ({ movies, setMovies }), [movies, setMovies]); + + return ( + {children} + ); +} + +export function useMovies() { + const context = useContext(MovieContext); + + if (!context) { + throw new Error( + "useMovies must be used within a MovieProvider. Wrap a parent component in to fix this error." + ); + } + + return context; +} + +MovieProvider.propTypes = { + children: PropTypes.node.isRequired, +}; diff --git a/frontend/src/main.jsx b/frontend/src/main.jsx index 997c47e..124a8b3 100644 --- a/frontend/src/main.jsx +++ b/frontend/src/main.jsx @@ -4,6 +4,7 @@ import { createBrowserRouter, RouterProvider } from "react-router-dom"; import App from "./App"; import Home from "./pages/Home"; import Search from "./pages/Search"; +import { MovieProvider } from "./contexts/MovieContext"; import "./sass/index.scss"; const router = createBrowserRouter([ @@ -31,6 +32,10 @@ const root = ReactDOM.createRoot(document.getElementById("root")); root.render( - + + + + + ); diff --git a/frontend/src/pages/Home.jsx b/frontend/src/pages/Home.jsx index c25e757..1ebee09 100644 --- a/frontend/src/pages/Home.jsx +++ b/frontend/src/pages/Home.jsx @@ -1,20 +1,8 @@ -import { useEffect, useState } from "react"; -import axios from "axios"; // eslint-disable-line +import { useMovies } from "../contexts/MovieContext"; function Home() { - const [movies, setMovies] = useState([]); + const { movies } = useMovies(); - useEffect(() => { - axios - .get("http://localhost:3310/api/films") - .then((response) => { - setMovies(response.data); - console.info(response.data); - }) - .catch((error) => { - console.error(error); - }); - }, []); return (
diff --git a/frontend/src/pages/Search.jsx b/frontend/src/pages/Search.jsx index 50e9189..c558d0c 100644 --- a/frontend/src/pages/Search.jsx +++ b/frontend/src/pages/Search.jsx @@ -12,6 +12,17 @@ function Search() { placeholder="Rechercher un film" />
+
+ +
+ {/*
*/}
); diff --git a/frontend/src/sass/_app.scss b/frontend/src/sass/_app.scss index 3982866..4d210b5 100644 --- a/frontend/src/sass/_app.scss +++ b/frontend/src/sass/_app.scss @@ -6,43 +6,4 @@ display: flex; overflow-x: hidden; flex: 1; - - .navbar { - align-self: stretch; - padding: calc(var(--spacing-constant) * 0.7) - calc(var(--spacing-constant) * 3); - justify-content: space-between; - align-items: center; - display: flex; - - .nav-icon-container { - width: var(--nav-icon-container-width, 18px); - height: var(--nav-icon-container-height, 18px); - position: relative; - - .home-icon { - width: var(--home-icon-width, 18px); - height: var(--home-icon-height, 18px); - left: 0; - top: 0; - position: absolute; - } - - .search-icon { - width: var(--search-icon-width, 18px); - height: var(--search-icon-height, 18px); - left: 0; - top: 0; - position: absolute; - } - - .profile-icon { - width: var(--profile-icon-width, 18px); - height: var(--profile-icon-height, 18px); - left: 0; - top: 0; - position: absolute; - } - } - } } diff --git a/frontend/src/sass/_navbar.scss b/frontend/src/sass/_navbar.scss new file mode 100644 index 0000000..b92da4b --- /dev/null +++ b/frontend/src/sass/_navbar.scss @@ -0,0 +1,37 @@ +.navbar { + align-self: stretch; + padding: calc(var(--spacing-constant) * 0.7) calc(var(--spacing-constant) * 3); + justify-content: space-between; + align-items: center; + display: flex; + + .nav-icon-container { + width: var(--nav-icon-container-width, 18px); + height: var(--nav-icon-container-height, 18px); + position: relative; + + .home-icon { + width: var(--home-icon-width, 18px); + height: var(--home-icon-height, 18px); + left: 0; + top: 0; + position: absolute; + } + + .search-icon { + width: var(--search-icon-width, 18px); + height: var(--search-icon-height, 18px); + left: 0; + top: 0; + position: absolute; + } + + .profile-icon { + width: var(--profile-icon-width, 18px); + height: var(--profile-icon-height, 18px); + left: 0; + top: 0; + position: absolute; + } + } +} diff --git a/frontend/src/sass/_search.scss b/frontend/src/sass/_search.scss index d672170..454339d 100644 --- a/frontend/src/sass/_search.scss +++ b/frontend/src/sass/_search.scss @@ -10,6 +10,7 @@ .search-display-section { align-self: stretch; flex: 1; + padding-top: calc(var(--spacing-constant) * 2); flex-direction: column; gap: calc(var(--spacing-constant) * 1); display: flex; @@ -30,6 +31,41 @@ display: flex; width: 100%; height: 100%; + border: none; + } + + .search-bar:focus { + outline: none; + } + } + + .sort-container { + align-self: stretch; + height: 30px; + padding: 0 calc(var(--spacing-constant) * 1); + justify-content: flex-end; + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .sort-button { + height: 100%; + padding: 0 calc(var(--spacing-constant) * 1); + border-radius: calc(var(--border-radius-constant, 10px) * 1.3); + justify-content: center; + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + border: none; + + .sort-text { + text-align: center; + font-size: calc(var(--font-size-constant) * 1.2); + font-weight: var(--font-weight-semi-bold); + } + + .sort-icon { + } } } } diff --git a/frontend/src/sass/index.scss b/frontend/src/sass/index.scss index b8d45fb..a586668 100644 --- a/frontend/src/sass/index.scss +++ b/frontend/src/sass/index.scss @@ -1,4 +1,5 @@ @import "settings"; -@import "home"; @import "app"; +@import "home"; @import "search"; +@import "navbar"; From f3f714e03affe22af5552a4e6f7b7735211a7385 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Thu, 14 Dec 2023 01:06:55 +0100 Subject: [PATCH 34/44] handling useParams --- frontend/src/components/MovieSlide.jsx | 40 ++++++++++++++++++++++++ frontend/src/contexts/MovieContext.jsx | 2 +- frontend/src/main.jsx | 7 ++++- frontend/src/pages/Home.jsx | 41 +++++-------------------- frontend/src/pages/Movie.jsx | 11 +++++++ frontend/src/pages/Search.jsx | 34 +++++++++++++++++++-- frontend/src/sass/_home.scss | 42 -------------------------- frontend/src/sass/_movieSlide.scss | 41 +++++++++++++++++++++++++ frontend/src/sass/_search.scss | 3 -- frontend/src/sass/index.scss | 1 + 10 files changed, 138 insertions(+), 84 deletions(-) create mode 100644 frontend/src/components/MovieSlide.jsx create mode 100644 frontend/src/pages/Movie.jsx create mode 100644 frontend/src/sass/_movieSlide.scss diff --git a/frontend/src/components/MovieSlide.jsx b/frontend/src/components/MovieSlide.jsx new file mode 100644 index 0000000..8aa00b0 --- /dev/null +++ b/frontend/src/components/MovieSlide.jsx @@ -0,0 +1,40 @@ +import PropTypes from "prop-types"; +// import { NavLink } from "react-router-dom"; + +function MovieSlide({ movie }) { + if (movie.IsAvailable) { + return ( + // + {movie.title} + ); + } + return ( +
+ {movie.title} +
+
+ lock icon +
+
+
+ ); +} + +MovieSlide.propTypes = { + movie: PropTypes.shape({ + id: PropTypes.number.isRequired, + miniature: PropTypes.string.isRequired, + title: PropTypes.string.isRequired, + videoUrl: PropTypes.string, + duration: PropTypes.number.isRequired, + year: PropTypes.string.isRequired, + description: PropTypes.string.isRequired, + IsAvailable: PropTypes.number.isRequired, + }).isRequired, +}; + +export default MovieSlide; diff --git a/frontend/src/contexts/MovieContext.jsx b/frontend/src/contexts/MovieContext.jsx index 1861cca..fc6bef9 100644 --- a/frontend/src/contexts/MovieContext.jsx +++ b/frontend/src/contexts/MovieContext.jsx @@ -12,7 +12,7 @@ export function MovieProvider({ children }) { .get("http://localhost:3310/api/films") .then((response) => { setMovies(response.data); - console.info(response.data); + // console.info(response.data); }) .catch((error) => { console.error(error); diff --git a/frontend/src/main.jsx b/frontend/src/main.jsx index 124a8b3..4feafe2 100644 --- a/frontend/src/main.jsx +++ b/frontend/src/main.jsx @@ -1,10 +1,11 @@ import React from "react"; import ReactDOM from "react-dom/client"; import { createBrowserRouter, RouterProvider } from "react-router-dom"; +import { MovieProvider } from "./contexts/MovieContext"; import App from "./App"; import Home from "./pages/Home"; import Search from "./pages/Search"; -import { MovieProvider } from "./contexts/MovieContext"; +import Movie from "./pages/Movie"; import "./sass/index.scss"; const router = createBrowserRouter([ @@ -24,6 +25,10 @@ const router = createBrowserRouter([ // path: "profile", // element:

Profile

, // }, + { + path: "/movies/:movieId", + element: , + }, ], }, ]); diff --git a/frontend/src/pages/Home.jsx b/frontend/src/pages/Home.jsx index 1ebee09..a44b751 100644 --- a/frontend/src/pages/Home.jsx +++ b/frontend/src/pages/Home.jsx @@ -1,4 +1,6 @@ +import { NavLink } from "react-router-dom"; import { useMovies } from "../contexts/MovieContext"; +import MovieSlide from "../components/MovieSlide"; function Home() { const { movies } = useMovies(); @@ -41,40 +43,11 @@ function Home() {

Voir tout

*/}
- {movies.map((movie) => { - if (movie.IsAvailable) { - return ( - {movie.title} - ); - } - - return ( -
- {movie.title} -
-
- lock icon -
-
-
- ); - })} + {movies.map((movie) => ( + + + + ))}
diff --git a/frontend/src/pages/Movie.jsx b/frontend/src/pages/Movie.jsx new file mode 100644 index 0000000..40286fc --- /dev/null +++ b/frontend/src/pages/Movie.jsx @@ -0,0 +1,11 @@ +import { useParams } from "react-router-dom"; + +function Movie() { + const { movieId } = useParams(); + if (!movieId) { + return

Movie not found

; + } + return

Movie {movieId}

; +} + +export default Movie; diff --git a/frontend/src/pages/Search.jsx b/frontend/src/pages/Search.jsx index c558d0c..b2eb8a4 100644 --- a/frontend/src/pages/Search.jsx +++ b/frontend/src/pages/Search.jsx @@ -1,7 +1,15 @@ -// import { useEffect, useState } from "react"; -// import axios from "axios"; // eslint-disable-line +import { useState } from "react"; +import { useMovies } from "../contexts/MovieContext"; +import MovieSlide from "../components/MovieSlide"; function Search() { + const [searchValue, setSearchValue] = useState(""); + const { movies } = useMovies(); + + function handleSearchChange(event) { + setSearchValue(event.target.value); + } + return (
@@ -10,6 +18,8 @@ function Search() { className="search-bar" type="search" placeholder="Rechercher un film" + value={searchValue} + onChange={handleSearchChange} />
@@ -22,7 +32,25 @@ function Search() { />
- {/*
*/} +
+ {searchValue.length > 0 ? ( + <> + {movies + .filter((movie) => + movie.title.toLowerCase().includes(searchValue.toLowerCase()) + ) + .map((movie) => ( + + ))} + + ) : ( + <> + {movies.map((movie) => ( + + ))} + + )} +
); diff --git a/frontend/src/sass/_home.scss b/frontend/src/sass/_home.scss index 4ed7543..1aedc3b 100644 --- a/frontend/src/sass/_home.scss +++ b/frontend/src/sass/_home.scss @@ -130,48 +130,6 @@ gap: calc(var(--spacing-constant) * 1); display: flex; overflow-x: scroll; - - .movie-slide { - width: var(--movie-slide-width, 70px); - height: var(--movie-slide-height, 90px); - border-radius: var(--border-radius-constant, 10px); - } - - .movie-slide-requiring-registration { - justify-content: center; - align-items: center; - gap: calc(var(--spacing-constant) * 1); - display: flex; - width: var(--movie-slide-width, 70px); - height: var(--movie-slide-height, 90px); - position: relative; - - .movie-slide { - border-radius: var(--border-radius-constant, 10px); - filter: blur(2px); - } - - .locked-overlay { - position: absolute; - top: 0; - left: 0; - right: 0; - bottom: 0; - padding: 0 calc(var(--spacing-constant) * 1); - justify-content: center; - align-items: center; - gap: calc(var(--spacing-constant) * 1); - display: flex; - - .lock-icon-container { - .lock-icon { - width: 30px; - height: 30px; - position: relative; - } - } - } - } } } } diff --git a/frontend/src/sass/_movieSlide.scss b/frontend/src/sass/_movieSlide.scss new file mode 100644 index 0000000..e19b6e5 --- /dev/null +++ b/frontend/src/sass/_movieSlide.scss @@ -0,0 +1,41 @@ +.movie-slide { + width: var(--movie-slide-width, 70px); + height: var(--movie-slide-height, 90px); + border-radius: var(--border-radius-constant, 10px); +} + +.movie-slide-requiring-registration { + justify-content: center; + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + width: var(--movie-slide-width, 70px); + height: var(--movie-slide-height, 90px); + position: relative; + + .movie-slide { + border-radius: var(--border-radius-constant, 10px); + filter: blur(2px); + } + + .locked-overlay { + position: absolute; + top: 0; + left: 0; + right: 0; + bottom: 0; + padding: 0 calc(var(--spacing-constant) * 1); + justify-content: center; + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .lock-icon-container { + .lock-icon { + width: 30px; + height: 30px; + position: relative; + } + } + } +} diff --git a/frontend/src/sass/_search.scss b/frontend/src/sass/_search.scss index 454339d..47abb52 100644 --- a/frontend/src/sass/_search.scss +++ b/frontend/src/sass/_search.scss @@ -63,9 +63,6 @@ font-size: calc(var(--font-size-constant) * 1.2); font-weight: var(--font-weight-semi-bold); } - - .sort-icon { - } } } } diff --git a/frontend/src/sass/index.scss b/frontend/src/sass/index.scss index a586668..0a6b4ed 100644 --- a/frontend/src/sass/index.scss +++ b/frontend/src/sass/index.scss @@ -3,3 +3,4 @@ @import "home"; @import "search"; @import "navbar"; +@import "movieSlide"; From ab77b360fa718ffd21c9c64470627af44f60f9ee Mon Sep 17 00:00:00 2001 From: Techer Tony Date: Thu, 14 Dec 2023 14:51:48 +0100 Subject: [PATCH 35/44] favori_serie controller manager table et route --- backend/database/schema.sql | 95 +++++++++---------- .../src/controllers/favoriSerieControllers.js | 57 +++++++++++ backend/src/models/FavoriSerieManager.js | 41 ++++++++ backend/src/router.js | 13 ++- backend/src/tables.js | 3 + 5 files changed, 153 insertions(+), 56 deletions(-) create mode 100644 backend/src/controllers/favoriSerieControllers.js create mode 100644 backend/src/models/FavoriSerieManager.js diff --git a/backend/database/schema.sql b/backend/database/schema.sql index c7eceb6..3d1c645 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -5,7 +5,7 @@ CREATE TABLE `id` int primary key auto_increment not null, `miniature` varchar(255) not null, `title` VARCHAR(50) not NULL, - `videoUrl` VARCHAR(255) , + `videoUrl` VARCHAR(255), `duration` INT not NULL, `year` VARCHAR(4) not NULL, `description` VARCHAR(500) not NULL, @@ -34,17 +34,24 @@ CREATE TABLE `id` int primary key auto_increment not null, `miniature` VARCHAR(255) not null, `title` VARCHAR(255) not null, - `videoUrl` VARCHAR(255) , + `videoUrl` VARCHAR(255), `duration` INT not null, `year` VARCHAR(4) NOT NULL, `description` VARCHAR(500) not null, `IsAvailable` BOOLEAN NOT NULL ); -INSERT INTO - `Film` (`miniature`, `title`, `videoUrl`, `duration`, `year`, `description`, `IsAvailable`) -VALUES - ( +INSERT INTO + `Film` ( + `miniature`, + `title`, + `videoUrl`, + `duration`, + `year`, + `description`, + `IsAvailable` + ) +VALUES ( "https://m.media-amazon.com/images/M/MV5BMTkxM2FiYjctYjliYy00NjY2LWFmOTEtMWZiYWRjNjA4MGYxXkEyXkFqcGdeQXVyMTUzMTg2ODkz._V1_.jpg", "Aquaman and the Lost Kingdom", "https://www.youtube.com/watch?v=2wcj6SrX4zw", @@ -52,8 +59,7 @@ VALUES "2023", "The film is directed by James Wan from a screenplay written by David Leslie Johnson-McGoldrick and Will Beall and stars Jason Momoa as Aquaman, alongside Amber Heard, Patrick Wilson, Dolph Lundgren, Yahya Abdul-Mateen II, and Temuera Morrison. In the film, Aquaman must save the world from the threat of Ocean Master and Black Manta.", 1 - ), - ( + ), ( "https://cdn.entries.clios.com/styles/clio_aotw_ems_image_details_retina/s3/entry_attachments/image/72/2297/22197/123544/xBckjuirX08J68hRmi7_Zgv4jhFeC3AbYX8REOHE770.jpeg/xBckjuirX08J68hRmi7_Zgv4jhFeC3AbYX8REOHE770.jpeg", "The Batman", "https://www.youtube.com/watch?v=mqqft2x_Aa4", @@ -63,7 +69,6 @@ VALUES 1 ); - DROP TABLE IF EXISTS `Categorie`; CREATE TABLE @@ -161,34 +166,37 @@ CREATE TABLE PRIMARY KEY (`filmId`, `categorieId`) ); -INSERT INTO - `Film` (`miniature`, `title`, `duration`, `year`, `description`, `isAvailable`) -VALUES - ( +INSERT INTO + `Film` ( + `miniature`, + `title`, + `duration`, + `year`, + `description`, + `isAvailable` + ) +VALUES ( 'https://m.media-amazon.com/images/M/MV5BMTc5MDE2ODcwNV5BMl5BanBnXkFtZTgwMzI2NzQ2NzM@._V1_.jpg', 'Avengers: Endgame', 181, '2019', 'After the devastating events of Avengers: Infinity War (2018), the universe is in ruins. With the help of remaining allies, the Avengers assemble once more in order to reverse Thanos actions and restore balance to the universe.', 1 - ), - ( + ), ( 'https://m.media-amazon.com/images/M/MV5BMjMxNjY2MDU1OV5BMl5BanBnXkFtZTgwNzY1MTUwNTM@._V1_.jpg', 'Avengers: Infinity War', 149, '2018', 'The Avengers and their allies must be willing to sacrifice all in an attempt to defeat the powerful Thanos before his blitz of devastation and ruin puts an end to the universe.', 0 - ), - ( + ), ( 'https://m.media-amazon.com/images/M/MV5BNDYxNjQyMjAtNTdiOS00NGYwLWFmNTAtNThmYjU5ZGI2YTI1XkEyXkFqcGdeQXVyMTMxODk2OTU@._V1_.jpg', 'The Avengers', 143, '2012', 'Earth mightiest heroes must come together and learn to fight as a team if they are going to stop the mischievous Loki and his alien army from enslaving humanity.', 1 - ), - ( + ), ( 'https://static.wikia.nocookie.net/ironman/images/d/da/P170620_v_v8_ba.jpg/revision/latest?cb=20191202183622', 'Iron man', 126, @@ -199,50 +207,33 @@ VALUES INSERT INTO `Categorie` (`name`, `position`) -VALUES - ('Action', 1), - ('Adventure', 2), - ('Sci-Fi', 3), - ('Drama', 4), - ('Thriller', 5), - ('Comedy', 6), - ('Crime', 7), - ('Fantasy', 8), - ('Mystery', 9), - ('Animation', 10), - ('Family', 11), - ('Biography', 12), - ('History', 13), - ('Horror', 14), - ('Music', 15), - ('Musical', 16), - ('Romance', 17), - ('Sport', 18), - ('War', 19), - ('Western', 20); - -INSERT INTO - `User` (`name`, `email`,`naissance`, `civility`, `password`, `IsAdmin`) - VALUES - ( +VALUES ('Action', 1), ('Adventure', 2), ('Sci-Fi', 3), ('Drama', 4), ('Thriller', 5), ('Comedy', 6), ('Crime', 7), ('Fantasy', 8), ('Mystery', 9), ('Animation', 10), ('Family', 11), ('Biography', 12), ('History', 13), ('Horror', 14), ('Music', 15), ('Musical', 16), ('Romance', 17), ('Sport', 18), ('War', 19), ('Western', 20); + +INSERT INTO + `User` ( + `name`, + `email`, + `naissance`, + `civility`, + `password`, + `IsAdmin` + ) +VALUES ( 'Aurel', 'aurelien.emeriau@wcs.com', '1983/06/10', '0', 'ggfd4554', '0' - ), - ( + ), ( 'Alex', 'alex@wcs.com', '1998/03/19', '0', 'ggfd455', '0' - ); + ); -INSERT INTO +INSERT INTO `Favori_film` (`userId`, `filmId`) - VALUES - (1, 1), - (1, 2) \ No newline at end of file +VALUES (1, 1), (1, 2) \ No newline at end of file diff --git a/backend/src/controllers/favoriSerieControllers.js b/backend/src/controllers/favoriSerieControllers.js new file mode 100644 index 0000000..e88f0c0 --- /dev/null +++ b/backend/src/controllers/favoriSerieControllers.js @@ -0,0 +1,57 @@ +const tables = require("../tables"); + +const browse = async (req, res, next) => { + try { + const FavoriSeries = await tables.favori_serie.readAll(); + res.json(FavoriSeries); + } catch (err) { + next(err); + } +}; + +const read = async (req, res, next) => { + try { + const favoriSerie = await tables.favori_serie.read(req.params.id); + if (favoriSerie == null) { + res.sendStatus(404); + } else { + res.json(favoriSerie); + } + } catch (err) { + next(err); + } +}; + +const add = async (req, res, next) => { + const favorite = req.body; + + try { + const insertId = await tables.favori_serie.create(favorite); + res.status(200).json({ insertId }); + } catch (err) { + next(err); + } +}; + +const destroy = async (req, res, next) => { + const { id: userId } = req.params; + const { serieId } = req.body; + + try { + const [result] = await tables.favori_serie.delete(userId, serieId); + if (result.affectedRows) { + res.sendStatus(200); + } else { + res.sendStatus(404); + } + } catch (err) { + next(err); + } +}; + +module.exports = { + browse, + read, + add, + destroy, +}; diff --git a/backend/src/models/FavoriSerieManager.js b/backend/src/models/FavoriSerieManager.js new file mode 100644 index 0000000..d67b6b1 --- /dev/null +++ b/backend/src/models/FavoriSerieManager.js @@ -0,0 +1,41 @@ +/*eslint-disable*/ +const AbstractManager = require("./AbstractManager"); + +class FavoriSerieManager extends AbstractManager { + constructor() { + super({ table: "favori_serie" }); + } + + async create({ userId, serieId }) { + const [result] = await this.database.query( + `INSERT INTO ${this.table} (userId, serieId) values (?,?)`, + [userId, serieId] + ); + return result.insertId; + } + async read(id) { + const [result] = await this.database.query( + `select u.id, s.id, s.title + from Favori_serie fs + inner join user u on fs.userId = u.id + inner join serie s on fs.serieId = s.id + where fs.userId = ?`, + [id] + ); + return result; + } + async readAll() { + const [result] = await this.database.query(`select * from ${this.table}`); + return result; + } + + async delete(userId, serieId) { + const result = await this.database.query( + `delete from ${this.table} where userId = ? and serieId = ?`, + [userId, serieId] + ); + return result; + } +} + +module.exports = FavoriSerieManager; diff --git a/backend/src/router.js b/backend/src/router.js index 10c47d8..65a84b3 100644 --- a/backend/src/router.js +++ b/backend/src/router.js @@ -12,6 +12,7 @@ const filmControllers = require("./controllers/filmControllers"); const userControllers = require("./controllers/userControllers"); const serieControllers = require("./controllers/serieControllers"); const favoriFilmControllers = require("./controllers/favoriFilmControllers"); +const favoriSerieControllers = require("./controllers/favoriSerieControllers"); // const categorieParFilmControllers = require("./controllers/categorieParFilmControllers"); // Route to get a list of items @@ -19,13 +20,15 @@ router.get("/categories", categorieControllers.browse); router.get("/films", filmControllers.browse); router.get("/series", serieControllers.browse); router.get("/users", userControllers.browse); -router.get("/favorites", favoriFilmControllers.browse); +router.get("/favorites/film", favoriFilmControllers.browse); +router.get("/favorites/serie", favoriSerieControllers.browse); // Route to get a specific item by ID router.get("/categories/:id", categorieControllers.read); router.get("/films/:id", filmControllers.read); router.get("/series/:id", serieControllers.read); router.get("/users/:id", userControllers.read); -router.get("/favorites/:id", favoriFilmControllers.read); +router.get("/favorites/film/:id", favoriFilmControllers.read); +router.get("/favorites/serie/:id", favoriSerieControllers.read); // Route to edit a specific item by ID router.put("/categories/:id", categorieControllers.edit); @@ -38,13 +41,15 @@ router.post("/categories", categorieControllers.add); router.post("/films", filmControllers.add); router.post("/series", serieControllers.add); router.post("/users", userControllers.add); -router.post("/favorites", favoriFilmControllers.add); +router.post("/favorites/film", favoriFilmControllers.add); +router.post("/favorites/serie", favoriSerieControllers.add); // Route to delete a specific item by ID router.delete("/categories/:id", categorieControllers.destroy); router.delete("/films/:id", filmControllers.destroy); router.delete("/series/:id", serieControllers.destroy); router.delete("/users/:id", userControllers.destroy); -router.delete("/favorites/:id", favoriFilmControllers.destroy); +router.delete("/favorites/film/:id", favoriFilmControllers.destroy); +router.delete("/favorites/serie/:id", favoriSerieControllers.destroy); module.exports = router; diff --git a/backend/src/tables.js b/backend/src/tables.js index b1cf080..52613eb 100644 --- a/backend/src/tables.js +++ b/backend/src/tables.js @@ -8,6 +8,7 @@ const UserManager = require("./models/UserManager"); const FilmManager = require("./models/FilmManager"); const SerieManager = require("./models/SerieManager"); const FavoriFilmManager = require("./models/FavoriFilmManager"); +const FavoriSerieManager = require("./models/FavoriSerieManager"); const CategorieParFilmManager = require("./models/CategorieParFilmManager"); const managers = [ @@ -16,7 +17,9 @@ const managers = [ FilmManager, SerieManager, FavoriFilmManager, + FavoriSerieManager, CategorieParFilmManager, + // Add other managers here ]; From 2813bd5350cc56e943dad7c0e70fdc5afe5ce73b Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Thu, 14 Dec 2023 15:30:01 +0100 Subject: [PATCH 36/44] implementing movie page --- .../src/assets/icons/play_button_icon.svg | 10 ++ frontend/src/pages/Movie.jsx | 60 ++++++- frontend/src/sass/_home.scss | 3 +- frontend/src/sass/_movie.scss | 149 ++++++++++++++++++ frontend/src/sass/_settings.scss | 1 + frontend/src/sass/index.scss | 1 + 6 files changed, 222 insertions(+), 2 deletions(-) create mode 100644 frontend/src/assets/icons/play_button_icon.svg create mode 100644 frontend/src/sass/_movie.scss diff --git a/frontend/src/assets/icons/play_button_icon.svg b/frontend/src/assets/icons/play_button_icon.svg new file mode 100644 index 0000000..195c6cc --- /dev/null +++ b/frontend/src/assets/icons/play_button_icon.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/frontend/src/pages/Movie.jsx b/frontend/src/pages/Movie.jsx index 40286fc..d80ca8c 100644 --- a/frontend/src/pages/Movie.jsx +++ b/frontend/src/pages/Movie.jsx @@ -1,11 +1,69 @@ import { useParams } from "react-router-dom"; +import { useMovies } from "../contexts/MovieContext"; function Movie() { const { movieId } = useParams(); + const { movies } = useMovies(); + console.info(movies); if (!movieId) { return

Movie not found

; } - return

Movie {movieId}

; + return ( +
+ {movies + .filter((movie) => { + return movie.id === parseInt(movieId, 10); + }) + .map((movie) => { + return ( +
+
+ {movie.title} +
+
+ play button +
+
+
+
+
+

{movie.year}

+

+

{movie.duration}m

+
+
+
+

{movie.title}

+

{movie.description}

+
+
+
+

Commentaires

+
+
+
+

+ Connectez-vous pour laisser un commentaire +

+
+
+
+
+ ); + })} +
+ ); } export default Movie; diff --git a/frontend/src/sass/_home.scss b/frontend/src/sass/_home.scss index 1aedc3b..569f46a 100644 --- a/frontend/src/sass/_home.scss +++ b/frontend/src/sass/_home.scss @@ -129,7 +129,8 @@ align-items: center; gap: calc(var(--spacing-constant) * 1); display: flex; - overflow-x: scroll; + // overflow-x: scroll; + flex-wrap: wrap; } } } diff --git a/frontend/src/sass/_movie.scss b/frontend/src/sass/_movie.scss new file mode 100644 index 0000000..e7a0230 --- /dev/null +++ b/frontend/src/sass/_movie.scss @@ -0,0 +1,149 @@ +.movie-page-details { + width: 100%; + height: 100%; + flex-direction: column; + display: flex; + flex: 1; + overflow-y: scroll; + + .movie-information-display { + align-self: stretch; + height: 100%; + flex-direction: column; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .thumbnail-container { + align-self: stretch; + height: 206px; + flex-direction: column; + gap: calc(var(--spacing-constant) * 1); + display: flex; + justify-content: center; + position: relative; + + .movie-cover { + align-self: stretch; + height: 100%; + flex-direction: column; + display: flex; + object-fit: cover; + } + + .upper-layer { + height: 100%; + background: hsla(0, 0%, 0%, 0.1); + justify-content: center; + align-items: center; + align-self: stretch; + flex-direction: column; + display: flex; + position: absolute; + top: 0; + left: 0; + right: 0; + bottom: 0; + + .play-button-container { + width: 34px; + height: 34px; + position: relative; + + .play-button { + width: 100%; + height: 100%; + } + } + } + } + + .details-option-wrapper { + align-self: stretch; + padding: 0 calc(var(--spacing-constant) * 1); + justify-content: space-between; + align-items: center; + display: flex; + + .details-container { + padding: 0 calc(var(--spacing-constant) * 1); + gap: calc(var(--spacing-constant) * 1); + display: flex; + align-items: center; + + .movie-info { + font-size: calc(var(--font-size-constant) * 1.2); + } + } + } + + .description-container { + align-self: stretch; + padding: 0 calc(var(--spacing-constant) * 1); + flex-direction: column; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .movie-title { + font-size: calc(var(--font-size-constant) * 1.4); + font-weight: var(--font-weight-semi-bold); + text-decoration: underline; + } + + .movie-description { + font-size: calc(var(--font-size-constant) * 1.2); + } + } + + .comments-section { + padding: 0 calc(var(--spacing-constant) * 1); + flex-direction: column; + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .comments-section-title { + align-self: stretch; + padding: 0 calc(var(--spacing-constant) * 1); + gap: calc(var(--spacing-constant) * 1); + display: flex; + + .comments-section-title-text { + font-size: calc(var(--font-size-constant) * 1.4); + font-weight: var(--font-weight-semi-bold); + text-decoration: underline; + } + } + + .comments-section-content { + align-self: stretch; + padding: 0 calc(var(--spacing-constant) * 1); + gap: calc(var(--spacing-constant) * 1); + display: flex; + flex: 1; + + .registration-invitation-container { + flex: 1 1 0; + align-self: stretch; + padding: calc(var(--spacing-constant) * 0.5) + calc(var(--spacing-constant) * 1); + background: var(--text-field-background-color); + justify-content: center; + align-items: center; + display: flex; + height: var(--comment-section-height, 200px); + border-radius: var(--border-radius-constant, 10px); + + .registration-invitation { + font-size: calc(var(--font-size-constant) * 2); + font-weight: var(--font-weight-semi-bold); + text-align: center; + color: var(--text-field-color, hsla(210, 89%, 7%, 1)); + } + } + } + } + } +} + +.movie-page-details::-webkit-scrollbar { + display: none; +} diff --git a/frontend/src/sass/_settings.scss b/frontend/src/sass/_settings.scss index 91ac9b8..2359e83 100644 --- a/frontend/src/sass/_settings.scss +++ b/frontend/src/sass/_settings.scss @@ -3,6 +3,7 @@ --background-color: hsla(210, 89%, 7%, 1); --primary-font-color: hsla(53, 82%, 66%, 1); --secondary-font-color: hsla(335, 100%, 66%, 1); + --text-field-background-color: hsla(0, 0%, 86%, 1); // ^ fonts --main-font: "Roboto Flex", sans-serif; diff --git a/frontend/src/sass/index.scss b/frontend/src/sass/index.scss index 0a6b4ed..6d6b0f5 100644 --- a/frontend/src/sass/index.scss +++ b/frontend/src/sass/index.scss @@ -4,3 +4,4 @@ @import "search"; @import "navbar"; @import "movieSlide"; +@import "movie"; From 00cd81f0fcf8c692b8ec7bd8ab201a1cc74f7262 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Thu, 14 Dec 2023 15:33:02 +0100 Subject: [PATCH 37/44] adding video field in movie table --- backend/database/schema.sql | 408 +++++++++++++++-------------- backend/src/models/SerieManager.js | 2 - 2 files changed, 215 insertions(+), 195 deletions(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 79076d3..d4ed78a 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -1,31 +1,31 @@ -DROP TABLE IF EXISTS `Serie`; +-- DROP TABLE IF EXISTS `Serie`; -CREATE TABLE - `Serie` ( - `id` int primary key auto_increment not null, - `miniature` varchar(255) not null, - `title` VARCHAR(50) not NULL, - `videoUrl` VARCHAR(255) , - `duration` INT not NULL, - `year` VARCHAR(4) not NULL, - `description` VARCHAR(500) not NULL, - `isAvailable` BOOLEAN not NULL, - `episodesNumber` INT not NULL, - `seasonsNumber` INT not NULL - ); +-- CREATE TABLE +-- `Serie` ( +-- `id` int primary key auto_increment not null, +-- `miniature` varchar(255) not null, +-- `title` VARCHAR(50) not NULL, +-- `videoUrl` VARCHAR(255), +-- `duration` INT not NULL, +-- `year` VARCHAR(4) not NULL, +-- `description` VARCHAR(500) not NULL, +-- `isAvailable` BOOLEAN not NULL, +-- `episodesNumber` INT not NULL, +-- `seasonsNumber` INT not NULL +-- ); -DROP TABLE IF EXISTS `User`; +-- DROP TABLE IF EXISTS `User`; -CREATE TABLE - `User` ( - `id` int primary key auto_increment not null, - `name` varchar(50) not null, - `email` varchar(50) not null, - `naissance` DATE NOT NULL, - `civility` BOOLEAN NOT NULL, - `password` varchar(50) not null, - `IsAdmin` bool not null - ); +-- CREATE TABLE +-- `User` ( +-- `id` int primary key auto_increment not null, +-- `name` varchar(50) not null, +-- `email` varchar(50) not null, +-- `naissance` DATE NOT NULL, +-- `civility` BOOLEAN NOT NULL, +-- `password` varchar(50) not null, +-- `IsAdmin` bool not null +-- ); DROP TABLE IF EXISTS `Film`; @@ -33,19 +33,70 @@ CREATE TABLE `Film` ( `id` int primary key auto_increment not null, `miniature` VARCHAR(255) not null, + `cover` VARCHAR(255) NOT NULL, `title` VARCHAR(255) not null, - `videoUrl` VARCHAR(255) , + `videoUrl` VARCHAR(255), `duration` INT not null, `year` VARCHAR(4) NOT NULL, - `description` VARCHAR(500) not null, + `description` VARCHAR(700) not null, `IsAvailable` BOOLEAN NOT NULL ); -INSERT INTO - `Film` (`miniature`, `title`, `videoUrl`, `duration`, `year`, `description`, `IsAvailable`) -VALUES +INSERT INTO + `Film` ( + `miniature`, + `cover`, + `title`, + `videoUrl`, + `duration`, + `year`, + `description`, + `IsAvailable` + ) +VALUES + ( + 'https://m.media-amazon.com/images/M/MV5BMTc5MDE2ODcwNV5BMl5BanBnXkFtZTgwMzI2NzQ2NzM@._V1_.jpg', + 'https://w0.peakpx.com/wallpaper/34/966/HD-wallpaper-the-avengers-avengers-endgame-avengers-avengers-endgame.jpg', + 'Avengers: Endgame', + 'https://www.youtube.com/watch?v=TcMBFSGVi1c', + 181, + '2019', + 'After the devastating events of Avengers: Infinity War (2018), the universe is in ruins. With the help of remaining allies, the Avengers assemble once more in order to reverse Thanos actions and restore balance to the universe.', + 1 + ), + ( + 'https://m.media-amazon.com/images/M/MV5BMjMxNjY2MDU1OV5BMl5BanBnXkFtZTgwNzY1MTUwNTM@._V1_.jpg', + 'https://www.highlandernews.org/wp-content/uploads/landscape-1522924460-avengers-infinity-war-poster.jpg', + 'Avengers: Infinity War', + 'https://www.youtube.com/watch?v=6ZfuNTqbHE8', + 149, + '2018', + 'The Avengers and their allies must be willing to sacrifice all in an attempt to defeat the powerful Thanos before his blitz of devastation and ruin puts an end to the universe.', + 1 + ), + ( + 'https://m.media-amazon.com/images/M/MV5BNDYxNjQyMjAtNTdiOS00NGYwLWFmNTAtNThmYjU5ZGI2YTI1XkEyXkFqcGdeQXVyMTMxODk2OTU@._V1_.jpg', + 'https://pbs.twimg.com/media/EJHjitpUUAA2EAp.jpg', + 'The Avengers', + 'https://www.youtube.com/watch?v=eOrNdBpGMv8', + 143, + '2012', + 'Earth mightiest heroes must come together and learn to fight as a team if they are going to stop the mischievous Loki and his alien army from enslaving humanity.', + 1 + ), + ( + 'https://i.ebayimg.com/images/g/Sv8AAOSwb7Rc0l0P/s-l1600.jpg', + 'https://wallpapercave.com/wp/wp11799668.jpg', + 'Iron man', + 'https://www.youtube.com/watch?v=8hYlB38asDY', + 126, + '2008', + 'After being held captive in an Afghan cave, billionaire engineer Tony Stark creates a unique weaponized suit of armor to fight evil.', + 1 + ), ( "https://m.media-amazon.com/images/M/MV5BMTkxM2FiYjctYjliYy00NjY2LWFmOTEtMWZiYWRjNjA4MGYxXkEyXkFqcGdeQXVyMTUzMTg2ODkz._V1_.jpg", + 'https://www.wheninmanila.com/wp-content/uploads/2023/11/SHARED-Cover-Collage-x2-30-2.png', "Aquaman and the Lost Kingdom", "https://www.youtube.com/watch?v=2wcj6SrX4zw", 120, @@ -55,6 +106,7 @@ VALUES ), ( "https://cdn.entries.clios.com/styles/clio_aotw_ems_image_details_retina/s3/entry_attachments/image/72/2297/22197/123544/xBckjuirX08J68hRmi7_Zgv4jhFeC3AbYX8REOHE770.jpeg/xBckjuirX08J68hRmi7_Zgv4jhFeC3AbYX8REOHE770.jpeg", + 'https://w0.peakpx.com/wallpaper/307/244/HD-wallpaper-batman-the-batman.jpg', "The Batman", "https://www.youtube.com/watch?v=mqqft2x_Aa4", 120, @@ -63,186 +115,156 @@ VALUES 1 ); +-- DROP TABLE IF EXISTS `Categorie`; -DROP TABLE IF EXISTS `Categorie`; +-- CREATE TABLE +-- `Categorie` ( +-- `id` int primary key auto_increment not null, +-- `name` VARCHAR(255) not null, +-- `position` INT +-- ); -CREATE TABLE - `Categorie` ( - `id` int primary key auto_increment not null, - `name` VARCHAR(255) not null, - `position` INT - ); +-- DROP TABLE IF EXISTS `Favori_film`; -DROP TABLE IF EXISTS `Favori_film`; +-- CREATE TABLE +-- `Favori_film` ( +-- `userId` INT NOT NULL, +-- `filmId` INT NOT NULL, +-- CONSTRAINT FK_Favori_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User` (`id`), +-- CONSTRAINT FK_Favori_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film` (`id`), +-- PRIMARY KEY (`userId`, `filmId`) +-- ); -CREATE TABLE - `Favori_film` ( - `userId` INT NOT NULL, - `filmId` INT NOT NULL, - CONSTRAINT FK_Favori_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), - CONSTRAINT FK_Favori_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), - PRIMARY KEY(`userId`, `filmId`) - ); +-- DROP TABLE IF EXISTS `Favori_serie`; -DROP TABLE IF EXISTS `Favori_serie`; +-- CREATE TABLE +-- `Favori_serie` ( +-- `userId` INT NOT NULL, +-- `serieId` INT NOT NULL, +-- CONSTRAINT FK_Favori_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User` (`id`), +-- CONSTRAINT FK_Favori_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie` (`id`), +-- PRIMARY KEY (`userId`, `serieId`) +-- ); -CREATE TABLE - `Favori_serie` ( - `userId` INT NOT NULL, - `serieId` INT NOT NULL, - CONSTRAINT FK_Favori_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), - CONSTRAINT FK_Favori_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie`(`id`), - PRIMARY KEY (`userId`, `serieId`) - ); +-- DROP TABLE IF EXISTS `En_tendance_film`; -DROP TABLE IF EXISTS `En_tendance_film`; +-- CREATE TABLE +-- `En_tendance_film` ( +-- `userId` INT NOT NULL, +-- `filmId` INT NOT NULL, +-- CONSTRAINT FK_En_tendance_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User` (`id`), +-- CONSTRAINT FK_En_tendance_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film` (`id`), +-- PRIMARY KEY (`userId`, `filmId`) +-- ); -CREATE TABLE - `En_tendance_film` ( - `userId` INT NOT NULL, - `filmId` INT NOT NULL, - CONSTRAINT FK_En_tendance_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), - CONSTRAINT FK_En_tendance_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), - PRIMARY KEY (`userId`, `filmId`) - ); +-- DROP TABLE IF EXISTS ` En_tendance_serie`; -DROP TABLE IF EXISTS ` En_tendance_serie`; +-- CREATE TABLE +-- `En_tendance_serie` ( +-- `userId` INT NOT NULL, +-- `serieId` INT NOT NULL, +-- CONSTRAINT FK_En_tendance_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User` (`id`), +-- CONSTRAINT FK_En_tendance_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie` (`id`), +-- PRIMARY KEY (`userId`, `serieId`) +-- ); -CREATE TABLE - `En_tendance_serie` ( - `userId` INT NOT NULL, - `serieId` INT NOT NULL, - CONSTRAINT FK_En_tendance_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), - CONSTRAINT FK_En_tendance_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie`(`id`), - PRIMARY KEY (`userId`, `serieId`) - ); +-- DROP TABLE IF EXISTS `Commentaire_serie`; -DROP TABLE IF EXISTS `Commentaire_serie`; +-- CREATE TABLE +-- `Commentaire_serie` ( +-- `userId` INT NOT NULL, +-- `serieId` INT NOT NULL, +-- CONSTRAINT FK_Commentaire_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User` (`id`), +-- CONSTRAINT FK_Commentaire_serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie` (`id`), +-- PRIMARY KEY (`userId`, `serieId`) +-- ); -CREATE TABLE - `Commentaire_serie` ( - `userId` INT NOT NULL, - `serieId` INT NOT NULL, - CONSTRAINT FK_Commentaire_Serie_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), - CONSTRAINT FK_Commentaire_serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie`(`id`), - PRIMARY KEY (`userId`, `serieId`) - ); +-- DROP TABLE IF EXISTS `Commentaire_film`; -DROP TABLE IF EXISTS `Commentaire_film`; +-- CREATE TABLE +-- `Commentaire_film` ( +-- `userId` INT NOT NULL, +-- `filmId` INT NOT NULL, +-- CONSTRAINT FK_Commentaire_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User` (`id`), +-- CONSTRAINT FK_Commentaire_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film` (`id`), +-- PRIMARY KEY (`userId`, `filmId`) +-- ); -CREATE TABLE - `Commentaire_film` ( - `userId` INT NOT NULL, - `filmId` INT NOT NULL, - CONSTRAINT FK_Commentaire_Film_user_id FOREIGN KEY (`userId`) REFERENCES `User`(`id`), - CONSTRAINT FK_Commentaire_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), - PRIMARY KEY (`userId`, `filmId`) - ); +-- DROP TABLE IF EXISTS `Categorie_par_serie`; -DROP TABLE IF EXISTS `Categorie_par_serie`; +-- CREATE TABLE +-- `Categorie_par_serie` ( +-- `serieId` INT NOT NULL, +-- `categorieId` INT NOT NULL, +-- CONSTRAINT FK_Categorie_Par_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie` (`id`), +-- CONSTRAINT FK_Categorie_Par_Serie_categorie_id FOREIGN KEY (`categorieId`) REFERENCES `Categorie` (`id`), +-- PRIMARY KEY (`serieId`, `categorieId`) +-- ); -CREATE TABLE - `Categorie_par_serie` ( - `serieId` INT NOT NULL, - `categorieId` INT NOT NULL, - CONSTRAINT FK_Categorie_Par_Serie_serie_id FOREIGN KEY (`serieId`) REFERENCES `Serie`(`id`), - CONSTRAINT FK_Categorie_Par_Serie_categorie_id FOREIGN KEY (`categorieId`) REFERENCES `Categorie`(`id`), - PRIMARY KEY (`serieId`, `categorieId`) - ); +-- DROP TABLE IF EXISTS `Categorie_par_film`; -DROP TABLE IF EXISTS `Categorie_par_film`; +-- CREATE TABLE +-- `Categorie_par_film` ( +-- `filmId` INT NOT NULL, +-- `categorieId` INT NOT NULL, +-- CONSTRAINT FK_Categorie_Par_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film` (`id`), +-- CONSTRAINT FK_Categorie_Par_Film_categorie_id FOREIGN KEY (`categorieId`) REFERENCES `Categorie` (`id`), +-- PRIMARY KEY (`filmId`, `categorieId`) +-- ); -CREATE TABLE - `Categorie_par_film` ( - `filmId` INT NOT NULL, - `categorieId` INT NOT NULL, - CONSTRAINT FK_Categorie_Par_Film_film_id FOREIGN KEY (`filmId`) REFERENCES `Film`(`id`), - CONSTRAINT FK_Categorie_Par_Film_categorie_id FOREIGN KEY (`categorieId`) REFERENCES `Categorie`(`id`), - PRIMARY KEY (`filmId`, `categorieId`) - ); +-- INSERT INTO +-- `Categorie` (`name`, `position`) +-- VALUES +-- ('Action', 1), +-- ('Adventure', 2), +-- ('Sci-Fi', 3), +-- ('Drama', 4), +-- ('Thriller', 5), +-- ('Comedy', 6), +-- ('Crime', 7), +-- ('Fantasy', 8), +-- ('Mystery', 9), +-- ('Animation', 10), +-- ('Family', 11), +-- ('Biography', 12), +-- ('History', 13), +-- ('Horror', 14), +-- ('Music', 15), +-- ('Musical', 16), +-- ('Romance', 17), +-- ('Sport', 18), +-- ('War', 19), +-- ('Western', 20); -INSERT INTO - `Film` (`miniature`, `title`, `duration`, `year`, `description`, `isAvailable`) -VALUES - ( - 'https://m.media-amazon.com/images/M/MV5BMTc5MDE2ODcwNV5BMl5BanBnXkFtZTgwMzI2NzQ2NzM@._V1_.jpg', - 'Avengers: Endgame', - 181, - '2019', - 'After the devastating events of Avengers: Infinity War (2018), the universe is in ruins. With the help of remaining allies, the Avengers assemble once more in order to reverse Thanos actions and restore balance to the universe.', - 1 - ), - ( - 'https://m.media-amazon.com/images/M/MV5BMjMxNjY2MDU1OV5BMl5BanBnXkFtZTgwNzY1MTUwNTM@._V1_.jpg', - 'Avengers: Infinity War', - 149, - '2018', - 'The Avengers and their allies must be willing to sacrifice all in an attempt to defeat the powerful Thanos before his blitz of devastation and ruin puts an end to the universe.', - 0 - ), - ( - 'https://m.media-amazon.com/images/M/MV5BNDYxNjQyMjAtNTdiOS00NGYwLWFmNTAtNThmYjU5ZGI2YTI1XkEyXkFqcGdeQXVyMTMxODk2OTU@._V1_.jpg', - 'The Avengers', - 143, - '2012', - 'Earth mightiest heroes must come together and learn to fight as a team if they are going to stop the mischievous Loki and his alien army from enslaving humanity.', - 1 - ), - ( - 'https://static.wikia.nocookie.net/ironman/images/d/da/P170620_v_v8_ba.jpg/revision/latest?cb=20191202183622', - 'Iron man', - 126, - '2008', - 'After being held captive in an Afghan cave, billionaire engineer Tony Stark creates a unique weaponized suit of armor to fight evil.', - 0 - ); +-- INSERT INTO +-- `User` ( +-- `name`, +-- `email`, +-- `naissance`, +-- `civility`, +-- `password`, +-- `IsAdmin` +-- ) +-- VALUES +-- ( +-- 'Aurel', +-- 'aurelien.emeriau@wcs.com', +-- '1983/06/10', +-- '0', +-- 'ggfd4554', +-- '0' +-- ), +-- ( +-- 'Alex', +-- 'alex@wcs.com', +-- '1998/03/19', +-- '0', +-- 'ggfd455', +-- '0' +-- ); -INSERT INTO - `Categorie` (`name`, `position`) -VALUES - ('Action', 1), - ('Adventure', 2), - ('Sci-Fi', 3), - ('Drama', 4), - ('Thriller', 5), - ('Comedy', 6), - ('Crime', 7), - ('Fantasy', 8), - ('Mystery', 9), - ('Animation', 10), - ('Family', 11), - ('Biography', 12), - ('History', 13), - ('Horror', 14), - ('Music', 15), - ('Musical', 16), - ('Romance', 17), - ('Sport', 18), - ('War', 19), - ('Western', 20); - -INSERT INTO - `User` (`name`, `email`,`naissance`, `civility`, `password`, `IsAdmin`) - VALUES - ( - 'Aurel', - 'aurelien.emeriau@wcs.com', - '1983/06/10', - '0', - 'ggfd4554', - '0' - ), - ( - 'Alex', - 'alex@wcs.com', - '1998/03/19', - '0', - 'ggfd455', - '0' - ); - -INSERT INTO - `Favori_film` (`userId`, `filmId`) - VALUES - (1, 1), - (1, 2); +-- INSERT INTO +-- `Favori_film` (`userId`, `filmId`) +-- VALUES +-- (1, 1), +-- (1, 2); \ No newline at end of file diff --git a/backend/src/models/SerieManager.js b/backend/src/models/SerieManager.js index 1139278..c0be0a7 100644 --- a/backend/src/models/SerieManager.js +++ b/backend/src/models/SerieManager.js @@ -61,7 +61,6 @@ class SerieManager extends AbstractManager { seasonsNumber, }) { const [result] = await this.database.query( - `UPDATE ${this.table} SET miniature=?, title=?, videoUrl=?, duration=?, year=?, description=?, isAvailable=?, episodesNumber=?, seasonsNumber=? WHERE id=?`, [ miniature, @@ -77,7 +76,6 @@ class SerieManager extends AbstractManager { ] ); return result.affectedRows; - } async delete(id) { const result = await this.database.query( From 8b50fc1de8cb8f24fa183350a3d6d9a2411cf7b2 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Fri, 15 Dec 2023 00:23:02 +0100 Subject: [PATCH 38/44] working on video player --- frontend/src/components/MovieSlide.jsx | 1 - frontend/src/main.jsx | 5 + frontend/src/pages/Home.jsx | 2 +- frontend/src/pages/Movie.jsx | 136 ++++++++++++++++++------- frontend/src/pages/MoviePlayer.jsx | 32 ++++++ frontend/src/sass/_movie.scss | 49 +++++++++ frontend/src/sass/_moviePlayer.scss | 2 + 7 files changed, 190 insertions(+), 37 deletions(-) create mode 100644 frontend/src/pages/MoviePlayer.jsx create mode 100644 frontend/src/sass/_moviePlayer.scss diff --git a/frontend/src/components/MovieSlide.jsx b/frontend/src/components/MovieSlide.jsx index 8aa00b0..4f22d0d 100644 --- a/frontend/src/components/MovieSlide.jsx +++ b/frontend/src/components/MovieSlide.jsx @@ -4,7 +4,6 @@ import PropTypes from "prop-types"; function MovieSlide({ movie }) { if (movie.IsAvailable) { return ( - // {movie.title} ); } diff --git a/frontend/src/main.jsx b/frontend/src/main.jsx index 4feafe2..c5d2a82 100644 --- a/frontend/src/main.jsx +++ b/frontend/src/main.jsx @@ -6,6 +6,7 @@ import App from "./App"; import Home from "./pages/Home"; import Search from "./pages/Search"; import Movie from "./pages/Movie"; +import MoviePlayer from "./pages/MoviePlayer"; import "./sass/index.scss"; const router = createBrowserRouter([ @@ -29,6 +30,10 @@ const router = createBrowserRouter([ path: "/movies/:movieId", element: , }, + { + path: "/moviePlayer/:movieId", + element: , + }, ], }, ]); diff --git a/frontend/src/pages/Home.jsx b/frontend/src/pages/Home.jsx index a44b751..b5f8329 100644 --- a/frontend/src/pages/Home.jsx +++ b/frontend/src/pages/Home.jsx @@ -45,7 +45,7 @@ function Home() {
{movies.map((movie) => ( - + ))}
diff --git a/frontend/src/pages/Movie.jsx b/frontend/src/pages/Movie.jsx index d80ca8c..32fab51 100644 --- a/frontend/src/pages/Movie.jsx +++ b/frontend/src/pages/Movie.jsx @@ -1,60 +1,126 @@ -import { useParams } from "react-router-dom"; +import { useParams, NavLink } from "react-router-dom"; import { useMovies } from "../contexts/MovieContext"; function Movie() { const { movieId } = useParams(); const { movies } = useMovies(); - console.info(movies); + // console.info(movies); if (!movieId) { - return

Movie not found

; + return

Aucun film trouvé.

; } return ( -
+ <> {movies .filter((movie) => { return movie.id === parseInt(movieId, 10); }) .map((movie) => { + if (movie.IsAvailable) { + return ( +
+
+
+ {movie.title} +
+ + play button + +
+
+
+
+

{movie.year}

+

+

{movie.duration}m

+
+
+
+

{movie.title}

+

{movie.description}

+
+
+
+

+ Commentaires +

+
+
+
+

+ Connectez-vous pour laisser un commentaire. +

+
+
+
+
+
+ ); + } return (
-
- {movie.title} -
-
+
+
+
play button +
+
+ play button +
+
+
+
+
+

{movie.year}

+

+

{movie.duration}m

+
+
+
+

{movie.title}

+

{movie.description}

+
+
+
+

+ Commentaires +

+
+
+
+

+ Connectez-vous pour laisser un commentaire. +

+
+
-
-
-
-

{movie.year}

-

-

{movie.duration}m

-
-
-
-

{movie.title}

-

{movie.description}

-
-
-
-

Commentaires

-
-
+

- Connectez-vous pour laisser un commentaire + Connectez-vous pour regarder ce film.

@@ -62,7 +128,7 @@ function Movie() {
); })} -
+ ); } diff --git a/frontend/src/pages/MoviePlayer.jsx b/frontend/src/pages/MoviePlayer.jsx new file mode 100644 index 0000000..2b5df2d --- /dev/null +++ b/frontend/src/pages/MoviePlayer.jsx @@ -0,0 +1,32 @@ +/* eslint-disable jsx-a11y/media-has-caption */ +import { useParams } from "react-router-dom"; +import { useMovies } from "../contexts/MovieContext"; + +function MoviePlayer() { + const { movieId } = useParams(); + const { movies } = useMovies(); + return ( +
+ {movies + .filter((movie) => { + return movie.id === parseInt(movieId, 10); + }) + .map((movie) => { + // console.info(movie.videoUrl); + return ( +
+
+
+
+ ); + })} +
+ ); +} + +export default MoviePlayer; diff --git a/frontend/src/sass/_movie.scss b/frontend/src/sass/_movie.scss index e7a0230..3421ea0 100644 --- a/frontend/src/sass/_movie.scss +++ b/frontend/src/sass/_movie.scss @@ -142,6 +142,55 @@ } } } + + .movie-information-display-wrapper { + width: 100%; + height: 100%; + flex-direction: column; + display: flex; + flex: 1; + position: relative; + + .movie-information-display { + filter: blur(2px); + } + + .upper-layer { + height: 100%; + background: hsla(0, 0%, 0%, 0.1); + justify-content: center; + align-items: center; + align-self: stretch; + flex-direction: column; + display: flex; + position: absolute; + top: 0; + left: 0; + right: 0; + bottom: 0; + + .registration-invitation-container { + align-self: stretch; + padding: calc(var(--spacing-constant) * 0.5) + calc(var(--spacing-constant) * 1); + background: var(--text-field-background-color); + justify-content: center; + align-items: center; + display: flex; + height: var(--comment-section-height, 200px); + border-radius: var(--border-radius-constant, 10px); + width: 90%; + margin: 0 auto; + + .registration-invitation { + font-size: calc(var(--font-size-constant) * 2); + font-weight: var(--font-weight-semi-bold); + text-align: center; + color: var(--text-field-color, hsla(210, 89%, 7%, 1)); + } + } + } + } } .movie-page-details::-webkit-scrollbar { diff --git a/frontend/src/sass/_moviePlayer.scss b/frontend/src/sass/_moviePlayer.scss new file mode 100644 index 0000000..0d0e6f0 --- /dev/null +++ b/frontend/src/sass/_moviePlayer.scss @@ -0,0 +1,2 @@ +.movie-player-wrapper { +} From 7a3ce037e11587904501a1c08a272a8b87e88e35 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Fri, 15 Dec 2023 00:24:46 +0100 Subject: [PATCH 39/44] updating --- backend/database/schema.sql | 20 +++++--------------- backend/src/app.js | 3 --- 2 files changed, 5 insertions(+), 18 deletions(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index 81ce95f..18d9022 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -62,7 +62,7 @@ VALUES 181, '2019', 'After the devastating events of Avengers: Infinity War (2018), the universe is in ruins. With the help of remaining allies, the Avengers assemble once more in order to reverse Thanos actions and restore balance to the universe.', - 1 + 0 ), ( 'https://m.media-amazon.com/images/M/MV5BMjMxNjY2MDU1OV5BMl5BanBnXkFtZTgwNzY1MTUwNTM@._V1_.jpg', @@ -82,7 +82,7 @@ VALUES 143, '2012', 'Earth mightiest heroes must come together and learn to fight as a team if they are going to stop the mischievous Loki and his alien army from enslaving humanity.', - 1 + 0 ), ( 'https://i.ebayimg.com/images/g/Sv8AAOSwb7Rc0l0P/s-l1600.jpg', @@ -102,7 +102,7 @@ VALUES 120, "2023", "The film is directed by James Wan from a screenplay written by David Leslie Johnson-McGoldrick and Will Beall and stars Jason Momoa as Aquaman, alongside Amber Heard, Patrick Wilson, Dolph Lundgren, Yahya Abdul-Mateen II, and Temuera Morrison. In the film, Aquaman must save the world from the threat of Ocean Master and Black Manta.", - 1 + 0 ), ( "https://cdn.entries.clios.com/styles/clio_aotw_ems_image_details_retina/s3/entry_attachments/image/72/2297/22197/123544/xBckjuirX08J68hRmi7_Zgv4jhFeC3AbYX8REOHE770.jpeg/xBckjuirX08J68hRmi7_Zgv4jhFeC3AbYX8REOHE770.jpeg", @@ -136,7 +136,7 @@ VALUES ), ( 'https://static.posters.cz/image/1300/art-photo/harry-potter-and-the-half-blood-prince-i167377.jpg', - 'https://picfiles.alphacoders.com/621/62184.jpg' + 'https://picfiles.alphacoders.com/621/62184.jpg', 'Harry Potter and the Half-Blood Prince', 'https://www.youtube.com/watch?v=tAiy66Xrsz4&ab_channel=HarryPotter', 153, @@ -162,7 +162,7 @@ VALUES 155, '2000', 'The Roman general Maximus is the most faithful support of the Emperor Marcus Aurelius, whom he led from victory to victory with exemplary bravery and dedication. Jealous of Maximus prestige, and even more so of the emperor love for him, Marcus Aurelius son, Commodus, brutally assumed power, then ordered the general arrest and execution. Maximus escapes his assassins but cannot prevent the massacre of his family. Captured by a slave trader, he becomes a gladiator and plots his revenge', - 1 + 0 ), ( 'https://fr.web.img6.acsta.net/medias/nmedia/18/82/69/17/19806656.jpg', @@ -173,16 +173,6 @@ VALUES '2011', 'Following a paragliding accident, Philippe, a rich aristocrat, hires Driss, a young man from the suburbs who has just been released from prison, as a home helper. In short the least appropriate person for the job. Together they will bring together Vivaldi and Earth Wind and Fire, the word and the joke, the costumes and the tracksuit bottoms... Two universes will collide, tame each other, to give birth to a friendship as crazy, funny and strong than unexpected, a unique relationship that will spark and make them... Untouchable.', 1 - ), - ( - 'https://fr.web.img2.acsta.net/medias/nmedia/18/84/94/35/20078430.jpg', - 'https://radiodisneyclub.fr/wp-content/uploads/2017/09/Braveentete-e1504969060697-700x359.jpg', - 'Rebelle', - 'https://www.youtube.com/watch?v=TEHWDA_6e3M&ab_channel=Pixar', - 95, - '2012', - 'Since the dawn of time, in the heart of the wild and mysterious lands of the Scottish Highlands, stories of epic battles and mythical legends have been passed down from generation to generation.', - 1 ); -- DROP TABLE IF EXISTS `Categorie`; diff --git a/backend/src/app.js b/backend/src/app.js index 1fc3165..6574349 100644 --- a/backend/src/app.js +++ b/backend/src/app.js @@ -31,9 +31,6 @@ app.use( cors({ origin: [ process.env.FRONTEND_URL, // keep this one, after checking the value in `backend/.env` - "http://mysite.com", - "http://another-domain.com", - "http://wildtube.com", ], }) ); From 2a9bfc1793bc085c954c00605f121e5b33669b32 Mon Sep 17 00:00:00 2001 From: Techer Tony Date: Fri, 15 Dec 2023 09:22:37 +0100 Subject: [PATCH 40/44] jointure favori serie ok --- backend/database/schema.sql | 138 +++++++++++++++++++----------------- 1 file changed, 72 insertions(+), 66 deletions(-) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index e1b3dfe..c57be10 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -8,7 +8,7 @@ CREATE TABLE `videoUrl` VARCHAR(255), `duration` INT not NULL, `year` VARCHAR(4) not NULL, - `description` VARCHAR(500) not NULL, + `description` TEXT not NULL, `isAvailable` BOOLEAN not NULL, `episodesNumber` INT not NULL, `seasonsNumber` INT not NULL @@ -69,6 +69,37 @@ VALUES ( 1 ); +INSERT INTO + `Serie` ( + `miniature`, + `title`, + `duration`, + `year`, + `description`, + `IsAvailable`, + `episodesNumber`, + `seasonsNumber` + ) +VALUES ( + "https://fr.web.img6.acsta.net/r_1280_720/pictures/23/01/30/15/02/5217749.jpg", + 'One Piece', + 55, + '2023', + 'Monkey D. Luffy is a young adventurer who has always dreamed of a life of freedom. Leaving his village, he embarks on a perilous journey in search of a mythical treasure, the One Piece, in order to become the king of the pirates! But to find this famous loot, Luffy will have to assemble the crew of his dreams then find a ship, crisscross the oceans, get rid of the Navy on his heels and prove himself to be a better strategist than the dangerous rivals who await him at every step.', + 1, + 9, + 1 + ), ( + "https://fr.web.img2.acsta.net/pictures/19/08/02/15/12/4423178.jpg", + "Naruto", + 22, + "2002", + "In the village of Konoha lives Naruto, a young boy hated and feared by the villagers, due to the fact that he holds within him Kyuubi (nine-tailed fox demon) of incredible strength, who has killed a large number of people. Konoha's most powerful ninja at the time, Minato Namikaze, managed to seal this demon in Naruto's body. This is how twelve years later, Naruto dreams of becoming the greatest Hokage of Konoha so that everyone will recognize his true worth. But the road to becoming Hokage is very long.", + 1, + 224, + 9 + ); + DROP TABLE IF EXISTS `Categorie`; CREATE TABLE @@ -196,152 +227,133 @@ VALUES ( '2012', 'Earth mightiest heroes must come together and learn to fight as a team if they are going to stop the mischievous Loki and his alien army from enslaving humanity.', 1 - ), - ( + ), ( 'https://fr.web.img6.acsta.net/c_310_420/medias/nmedia/18/62/89/45/18876909.jpg', 'Iron man', 126, '2008', 'After being held captive in an Afghan cave, billionaire engineer Tony Stark creates a unique weaponized suit of armor to fight evil.', 0 - ), - ( + ), ( 'https://fr.web.img2.acsta.net/medias/nmedia/18/70/76/18/19444000.jpg', 'the last airbender', 103, '2010', 'Air, Water, Earth, Fire: the balance of the world is tipped by a savage war waged for a century already by the Fire Nation against the three other nations. Challenging his courage and combat skills, Aang discovers that he is the new Avatar, the only one capable of mastering all four elements. He joins forces with Katara, a Waterbender, and his older brother Sokka, to stop the Fire Nation before it is too late...', 0 - ), - ( + ), ( 'https://fr.web.img4.acsta.net/pictures/21/11/17/17/24/3336846.jpg', 'Matrix Resurrections', 148, '2020', - 'MATRIX RESURRECTIONS takes us back into two parallel realities – that of our daily lives and that of the world hidden there. To know with certainty whether his own reality is a physical or mental construct, and to truly know himself, Mr. Anderson will have to follow the white rabbit again. ', + 'MATRIX RESURRECTIONS takes us back into two parallel realities – that of our daily lives and that of the world hidden there. To know with certainty whether his own reality is a physical or mental construct, and to truly know himself, Mr. Anderson will have to follow the white rabbit again. ', 1 - ), - ( + ), ( 'https://fr.web.img3.acsta.net/medias/nmedia/18/65/64/35/19116953.jpg', 'Harry Potter', 153, '2009', - 'Voldemort demonic grip tightens on the Muggle universe and the world of witchcraft. Hogwarts has ceased to be a haven of peace, danger lurks in the heart of the castle... But Dumbledore is more determined than ever to prepare Harry for his final battle, now imminent.', + 'Voldemort demonic grip tightens on the Muggle universe and the world of witchcraft. Hogwarts has ceased to be a haven of peace, danger lurks in the heart of the castle... But Dumbledore is more determined than ever to prepare Harry for his final battle, now imminent.', 0 - ), - ( + ), ( 'https://fr.web.img2.acsta.net/pictures/17/09/12/10/29/1142495.jpg', 'Blade Runner 2049', 164, '2017', - 'In 2049, society is weakened by the numerous tensions between humans and their slaves created by bioengineering. Officer K is a Blade Runner: part of an elite task force tasked with finding and eliminating those who do not obey human orders.', + 'In 2049, society is weakened by the numerous tensions between humans and their slaves created by bioengineering. Officer K is a Blade Runner: part of an elite task force tasked with finding and eliminating those who do not obey human orders.', 1 - ), - ( + ), ( 'https://fr.web.img4.acsta.net/r_1280_720/img/6b/c7/6bc7a13ca6446a603f160b4ab4414141.jpg', 'Gladiator', 155, '2000', - 'The Roman general Maximus is the most faithful support of the Emperor Marcus Aurelius, whom he led from victory to victory with exemplary bravery and dedication. Jealous of Maximus prestige, and even more so of the emperor love for him, Marcus Aurelius son, Commodus, brutally assumed power, then ordered the general arrest and execution. Maximus escapes his assassins but cannot prevent the massacre of his family. Captured by a slave trader, he becomes a gladiator and plots his revenge', + 'The Roman general Maximus is the most faithful support of the Emperor Marcus Aurelius, whom he led from victory to victory with exemplary bravery and dedication. Jealous of Maximus prestige, and even more so of the emperor love for him, Marcus Aurelius son, Commodus, brutally assumed power, then ordered the general arrest and execution. Maximus escapes his assassins but cannot prevent the massacre of his family. Captured by a slave trader, he becomes a gladiator and plots his revenge', 1 - ), - ( + ), ( 'https://fr.web.img6.acsta.net/medias/nmedia/18/82/69/17/19806656.jpg', 'Intouchables', 92, '2011', - 'Following a paragliding accident, Philippe, a rich aristocrat, hires Driss, a young man from the suburbs who has just been released from prison, as a home helper. In short the least appropriate person for the job. Together they will bring together Vivaldi and Earth Wind and Fire, the word and the joke, the costumes and the tracksuit bottoms... Two universes will collide, tame each other, to give birth to a friendship as crazy, funny and strong than unexpected, a unique relationship that will spark and make them... Untouchable.', + 'Following a paragliding accident, Philippe, a rich aristocrat, hires Driss, a young man from the suburbs who has just been released from prison, as a home helper. In short the least appropriate person for the job. Together they will bring together Vivaldi and Earth Wind and Fire, the word and the joke, the costumes and the tracksuit bottoms... Two universes will collide, tame each other, to give birth to a friendship as crazy, funny and strong than unexpected, a unique relationship that will spark and make them... Untouchable.', 1 - ), - ( + ), ( 'https://fr.web.img2.acsta.net/medias/nmedia/18/84/94/35/20078430.jpg', 'Rebelle', 95, '2012', - 'Since the dawn of time, in the heart of the wild and mysterious lands of the Scottish Highlands, stories of epic battles and mythical legends have been passed down from generation to generation.', + 'Since the dawn of time, in the heart of the wild and mysterious lands of the Scottish Highlands, stories of epic battles and mythical legends have been passed down from generation to generation.', 1 - ), - ( + ), ( 'https://fr.web.img4.acsta.net/medias/nmedia/18/35/57/73/18660716.jpg', 'Le parrain', 175, '1972', - 'In 1945, in New York, the Corleones are one of the five mafia families. Don Vito Corleone, "godfather" of this family, marries his daughter to a bookmaker. Sollozzo, "godfather" of the Tattaglia family, offers Don Vito an association in drug trafficking, but he refuses. Sonny, one of his sons, is in favor of it.', + 'In 1945, in New York, the Corleones are one of the five mafia families. Don Vito Corleone, "godfather" of this family, marries his daughter to a bookmaker. Sollozzo, "godfather" of the Tattaglia family, offers Don Vito an association in drug trafficking, but he refuses. Sonny, one of his sons, is in favor of it.', 1 - ), - ( + ), ( 'https://fr.web.img5.acsta.net/medias/nmedia/18/63/95/41/18927494.jpg', 'Indina Jones et le cadran de la destinée', 154, '2023', - '1969. After spending more than ten years teaching at Hunter College in New York, the esteemed Dr. Jones, professor of archeology, is about to retire and live out peaceful days.', + '1969. After spending more than ten years teaching at Hunter College in New York, the esteemed Dr. Jones, professor of archeology, is about to retire and live out peaceful days.', 1 - ), - ( + ), ( 'https://fr.web.img2.acsta.net/pictures/16/02/03/11/17/130929.jpg', 'Batman VS Superman', 153, '2016', - 'Fearing that Superman will abuse his omnipotence, the Dark Knight decides to confront him: does the world need more a superhero with limitless powers or a vigilante with formidable strength? of human origin? Meanwhile, a terrible threat looms on the horizon...', + 'Fearing that Superman will abuse his omnipotence, the Dark Knight decides to confront him: does the world need more a superhero with limitless powers or a vigilante with formidable strength? of human origin? Meanwhile, a terrible threat looms on the horizon...', 1 - ), - ( + ), ( 'https://fr.web.img5.acsta.net/pictures/22/04/08/10/30/1779137.jpg', 'Dr Strange', 126, '2022', - 'In this new Marvel Studios film, the Marvel Cinematic Universe unlocks and pushes the boundaries of the multiverse even further. Journey into the unknown with Doctor Strange, who with the help of old and new mystical allies, traverses the mind-blowing and dangerous realities of the multiverse to face a mysterious new adversary.', + 'In this new Marvel Studios film, the Marvel Cinematic Universe unlocks and pushes the boundaries of the multiverse even further. Journey into the unknown with Doctor Strange, who with the help of old and new mystical allies, traverses the mind-blowing and dangerous realities of the multiverse to face a mysterious new adversary.', 1 - ), - ( + ), ( 'https://fr.web.img3.acsta.net/pictures/22/10/04/09/10/4429153.jpg', 'Black Panter', 162, '2022', - 'Queen Ramonda, Shuri, MBaku, Okoye and the Dora Milaje fight to protect their nation from interference from other world powers after the death of King TChalla. As the people strive to move forward, our heroes will have to unite and count on the help of mercenary Nakia and Everett Ross to bring the kingdom of Wakanda into a new era. But a terrible threat arises from a kingdom hidden deep in the oceans: Talokan.', + 'Queen Ramonda, Shuri, MBaku, Okoye and the Dora Milaje fight to protect their nation from interference from other world powers after the death of King TChalla. As the people strive to move forward, our heroes will have to unite and count on the help of mercenary Nakia and Everett Ross to bring the kingdom of Wakanda into a new era. But a terrible threat arises from a kingdom hidden deep in the oceans: Talokan.', 1 - ), - ( + ), ( 'https://fr.web.img4.acsta.net/pictures/21/11/16/10/01/4860598.jpg', 'SpiderMan No Way Hole', 148, '2021', - 'For the first time in his cinematic history, Spider-Man, the friendly neighborhood hero, is unmasked and can no longer separate his normal life from his heavy superhero responsibilities. When he asks Doctor Strange for help, the stakes become even more dangerous, forcing him to discover what being Spider-Man truly means', + 'For the first time in his cinematic history, Spider-Man, the friendly neighborhood hero, is unmasked and can no longer separate his normal life from his heavy superhero responsibilities. When he asks Doctor Strange for help, the stakes become even more dangerous, forcing him to discover what being Spider-Man truly means', 1 - ), - ( + ), ( 'https://fr.web.img6.acsta.net/pictures/22/05/24/11/16/2411535.jpg', 'Thot Love and Thunder', 119, '2022', - 'While Thor is deep in introspection and seeking serenity, his retreat is interrupted by a galactic killer known as Gorr, who has made it his mission to exterminate all the gods.', + 'While Thor is deep in introspection and seeking serenity, his retreat is interrupted by a galactic killer known as Gorr, who has made it his mission to exterminate all the gods.', 1 - ), - ( + ), ( 'https://fr.web.img4.acsta.net/pictures/21/07/30/15/39/5399627.jpg', 'Shang-Shi', 132, '2021', - 'Shang-Chi will have to confront a past he thought he had left behind when he is caught in the web of the mysterious Ten Rings organization.', + 'Shang-Chi will have to confront a past he thought he had left behind when he is caught in the web of the mysterious Ten Rings organization.', 1 - ), - ( + ), ( 'https://fr.web.img6.acsta.net/pictures/23/07/17/15/06/1535719.jpg', 'Napoleon', 158, '2023', - 'Spectacular fresco, Napoleon focuses on the rise and fall of Emperor Napoleon Bonaparte. The film traces Bonaparte s relentless conquest of power through the prism of his passionate and tormented relationship with Joséphine, the great love of his life.', + 'Spectacular fresco, Napoleon focuses on the rise and fall of Emperor Napoleon Bonaparte. The film traces Bonaparte s relentless conquest of power through the prism of his passionate and tormented relationship with Joséphine, the great love of his life.', 1 - ), - ( + ), ( 'https://fr.web.img2.acsta.net/pictures/19/10/25/11/18/5224976.jpg', 'Titanic', 194, '1998', - 'Southampton, April 10, 1912. The largest and most modern liner in the world, renowned for its unsinkability, the "Titanic", sets sail for its first voyage. Four days later, it hits an iceberg. On board, a poor artist and a wealthy bourgeois woman fall in love.', + 'Southampton, April 10, 1912. The largest and most modern liner in the world, renowned for its unsinkability, the "Titanic", sets sail for its first voyage. Four days later, it hits an iceberg. On board, a poor artist and a wealthy bourgeois woman fall in love.', 1 - ), - ( + ), ( 'https://fr.web.img2.acsta.net/pictures/20/08/03/12/15/2118693.jpg', 'Tenet', 210, @@ -377,18 +389,12 @@ VALUES ( '0', 'ggfd455', '0' - ); + ); -INSERT INTO +INSERT INTO `En_tendance_film` (`userId`, `filmId`) - VALUES - (1, 1), - (1, 2); +VALUES (1, 1), (1, 2); - -INSERT INTO +INSERT INTO `Favori_film` (`userId`, `filmId`) - VALUES - (1, 1), - (1, 2); - +VALUES (1, 1), (1, 2); \ No newline at end of file From e166c85d4eb5db61585ee6365036c0dda46f10ce Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Fri, 15 Dec 2023 10:43:26 +0100 Subject: [PATCH 41/44] pending... --- frontend/src/App.jsx | 6 +- .../assets/icons/circle-arrow-left-solid.svg | 1 + frontend/src/pages/MoviePlayer.jsx | 55 ++++++++++++------- frontend/src/sass/_moviePlayer.scss | 30 +++++++++- frontend/src/sass/index.scss | 1 + 5 files changed, 69 insertions(+), 24 deletions(-) create mode 100644 frontend/src/assets/icons/circle-arrow-left-solid.svg diff --git a/frontend/src/App.jsx b/frontend/src/App.jsx index 2baf6ec..6b19efd 100644 --- a/frontend/src/App.jsx +++ b/frontend/src/App.jsx @@ -1,14 +1,16 @@ -import { Outlet } from "react-router-dom"; +import { Outlet, useLocation } from "react-router-dom"; import NavBar from "./components/NavBar"; import { MovieProvider } from "./contexts/MovieContext"; function App() { + const location = useLocation(); + return (
- + {!location.pathname.includes("/moviePlayer/") && }
); } diff --git a/frontend/src/assets/icons/circle-arrow-left-solid.svg b/frontend/src/assets/icons/circle-arrow-left-solid.svg new file mode 100644 index 0000000..4d0bee1 --- /dev/null +++ b/frontend/src/assets/icons/circle-arrow-left-solid.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/frontend/src/pages/MoviePlayer.jsx b/frontend/src/pages/MoviePlayer.jsx index 2b5df2d..ffc2a53 100644 --- a/frontend/src/pages/MoviePlayer.jsx +++ b/frontend/src/pages/MoviePlayer.jsx @@ -1,30 +1,43 @@ -/* eslint-disable jsx-a11y/media-has-caption */ -import { useParams } from "react-router-dom"; +/* eslint-disable react/self-closing-comp */ +import { useParams, NavLink } from "react-router-dom"; import { useMovies } from "../contexts/MovieContext"; function MoviePlayer() { const { movieId } = useParams(); const { movies } = useMovies(); return ( -
- {movies - .filter((movie) => { - return movie.id === parseInt(movieId, 10); - }) - .map((movie) => { - // console.info(movie.videoUrl); - return ( -
-
-
-
- ); - })} +
+
+ + back arrow + +
+
+ {movies + .filter((movie) => { + return movie.id === parseInt(movieId, 10); + }) + .map((movie) => { + const videoId = new URL(movie.videoUrl).searchParams.get("v"); + const embedUrl = `https://www.youtube.com/embed/${videoId}`; + return ( + + ); + })} +
); } diff --git a/frontend/src/sass/_moviePlayer.scss b/frontend/src/sass/_moviePlayer.scss index 0d0e6f0..0eb330f 100644 --- a/frontend/src/sass/_moviePlayer.scss +++ b/frontend/src/sass/_moviePlayer.scss @@ -1,2 +1,30 @@ -.movie-player-wrapper { +.movie-player { + width: 100%; + height: 100%; + flex-direction: column; + justify-content: center; + align-items: center; + display: flex; + flex: 1; + background-color: var(--background-color-2, hsla(0, 0%, 0%, 1)); + padding-top: calc(var(--spacing-constant) * 1); + + .back-to-previous-page { + display: flex; + width: 100%; + padding-left: calc(var(--spacing-constant) * 1); + } + + .movie-player-wrapper { + width: 100%; + height: 100%; + justify-content: center; + align-items: center; + display: flex; + flex: 1; + + iframe { + flex: 1; + } + } } diff --git a/frontend/src/sass/index.scss b/frontend/src/sass/index.scss index 6d6b0f5..acbb14e 100644 --- a/frontend/src/sass/index.scss +++ b/frontend/src/sass/index.scss @@ -5,3 +5,4 @@ @import "navbar"; @import "movieSlide"; @import "movie"; +@import "moviePlayer"; From 337cab902d38d1855ba606ba68a7b151377dfb31 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Fri, 15 Dec 2023 10:46:55 +0100 Subject: [PATCH 42/44] pending... --- backend/src/app.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/backend/src/app.js b/backend/src/app.js index 6574349..1b87a29 100644 --- a/backend/src/app.js +++ b/backend/src/app.js @@ -110,7 +110,7 @@ app.use("/api", router); // // Serve react resources -// app.use(express.static(reactBuildPath)); +app.use(express.static("./public")); // // Redirect unhandled requests to the react index file From 776bcc914dfd29b50dfc012007bca937d3b98359 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Fri, 15 Dec 2023 11:55:36 +0100 Subject: [PATCH 43/44] pending... --- frontend/src/pages/Search.jsx | 13 +++++++++---- frontend/src/sass/_home.scss | 1 + frontend/src/sass/_movieSlide.scss | 10 ++++++---- frontend/src/sass/_search.scss | 11 +++++++++++ frontend/src/sass/_settings.scss | 4 ++++ 5 files changed, 31 insertions(+), 8 deletions(-) diff --git a/frontend/src/pages/Search.jsx b/frontend/src/pages/Search.jsx index b2eb8a4..42b3746 100644 --- a/frontend/src/pages/Search.jsx +++ b/frontend/src/pages/Search.jsx @@ -1,3 +1,4 @@ +import { NavLink } from "react-router-dom"; import { useState } from "react"; import { useMovies } from "../contexts/MovieContext"; import MovieSlide from "../components/MovieSlide"; @@ -22,7 +23,7 @@ function Search() { onChange={handleSearchChange} />
-
+ {/*
-
+
*/}
{searchValue.length > 0 ? ( <> @@ -40,13 +41,17 @@ function Search() { movie.title.toLowerCase().includes(searchValue.toLowerCase()) ) .map((movie) => ( - + + + ))} ) : ( <> {movies.map((movie) => ( - + + + ))} )} diff --git a/frontend/src/sass/_home.scss b/frontend/src/sass/_home.scss index 569f46a..9464fba 100644 --- a/frontend/src/sass/_home.scss +++ b/frontend/src/sass/_home.scss @@ -131,6 +131,7 @@ display: flex; // overflow-x: scroll; flex-wrap: wrap; + justify-content: center; } } } diff --git a/frontend/src/sass/_movieSlide.scss b/frontend/src/sass/_movieSlide.scss index e19b6e5..d10f036 100644 --- a/frontend/src/sass/_movieSlide.scss +++ b/frontend/src/sass/_movieSlide.scss @@ -1,20 +1,22 @@ .movie-slide { - width: var(--movie-slide-width, 70px); - height: var(--movie-slide-height, 90px); + width: calc(var(--movie-slide-width) * 1); + height: calc(var(--movie-slide-width, 70px) * 1.3); border-radius: var(--border-radius-constant, 10px); + object-fit: cover; } .movie-slide-requiring-registration { + width: calc(var(--movie-slide-width) * 1); + height: calc(var(--movie-slide-width, 70px) * 1.3); justify-content: center; align-items: center; gap: calc(var(--spacing-constant) * 1); display: flex; - width: var(--movie-slide-width, 70px); - height: var(--movie-slide-height, 90px); position: relative; .movie-slide { border-radius: var(--border-radius-constant, 10px); + object-fit: cover; filter: blur(2px); } diff --git a/frontend/src/sass/_search.scss b/frontend/src/sass/_search.scss index 47abb52..62f7278 100644 --- a/frontend/src/sass/_search.scss +++ b/frontend/src/sass/_search.scss @@ -65,5 +65,16 @@ } } } + + .search-result-container { + align-self: stretch; + flex: 1; + justify-content: center; + align-items: center; + gap: calc(var(--spacing-constant) * 1); + display: flex; + flex-wrap: wrap; + padding: 0 calc(var(--spacing-constant) * 1.5); + } } } diff --git a/frontend/src/sass/_settings.scss b/frontend/src/sass/_settings.scss index 2359e83..f6e5986 100644 --- a/frontend/src/sass/_settings.scss +++ b/frontend/src/sass/_settings.scss @@ -18,6 +18,10 @@ // ^ spacing --spacing-constant: 8px; + + // ^ other sizes + + --movie-slide-width: 90px; } * { From b75bd32aacb63d55406a1edeb3a7f0d1c6bf6d70 Mon Sep 17 00:00:00 2001 From: Ange230700 Date: Fri, 15 Dec 2023 13:34:12 +0100 Subject: [PATCH 44/44] ... --- backend/database/schema.sql | 60 +++++++++++++++++++++++++++++++++++++ 1 file changed, 60 insertions(+) diff --git a/backend/database/schema.sql b/backend/database/schema.sql index e251ffd..4e0bcd4 100644 --- a/backend/database/schema.sql +++ b/backend/database/schema.sql @@ -111,6 +111,66 @@ VALUES "2022", "The film is directed by Matt Reeves, who wrote the screenplay with Peter Craig. It stars Robert Pattinson as Bruce Wayne / Batman, with Zoë Kravitz, Paul Dano, Jeffrey Wright, John Turturro, Peter Sarsgaard, Barry Keoghan, Jayme Lawson, Andy Serkis, and Colin Farrell rounding out the ensemble cast.", 1 + ), + ( + 'https://m.media-amazon.com/images/M/MV5BMzZhYTVlMTMtMGZhMC00ZWYxLTljZDQtN2Y3YmFmZTk5OWU2XkEyXkFqcGdeQXVyMTkxNjUyNQ@@._V1_FMjpg_UX1000_.jpg', + 'https://www.tvinsider.com/wp-content/uploads/2023/11/avatar-the-last-airbender-770x433.jpg', + 'Avatar: The Last Airbender', + 'https://www.youtube.com/watch?v=waJKJW_XU90&ab_channel=Netflix', + 103, + '2010', + 'Air, Water, Earth, Fire: the balance of the world is tipped by a savage war waged for a century already by the Fire Nation against the three other nations. Challenging his courage and combat skills, Aang discovers that he is the new Avatar, the only one capable of mastering all four elements. He joins forces with Katara, a Waterbender, and his older brother Sokka, to stop the Fire Nation before it is too late...', + 0 + ), + ( + 'https://fr.web.img4.acsta.net/pictures/21/11/17/17/24/3336846.jpg', + 'https://hustonsite.files.wordpress.com/2023/06/93361-matrixresurrections_bannerposter.jpg', + 'Matrix Resurrections', + 'https://www.youtube.com/watch?v=9ix7TUGVYIo', + 148, + '2020', + 'MATRIX RESURRECTIONS takes us back into two parallel realities – that of our daily lives and that of the world hidden there. To know with certainty whether his own reality is a physical or mental construct, and to truly know himself, Mr. Anderson will have to follow the white rabbit again. ', + 1 + ), + ( + 'https://static.posters.cz/image/1300/art-photo/harry-potter-and-the-half-blood-prince-i167377.jpg', + 'https://picfiles.alphacoders.com/621/62184.jpg', + 'Harry Potter and the Half-Blood Prince', + 'https://www.youtube.com/watch?v=tAiy66Xrsz4&ab_channel=HarryPotter', + 153, + '2009', + 'Voldemort demonic grip tightens on the Muggle universe and the world of witchcraft. Hogwarts has ceased to be a haven of peace, danger lurks in the heart of the castle... But Dumbledore is more determined than ever to prepare Harry for his final battle, now imminent.', + 0 + ), + ( + 'https://fr.web.img2.acsta.net/pictures/17/09/12/10/29/1142495.jpg', + 'https://pop.h-cdn.co/assets/17/39/1600x900/hd-aspect-1506522430-2049.jpg', + 'Blade Runner 2049', + 'https://www.youtube.com/watch?v=gCcx85zbxz4&ab_channel=WarnerBros.France', + 164, + '2017', + 'In 2049, society is weakened by the numerous tensions between humans and their slaves created by bioengineering. Officer K is a Blade Runner: part of an elite task force tasked with finding and eliminating those who do not obey human orders.', + 1 + ), + ( + 'https://fr.web.img4.acsta.net/r_1280_720/img/6b/c7/6bc7a13ca6446a603f160b4ab4414141.jpg', + 'https://c8.alamy.com/comp/K36B8T/gladiator-gladiator-date-2000-K36B8T.jpg', + 'Gladiator', + 'https://www.youtube.com/watch?v=owK1qxDselE&ab_channel=UniversalPicturesFrance', + 155, + '2000', + 'The Roman general Maximus is the most faithful support of the Emperor Marcus Aurelius, whom he led from victory to victory with exemplary bravery and dedication. Jealous of Maximus prestige, and even more so of the emperor love for him, Marcus Aurelius son, Commodus, brutally assumed power, then ordered the general arrest and execution. Maximus escapes his assassins but cannot prevent the massacre of his family. Captured by a slave trader, he becomes a gladiator and plots his revenge', + 0 + ), + ( + 'https://fr.web.img6.acsta.net/medias/nmedia/18/82/69/17/19806656.jpg', + 'https://assets.mubicdn.net/images/artworks/582651/images-original.png?1686650120', + 'Intouchables', + 'https://www.youtube.com/watch?v=34WIbmXkewU&ab_channel=Gaumont', + 92, + '2011', + 'Following a paragliding accident, Philippe, a rich aristocrat, hires Driss, a young man from the suburbs who has just been released from prison, as a home helper. In short the least appropriate person for the job. Together they will bring together Vivaldi and Earth Wind and Fire, the word and the joke, the costumes and the tracksuit bottoms... Two universes will collide, tame each other, to give birth to a friendship as crazy, funny and strong than unexpected, a unique relationship that will spark and make them... Untouchable.', + 1 ); INSERT INTO