parent
140b61e1d7
commit
7f8e5dd903
@ -0,0 +1,7 @@
|
||||
/*
|
||||
* Replace this with your own classes
|
||||
*
|
||||
* e.g.
|
||||
* .container {
|
||||
* }
|
||||
*/
|
||||
@ -0,0 +1,10 @@
|
||||
import { render } from '@testing-library/react';
|
||||
|
||||
import BlogPagination from './blog-pagination';
|
||||
|
||||
describe('BlogPagination', () => {
|
||||
it('should render successfully', () => {
|
||||
const { baseElement } = render(<BlogPagination />);
|
||||
expect(baseElement).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@ -0,0 +1,74 @@
|
||||
import styles from './blog-pagination.module.scss';
|
||||
import {useRouter} from "next/router";
|
||||
|
||||
/* eslint-disable-next-line */
|
||||
export interface BlogPaginationProps {
|
||||
paginator: any;
|
||||
}
|
||||
|
||||
export function BlogPagination({paginator}: BlogPaginationProps) {
|
||||
const router = useRouter();
|
||||
const {total, pageCount, page} = paginator.pagination;
|
||||
const isOnlyOne = pageCount > 0 && pageCount === 1;
|
||||
const isEmpty = total === 0;
|
||||
const isFirst = page === 1;
|
||||
const isLast = page === pageCount;
|
||||
const goPrevious = async () => {
|
||||
await router.push(`${window.location.origin}${window.location.pathname}?page=${page - 1}`);
|
||||
}
|
||||
|
||||
const goNext = async () => {
|
||||
await router.push(`${window.location.origin}${window.location.pathname}?page=${page + 1}`);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className={styles['container']}>
|
||||
<div className="flex flex-col items-center">
|
||||
{isOnlyOne && !isEmpty && (
|
||||
<span className="text-sm text-gray-700 dark:text-gray-400">{total} article(s)</span>)}
|
||||
{!isOnlyOne && !isEmpty && (<span className="text-sm text-gray-700 dark:text-gray-400">
|
||||
Articles <span className="font-semibold text-gray-900 dark:text-white">{page}</span> à <span
|
||||
className="font-semibold text-gray-900 dark:text-white">{pageCount}</span> sur un total de <span
|
||||
className="font-semibold text-gray-900 dark:text-white">{total}</span>
|
||||
</span>)}
|
||||
<div className="inline-flex mt-2 xs:mt-0">
|
||||
<button
|
||||
disabled={isOnlyOne || isFirst || isEmpty}
|
||||
onClick={goPrevious}
|
||||
className="
|
||||
inline-flex items-center px-4 py-2 mr-2 text-sm font-medium rounded
|
||||
text-white bg-gray-800
|
||||
hover:bg-gray-900
|
||||
disabled:bg-gray-500 disabled:hover:bg-gray-500
|
||||
dark:bg-gray-800 dark:border-gray-700 dark:text-gray-400 dark:hover:bg-gray-700 dark:hover:text-white">
|
||||
<svg aria-hidden="true" className="w-5 h-5 mr-2" fill="currentColor" viewBox="0 0 20 20"
|
||||
xmlns="http://www.w3.org/2000/svg">
|
||||
<path fillRule="evenodd"
|
||||
d="M7.707 14.707a1 1 0 01-1.414 0l-4-4a1 1 0 010-1.414l4-4a1 1 0 011.414 1.414L5.414 9H17a1 1 0 110 2H5.414l2.293 2.293a1 1 0 010 1.414z"
|
||||
clipRule="evenodd"></path>
|
||||
</svg>
|
||||
Prev
|
||||
</button>
|
||||
<button
|
||||
disabled={isOnlyOne || isLast || isEmpty}
|
||||
onClick={goNext}
|
||||
className="inline-flex items-center px-4 py-2 ml-2 text-sm font-medium rounded
|
||||
text-white bg-gray-800
|
||||
hover:bg-gray-900
|
||||
disabled:bg-gray-500 disabled:hover:bg-gray-500
|
||||
dark:bg-gray-800 dark:border-gray-700 dark:text-gray-400 dark:hover:bg-gray-700 dark:hover:text-white">
|
||||
Next
|
||||
<svg aria-hidden="true" className="w-5 h-5 ml-2" fill="currentColor" viewBox="0 0 20 20"
|
||||
xmlns="http://www.w3.org/2000/svg">
|
||||
<path fillRule="evenodd"
|
||||
d="M12.293 5.293a1 1 0 011.414 0l4 4a1 1 0 010 1.414l-4 4a1 1 0 01-1.414-1.414L14.586 11H3a1 1 0 110-2h11.586l-2.293-2.293a1 1 0 010-1.414z"
|
||||
clipRule="evenodd"></path>
|
||||
</svg>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default BlogPagination;
|
||||
@ -0,0 +1,7 @@
|
||||
/*
|
||||
* Replace this with your own classes
|
||||
*
|
||||
* e.g.
|
||||
* .container {
|
||||
* }
|
||||
*/
|
||||
@ -0,0 +1,10 @@
|
||||
import { render } from '@testing-library/react';
|
||||
|
||||
import BlogSearch from './blog-search';
|
||||
|
||||
describe('BlogSearch', () => {
|
||||
it('should render successfully', () => {
|
||||
const { baseElement } = render(<BlogSearch />);
|
||||
expect(baseElement).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@ -0,0 +1,34 @@
|
||||
import styles from './blog-search.module.scss';
|
||||
|
||||
/* eslint-disable-next-line */
|
||||
export interface BlogSearchProps {
|
||||
}
|
||||
|
||||
export function BlogSearch(props: BlogSearchProps) {
|
||||
return (
|
||||
<div className={styles['container'] + " bg-white rounded-lg mx-2 lg:mx-0 mt-5 lg:mt-0 p-5 mb-5 shadow-sm"}>
|
||||
<form>
|
||||
<label htmlFor="default-search"
|
||||
className="mb-2 text-sm font-medium text-gray-900 sr-only dark:text-white">Search</label>
|
||||
<div className="relative">
|
||||
<div className="absolute inset-y-0 left-0 flex items-center pl-3 pointer-events-none">
|
||||
<svg aria-hidden="true" className="w-5 h-5 text-gray-500 dark:text-gray-400" fill="none"
|
||||
stroke="currentColor" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg">
|
||||
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth="2"
|
||||
d="M21 21l-6-6m2-5a7 7 0 11-14 0 7 7 0 0114 0z"></path>
|
||||
</svg>
|
||||
</div>
|
||||
<input type="search" id="default-search"
|
||||
className="block w-full p-4 pl-10 text-sm text-gray-900 border border-gray-300 rounded-lg bg-gray-50 focus:ring-blue-500 focus:border-blue-500 dark:bg-gray-700 dark:border-gray-600 dark:placeholder-gray-400 dark:text-white dark:focus:ring-blue-500 dark:focus:border-blue-500"
|
||||
placeholder="Rechercher un article ..." required />
|
||||
<button type="submit"
|
||||
className="text-white absolute right-2.5 bottom-2.5 bg-blue-700 hover:bg-blue-800 focus:ring-4 focus:outline-none focus:ring-blue-300 font-medium rounded-lg text-sm px-4 py-2 dark:bg-blue-600 dark:hover:bg-blue-700 dark:focus:ring-blue-800">Search
|
||||
</button>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default BlogSearch;
|
||||
@ -0,0 +1,7 @@
|
||||
/*
|
||||
* Replace this with your own classes
|
||||
*
|
||||
* e.g.
|
||||
* .container {
|
||||
* }
|
||||
*/
|
||||
@ -0,0 +1,10 @@
|
||||
import { render } from '@testing-library/react';
|
||||
|
||||
import CardBlogDetails from './card-blog-details';
|
||||
|
||||
describe('CardBlogDetails', () => {
|
||||
it('should render successfully', () => {
|
||||
const { baseElement } = render(<CardBlogDetails />);
|
||||
expect(baseElement).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@ -0,0 +1,111 @@
|
||||
import delve from 'dlv';
|
||||
import NextImage from "next/image";
|
||||
import {
|
||||
FacebookIcon,
|
||||
FacebookMessengerIcon,
|
||||
FacebookMessengerShareButton,
|
||||
FacebookShareButton,
|
||||
LinkedinIcon,
|
||||
LinkedinShareButton,
|
||||
TwitterIcon,
|
||||
TwitterShareButton,
|
||||
WhatsappIcon,
|
||||
WhatsappShareButton
|
||||
} from "react-share";
|
||||
|
||||
import {environment} from "../../environments/environment";
|
||||
|
||||
import styles from './card-blog-details.module.scss';
|
||||
|
||||
/* eslint-disable-next-line */
|
||||
export interface CardBlogDetailsProps {
|
||||
item: any;
|
||||
}
|
||||
|
||||
export function CardBlogDetails({item}: CardBlogDetailsProps) {
|
||||
const {alternativeText, width, height} = item.image.data.attributes;
|
||||
const {slug} = item.category.data.attributes;
|
||||
const {title} = item;
|
||||
const shareUrl = `${environment.appUrl}/blog/${slug}/${item.slug}`;
|
||||
console.log(shareUrl);
|
||||
return (
|
||||
<div className={styles['container'] + " bg-white rounded-l p-8 overflow-hidden shadow-sm"}>
|
||||
<header className="md:flex flex-col">
|
||||
<h2 className="text-3xl mb-5 text-bold">
|
||||
{delve(item, 'title', 'N/A')}
|
||||
</h2>
|
||||
<section className="flex items-center justify-between">
|
||||
<div className="flex">
|
||||
<a href="#" className="flex items-center">
|
||||
<img
|
||||
src="https://images.unsplash.com/photo-1492562080023-ab3db95bfbce?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=731&q=80"
|
||||
alt="avatar" className="mr-4 w-10 h-10 object-cover rounded-full hidden sm:block"/>
|
||||
<h3 className="text-gray-700 text-normal font-bold hover:underline text-slate-400">Par Alex John</h3>
|
||||
</a>
|
||||
</div>
|
||||
<div className="flex flex-col">
|
||||
<a href={'/blog/' + delve(item, 'category.data.attributes.slug', '')}
|
||||
className="px-2 py-1 text-sm bg-gray-600 text-gray-100 font-bold rounded hover:bg-gray-500">
|
||||
{delve(item, 'category.data.attributes.name', 'N/A')}
|
||||
</a>
|
||||
</div>
|
||||
</section>
|
||||
</header>
|
||||
<hr className="border-gray-100 my-5 sm:mx-auto dark:border-gray-700 container mx-auto"/>
|
||||
<main>
|
||||
<section>
|
||||
<div className="whitespace-pre-wrap text-lg font-bold text-slate-500"
|
||||
dangerouslySetInnerHTML={{__html: delve(item, 'description', 'N/A')}}/>
|
||||
<NextImage
|
||||
layout="responsive"
|
||||
width={width}
|
||||
height={height}
|
||||
objectFit="contain"
|
||||
className="rounded-lg my-5"
|
||||
src={environment.strapiUrl + delve(item, 'image.data.attributes.url', '')}
|
||||
alt={delve(item, 'title', 'N/A')}/>
|
||||
</section>
|
||||
<section className="whitespace-pre-wrap text-lg text-slate-400"
|
||||
dangerouslySetInnerHTML={{__html: delve(item, 'content', 'N/A')}}/>
|
||||
<hr className="border-gray-100 my-5 sm:mx-auto dark:border-gray-700 container mx-auto"/>
|
||||
<section className="flex justify-between">
|
||||
<div>
|
||||
<h4 className="font-bold text-lg text-gray-400 mb-2">Partager cet article</h4>
|
||||
<div className="grid grid-cols-5 gap-2">
|
||||
<FacebookShareButton url={shareUrl}>
|
||||
<FacebookIcon size={32} round/>
|
||||
</FacebookShareButton>
|
||||
<FacebookMessengerShareButton
|
||||
url={shareUrl}
|
||||
appId="521270401588372"
|
||||
className="Demo__some-network__share-button"
|
||||
>
|
||||
<FacebookMessengerIcon size={32} round/>
|
||||
</FacebookMessengerShareButton>
|
||||
<TwitterShareButton
|
||||
url={shareUrl}
|
||||
title={title}
|
||||
className="Demo__some-network__share-button"
|
||||
>
|
||||
<TwitterIcon size={32} round/>
|
||||
</TwitterShareButton>
|
||||
<WhatsappShareButton
|
||||
url={shareUrl}
|
||||
title={title}
|
||||
separator=":: "
|
||||
className="Demo__some-network__share-button"
|
||||
>
|
||||
<WhatsappIcon size={32} round/>
|
||||
</WhatsappShareButton>
|
||||
<LinkedinShareButton url={shareUrl} className="Demo__some-network__share-button">
|
||||
<LinkedinIcon size={32} round/>
|
||||
</LinkedinShareButton>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</main>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default CardBlogDetails;
|
||||
@ -0,0 +1,7 @@
|
||||
/*
|
||||
* Replace this with your own classes
|
||||
*
|
||||
* e.g.
|
||||
* .container {
|
||||
* }
|
||||
*/
|
||||
@ -0,0 +1,10 @@
|
||||
import { render } from '@testing-library/react';
|
||||
|
||||
import CardBlog from './card-blog';
|
||||
|
||||
describe('CardBlog', () => {
|
||||
it('should render successfully', () => {
|
||||
const { baseElement } = render(<CardBlog />);
|
||||
expect(baseElement).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@ -0,0 +1,57 @@
|
||||
import delve from 'dlv';
|
||||
import { format } from 'date-fns';
|
||||
import {environment} from '../../environments/environment';
|
||||
|
||||
import styles from './card-blog.module.scss';
|
||||
|
||||
/* eslint-disable-next-line */
|
||||
export interface CardBlogProps {
|
||||
item: object;
|
||||
}
|
||||
|
||||
export function CardBlog({item}: CardBlogProps) {
|
||||
return (
|
||||
<div className={styles['container'] + " bg-white rounded-l overflow-hidden shadow-sm"}>
|
||||
<div className="md:flex">
|
||||
<div className="md:shrink-0">
|
||||
<img className="h-48 w-full object-cover md:h-full md:w-48"
|
||||
src={environment.strapiUrl + delve(item, 'attributes.image.data.attributes.formats.medium.url', '')}
|
||||
alt="Modern building architecture"/>
|
||||
</div>
|
||||
<div className="p-8 w-full">
|
||||
<div className="flex justify-between items-center">
|
||||
<span
|
||||
className="font-light text-gray-600 text-sm">{format(new Date(delve(item, 'attributes.publishedAt', 'Jun 1, 2020')),'dd/MM/yyyy')}</span>
|
||||
<a href={'/blog/' + delve(item, 'attributes.category.data.attributes.slug', '')}
|
||||
className="px-2 py-1 text-sm bg-gray-600 text-gray-100 font-bold rounded hover:bg-gray-500">
|
||||
{delve(item, 'attributes.category.data.attributes.name', 'N/A')}
|
||||
</a>
|
||||
</div>
|
||||
<div className="mt-2">
|
||||
<a
|
||||
href={'/blog/' + delve(item, 'attributes.category.data.attributes.slug', '') + '/' + delve(item, 'attributes.slug', '')}
|
||||
className="text-xl text-gray-700 font-bold hover:underline">
|
||||
{delve(item, 'attributes.title', 'N/A')}
|
||||
</a>
|
||||
<p className="mt-2 font-light text-sm text-gray-600">{delve(item, 'attributes.description', 'N/A')}</p>
|
||||
</div>
|
||||
<div className="flex justify-between items-center mt-4">
|
||||
<a href="#" className="text-blue-500 text-sm hover:underline">Lire l'article</a>
|
||||
<div>
|
||||
<a href="#" className="flex items-center">
|
||||
<img
|
||||
src="https://images.unsplash.com/photo-1492562080023-ab3db95bfbce?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=731&q=80"
|
||||
alt="avatar" className="mx-4 w-10 h-10 object-cover rounded-full hidden sm:block"/>
|
||||
<h3 className="text-gray-700 text-normal font-bold hover:underline">Alex John</h3>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default CardBlog;
|
||||
@ -0,0 +1,7 @@
|
||||
/*
|
||||
* Replace this with your own classes
|
||||
*
|
||||
* e.g.
|
||||
* .container {
|
||||
* }
|
||||
*/
|
||||
@ -0,0 +1,10 @@
|
||||
import { render } from '@testing-library/react';
|
||||
|
||||
import Categories from './categories';
|
||||
|
||||
describe('Categories', () => {
|
||||
it('should render successfully', () => {
|
||||
const { baseElement } = render(<Categories />);
|
||||
expect(baseElement).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@ -0,0 +1,43 @@
|
||||
import delve from 'dlv';
|
||||
|
||||
import {environment} from "../../environments/environment";
|
||||
|
||||
import styles from './categories.module.scss';
|
||||
import Link from "next/link";
|
||||
|
||||
/* eslint-disable-next-line */
|
||||
export interface CategoriesProps {
|
||||
items: object[];
|
||||
}
|
||||
|
||||
// <!-- pb-0 sm:pt-4 -->
|
||||
|
||||
export function Categories({items = []}: CategoriesProps) {
|
||||
return (
|
||||
<div
|
||||
className={styles['container'] + " bg-white rounded-lg mx-2 lg:mx-0 mt-5 lg:mt-0 p-5 mb-5 shadow-sm"}>
|
||||
<div className="flex items-center justify-between mb-4">
|
||||
<h5 className="text-xl font-bold leading-none text-gray-900 dark:text-white">Catégories</h5>
|
||||
</div>
|
||||
<div className="flow-root">
|
||||
<ul role="list" className="divide-y divide-gray-200 dark:divide-gray-700">
|
||||
{items.map((item: any, index: number) => (<li key={'categories-' + item.slug + index} className="py-3 sm:py-4">
|
||||
<div className="flex items-center space-x-4">
|
||||
<div className="flex-shrink-0">
|
||||
<img className="w-8 h-8 rounded-full"
|
||||
src={environment.strapiUrl + delve(item, 'attributes.image.data.attributes.formats.thumbnail.url', '')}
|
||||
alt="Neil image"/>
|
||||
</div>
|
||||
<div className="flex-1 min-w-0">
|
||||
<h4><Link href={"/blog/" + item.attributes.slug}>{delve(item, 'attributes.name', 'N/A')}</Link></h4>
|
||||
</div>
|
||||
</div>
|
||||
</li>))
|
||||
}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default Categories;
|
||||
@ -0,0 +1,7 @@
|
||||
/*
|
||||
* Replace this with your own classes
|
||||
*
|
||||
* e.g.
|
||||
* .container {
|
||||
* }
|
||||
*/
|
||||
@ -0,0 +1,10 @@
|
||||
import { render } from '@testing-library/react';
|
||||
|
||||
import LastArticles from './last-articles';
|
||||
|
||||
describe('LastArticles', () => {
|
||||
it('should render successfully', () => {
|
||||
const { baseElement } = render(<LastArticles />);
|
||||
expect(baseElement).toBeTruthy();
|
||||
});
|
||||
});
|
||||
@ -0,0 +1,44 @@
|
||||
import delve from 'dlv';
|
||||
|
||||
import styles from './last-articles.module.scss';
|
||||
import {environment} from "../../environments/environment";
|
||||
import {format} from "date-fns";
|
||||
|
||||
/* eslint-disable-next-line */
|
||||
export interface LastArticlesProps {
|
||||
items: object[];
|
||||
}
|
||||
|
||||
export function LastArticles({items = []}: LastArticlesProps) {
|
||||
return (
|
||||
<div
|
||||
className={styles['container'] + " bg-white rounded-lg mx-2 lg:mx-0 mt-5 lg:mt-0 p-5 mb-5 shadow-sm"}>
|
||||
<div className="flex items-center justify-between mb-4">
|
||||
<h5 className="text-xl font-bold leading-none text-gray-900 dark:text-white">Derniers articles publiés</h5>
|
||||
</div>
|
||||
<div className="flow-root">
|
||||
<ul role="list" className="divide-y divide-gray-200 dark:divide-gray-700">
|
||||
{items.map((item: object, index: number) => (<li key={'last-articles-' + index} className="py-3 sm:py-4">
|
||||
<div className="flex items-center space-x-4">
|
||||
<div className="flex-shrink-0">
|
||||
<img className="w-[85px] h-[75px] rounded-lg"
|
||||
src={environment.strapiUrl + delve(item, 'attributes.image.data.attributes.formats.medium.url', '')}
|
||||
alt="Neil image"/>
|
||||
</div>
|
||||
<div className="flex-1 min-w-0">
|
||||
<p className="text-xl font-medium text-gray-900 dark:text-white">
|
||||
{delve(item, 'attributes.title', 'N/A')}
|
||||
</p>
|
||||
<p className="text-sm text-gray-500 dark:text-gray-400">
|
||||
{delve(item, 'attributes.category.data.attributes.name', 'N/A')} - {format(new Date(delve(item, 'attributes.publishedAt', 'Jun 1, 2020')), 'dd/MM/yyyy')}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</li>))}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export default LastArticles;
|
||||
@ -1,5 +1,6 @@
|
||||
export const environment = {
|
||||
strapiUrl: 'http://127.0.0.1:1337/',
|
||||
appUrl: 'http://localhost:4200',
|
||||
strapiUrl: 'http://127.0.0.1:1337',
|
||||
strapiApiUrl: 'http://127.0.0.1:1337/api',
|
||||
nextAuthSecret: "yBNW1wrb9CgOvEfbX6EQCvCDqiMkRBZP"
|
||||
}
|
||||
|
||||
@ -1,5 +1,6 @@
|
||||
export const environment = {
|
||||
strapiUrl: 'https://admin.mecp.nasercloud.fr/',
|
||||
appUrl: 'http://localhost:4200',
|
||||
strapiUrl: 'https://admin.mecp.nasercloud.fr',
|
||||
strapiApiUrl: 'https://admin.mecp.nasercloud.fr/api',
|
||||
nextAuthSecret: "yBNW1wrb9CgOvEfbX6EQCvCDqiMkRBZP"
|
||||
}
|
||||
|
||||
@ -1,5 +1,6 @@
|
||||
export const environment = {
|
||||
strapiUrl: 'https://admin.mecp.nasercloud.fr/',
|
||||
appUrl: 'http://localhost:4200',
|
||||
strapiUrl: 'https://admin.mecp.nasercloud.fr',
|
||||
strapiApiUrl: 'https://admin.mecp.nasercloud.fr/api',
|
||||
nextAuthSecret: "yBNW1wrb9CgOvEfbX6EQCvCDqiMkRBZP"
|
||||
}
|
||||
|
||||
@ -1,5 +1,6 @@
|
||||
export const environment = {
|
||||
strapiUrl: 'http://127.0.0.1:1337/',
|
||||
appUrl: 'http://localhost:4200',
|
||||
strapiUrl: 'http://127.0.0.1:1337',
|
||||
strapiApiUrl: 'http://127.0.0.1:1337/api',
|
||||
nextAuthSecret: "yBNW1wrb9CgOvEfbX6EQCvCDqiMkRBZP"
|
||||
}
|
||||
|
||||
@ -0,0 +1,57 @@
|
||||
import axios from "axios";
|
||||
import delve from 'dlv';
|
||||
|
||||
import {environment} from "../../../environments/environment";
|
||||
import SeoConfig from "../../../components/seo-config/seo-config";
|
||||
import Layout from "../../../components/layout/layout";
|
||||
import styles from "../../index.module.scss";
|
||||
import BlogSearch from "../../../components/blog-search/blog-search";
|
||||
import Categories from "../../../components/categories/categories";
|
||||
import LastArticles from "../../../components/last-articles/last-articles";
|
||||
import CardBlogDetails from "../../../components/card-blog-details/card-blog-details";
|
||||
|
||||
export async function getServerSideProps(context) {
|
||||
console.log(context);
|
||||
const categories = await axios.get(`${environment.strapiApiUrl}/categories?populate=deep`);
|
||||
const lastPublished = await axios.get(`${environment.strapiApiUrl}/articles?populate=deep&_sort=date:DESC`);
|
||||
const post = await axios.get(`${environment.strapiApiUrl}/articles?populate=deep&filters[slug]=${context.params.post_slug}`);
|
||||
|
||||
if (!delve(post, "data.data.0.attributes", null)) {
|
||||
return {
|
||||
notFound: true
|
||||
}
|
||||
} else {
|
||||
return {
|
||||
props: {
|
||||
categories: delve(categories, 'data.data', []),
|
||||
lastPublished: delve(lastPublished, 'data.data', []),
|
||||
post: delve(post, "data.data.0.attributes", null),
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
export function PostBlog({menuHeader, menuFooter, seo, categories, post, lastPublished}) {
|
||||
return (
|
||||
<>
|
||||
<SeoConfig {...seo}/>
|
||||
<Layout menuHeader={menuHeader} menuFooter={menuFooter} headerTransparent={true}>
|
||||
<main className={styles['blog-container'] + " w-full lg:my-10"}>
|
||||
<section className="container max-w-screen-xl mx-auto relative flex flex-col lg:flex-row">
|
||||
<section className="grow lg:basis-4/6 mx-2 lg:mx-0 lg:pr-5">
|
||||
<CardBlogDetails item={post}/>
|
||||
</section>
|
||||
<aside className="grow lg:basis-2/6">
|
||||
<BlogSearch/>
|
||||
<Categories items={categories}/>
|
||||
<LastArticles items={lastPublished}/>
|
||||
</aside>
|
||||
</section>
|
||||
</main>
|
||||
</Layout>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
export default PostBlog;
|
||||
@ -0,0 +1,77 @@
|
||||
import axios from "axios";
|
||||
import delve from "dlv";
|
||||
|
||||
import {environment} from "../../../environments/environment";
|
||||
import SeoConfig from "../../../components/seo-config/seo-config";
|
||||
import Layout from "../../../components/layout/layout";
|
||||
import BlogSearch from "../../../components/blog-search/blog-search";
|
||||
import Categories from "../../../components/categories/categories";
|
||||
import LastArticles from "../../../components/last-articles/last-articles";
|
||||
|
||||
import styles from "../index.module.scss";
|
||||
import CardBlog from "../../../components/card-blog/card-blog";
|
||||
import BlogPagination from "../../../components/blog-pagination/blog-pagination";
|
||||
|
||||
export async function getServerSideProps(context) {
|
||||
const {query} = context;
|
||||
const categories = await axios.get(`${environment.strapiApiUrl}/categories?populate=deep`);
|
||||
const category = await axios.get(`${environment.strapiApiUrl}/categories?populate=deep&filters[slug]=${context.params.category_slug}`);
|
||||
const lastPublished = await axios.get(`${environment.strapiApiUrl}/articles?populate=deep&_sort=date:DESC`);
|
||||
let postsUrl = `${environment.strapiApiUrl}/articles?populate=deep&_sort=date:DESC&filters[category][slug][$contains]=${context.params.category_slug}`;
|
||||
if (query && query.page) {
|
||||
postsUrl += `$pagination[page]=${query.page}`;
|
||||
}
|
||||
const posts = await axios.get(postsUrl);
|
||||
|
||||
if (!delve(category, "data.data.0.attributes", null)) {
|
||||
return {
|
||||
notFound: true
|
||||
}
|
||||
} else {
|
||||
return {
|
||||
props: {
|
||||
categories: delve(categories, 'data.data', []),
|
||||
category: delve(category, "data.data.0.attributes", null),
|
||||
lastPublished: delve(lastPublished, 'data.data', []),
|
||||
posts: delve(posts, 'data.data', []),
|
||||
paginator: delve(posts, 'data.meta', []),
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
export function CategoryBlog({menuHeader, menuFooter, seo, categories, category, posts, lastPublished, paginator}) {
|
||||
return (
|
||||
<>
|
||||
<SeoConfig {...seo}/>
|
||||
<Layout menuHeader={menuHeader} menuFooter={menuFooter} headerTransparent={true}>
|
||||
<main className={styles['blog-container'] + " w-full lg:my-10"}>
|
||||
<section className="container max-w-screen-xl mx-auto relative flex">
|
||||
<section className="grow lg:basis-4/6 mx-2 lg:mx-0 lg:pr-5">
|
||||
<h3 className="text-2xl font-bold mb-5">{category.name}</h3>
|
||||
{posts.length === 0 && (
|
||||
<p>Aucun article n'a été posté dans cette catégorie pour l'instant</p>
|
||||
)
|
||||
}
|
||||
{posts.length > 0 && posts.map((post, index: number) => (
|
||||
<CardBlog key={'card-blog-' + post.id + index} item={post}/>))
|
||||
}
|
||||
|
||||
{posts.length > 0 && (<footer className="mt-10">
|
||||
<BlogPagination paginator={paginator}/>
|
||||
</footer>)}
|
||||
</section>
|
||||
<aside className="grow lg:basis-2/6">
|
||||
<BlogSearch/>
|
||||
<Categories items={categories}/>
|
||||
<LastArticles items={lastPublished}/>
|
||||
</aside>
|
||||
</section>
|
||||
</main>
|
||||
</Layout>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
export default CategoryBlog;
|
||||
@ -0,0 +1,9 @@
|
||||
/*
|
||||
* Replace this with your own classes
|
||||
*
|
||||
* e.g.
|
||||
* .container {
|
||||
* }
|
||||
*/
|
||||
.blog-container {
|
||||
}
|
||||
@ -0,0 +1,47 @@
|
||||
import axios from "axios";
|
||||
import delve from "dlv";
|
||||
|
||||
import SeoConfig from "../../components/seo-config/seo-config";
|
||||
import Layout from "../../components/layout/layout";
|
||||
import Categories from "../../components/categories/categories";
|
||||
|
||||
import styles from "./index.module.scss";
|
||||
import BlogSearch from "../../components/blog-search/blog-search";
|
||||
import {environment} from "../../environments/environment";
|
||||
import CardBlog from "../../components/card-blog/card-blog";
|
||||
|
||||
export async function getServerSideProps(context) {
|
||||
const categories = await axios.get(`${environment.strapiApiUrl}/categories?populate=deep`)
|
||||
const posts = await axios.get(`${environment.strapiApiUrl}/articles?populate=deep&_sort=date:DESC`)
|
||||
return {
|
||||
props: {
|
||||
categories: delve(categories, 'data.data', []),
|
||||
lastPublished: delve(posts, 'data.data', []),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export function Blog({menuHeader, menuFooter, seo, categories, lastPublished}) {
|
||||
return (
|
||||
<>
|
||||
<SeoConfig {...seo}/>
|
||||
<Layout menuHeader={menuHeader} menuFooter={menuFooter} headerTransparent={true}>
|
||||
<main className={styles['blog-container'] + " w-full lg:my-10"}>
|
||||
<section className="container mx-auto relative flex">
|
||||
<section className="grow lg:basis-4/6 mx-2 lg:mx-0 lg:pr-5">
|
||||
{lastPublished.map((post, index: number) => (
|
||||
<CardBlog key={'card-blog-' + post.id + index} item={post}/>))
|
||||
}
|
||||
</section>
|
||||
<aside className="grow lg:basis-2/6">
|
||||
<BlogSearch/>
|
||||
<Categories items={categories}/>
|
||||
</aside>
|
||||
</section>
|
||||
</main>
|
||||
</Layout>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
export default Blog;
|
||||
File diff suppressed because it is too large
Load Diff
Loading…
Reference in new issue