summaryrefslogtreecommitdiffstats
path: root/src/utils/helpers/projects.ts
blob: 02e0e02531a049dc8fa24c989c31b11c26f4a163 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
import { ProjectCard } from '@ts/types/app';
import { MDXProjectMeta } from '@ts/types/mdx';
import { readdirSync } from 'fs';
import path from 'path';

/**
 * Retrieve all the projects filename.
 *
 * @returns {string[]} An array of filenames.
 */
export const getProjectFilenames = (): string[] => {
  const projectsDirectory = path.join(process.cwd(), 'src/content/projects');
  const filenames = readdirSync(projectsDirectory);

  return filenames.map((filename) => filename.replace(/\.mdx$/, ''));
};

/**
 * Retrieve project's data by filename.
 *
 * @param {string[]} filenames - The filenames without extension.
 * @returns {Promise<ProjectCard[]>} - The project data.
 */
export const getProjectsData = async (
  filenames: string[]
): Promise<ProjectCard[]> => {
  return Promise.all(
    filenames.map(async (filename) => {
      try {
        const {
          meta,
        }: {
          meta: MDXProjectMeta;
        } = await import(`../../content/projects/${filename}.mdx`);

        const { intro: _intro, title, ...projectMeta } = meta;

        const cover = await import(`../../../public/projects/${filename}.jpg`);

        return {
          id: filename,
          meta: {
            ...projectMeta,
            // Dynamic import source does not work so I use it only to get sizes
            cover: {
              ...cover.default,
              alt: `${title} image`,
              src: `/projects/${filename}.jpg`,
            },
          },
          slug: filename,
          title: title,
        };
      } catch (err) {
        console.error(err);
        throw err;
      }
    })
  );
};

/**
 * Method to sort an array of projects by publication date.
 *
 * @param {ProjectCard} a - A single project.
 * @param {ProjectCard} b - A single project.
 * @returns The result used by Array.sort() method: 1 || -1 || 0.
 */
const sortProjectsByPublicationDate = (a: ProjectCard, b: ProjectCard) => {
  if (a.meta.dates.publication < b.meta.dates.publication) return 1;
  if (a.meta.dates.publication > b.meta.dates.publication) return -1;
  return 0;
};

/**
 * Retrieve all projects in content folder sorted by publication date.
 *
 * @returns {Promise<ProjectCard[]>} An array of projects.
 */
export const getProjectsCard = async (): Promise<ProjectCard[]> => {
  const filenames = getProjectFilenames();
  const projects = await getProjectsData(filenames);

  return [...projects].sort(sortProjectsByPublicationDate);
};