├── .browserslistrc
├── .eslintrc.js
├── .gitignore
├── .yarnrc.yml
├── LICENSE
├── README.md
├── env.d.ts
├── index.html
├── package-lock.json
├── package.json
├── public
├── favicon.ico
├── fonts
│ ├── hack-bold.woff
│ ├── hack-bold.woff2
│ ├── hack-regular.woff
│ └── hack-regular.woff2
├── packages.crvx.fr.gpg
├── raphael@crvx.fr.gpg
├── robots.txt
└── social_icon.jpg
├── scripts
└── gh-pages-deploy.js
├── src
├── App.vue
├── assets
│ ├── avatar.webp
│ ├── error.gif
│ ├── fork-banner.png
│ └── main.css
├── components
│ └── ReturnLink.vue
├── config.ts
├── main.ts
├── router
│ └── index.ts
├── types.d.ts
└── views
│ ├── ArticlesView.vue
│ ├── ContactView.vue
│ ├── FilmmakingView.vue
│ ├── HomeView.vue
│ ├── LinksView.vue
│ ├── NotFound.vue
│ ├── SponsorsView.vue
│ └── WorkView.vue
├── tsconfig.app.json
├── tsconfig.json
├── tsconfig.node.json
├── tsconfig.node.tsbuildinfo
├── tsconfig.vitest.json
├── vercel.json
├── vite.config.ts
└── vitest.config.ts
/.browserslistrc:
--------------------------------------------------------------------------------
1 | > 1%
2 | last 2 versions
3 |
--------------------------------------------------------------------------------
/.eslintrc.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | root: true,
3 | env: {
4 | node: true
5 | },
6 | extends: [
7 | "plugin:vue/essential",
8 | "eslint:recommended",
9 | "@vue/typescript/recommended",
10 | "@vue/prettier",
11 | "@vue/prettier/@typescript-eslint"
12 | ],
13 | parserOptions: {
14 | ecmaVersion: 2020
15 | },
16 | rules: {
17 | "no-console": process.env.NODE_ENV === "production" ? "error" : "off",
18 | "no-debugger": process.env.NODE_ENV === "production" ? "error" : "off"
19 | }
20 | };
21 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | .DS_Store
2 | node_modules
3 | /dist
4 |
5 | # local env files
6 | .env.local
7 | .env.*.local
8 |
9 | # Log files
10 | npm-debug.log*
11 | yarn-debug.log*
12 | yarn-error.log*
13 |
14 | # Editor directories and files
15 | .idea
16 | .vscode
17 | *.suo
18 | *.ntvs*
19 | *.njsproj
20 | *.sln
21 | *.sw?
22 |
--------------------------------------------------------------------------------
/.yarnrc.yml:
--------------------------------------------------------------------------------
1 | nodeLinker: node-modules
2 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) Microsoft Corporation. All rights reserved.
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # website
2 |
3 | 2019 version of my personal website.
4 |
5 | ## Project Setup
6 |
7 | ```sh
8 | npm install
9 | ```
10 |
11 | ### Compile and Hot-Reload for Development
12 |
13 | ```sh
14 | npm run dev
15 | ```
16 |
17 | ### Type-Check, Compile and Minify for Production
18 |
19 | ```sh
20 | npm run build
21 | ```
22 |
23 | ### Run Unit Tests with [Vitest](https://vitest.dev/)
24 |
25 | ```sh
26 | npm run test:unit
27 | ```
28 |
29 | ### Lint with [ESLint](https://eslint.org/)
30 |
31 | ```sh
32 | npm run lint
33 | ```
34 |
--------------------------------------------------------------------------------
/env.d.ts:
--------------------------------------------------------------------------------
1 | ///
2 |
--------------------------------------------------------------------------------
/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
10 | Raphaël Cerveaux, Software Engineer
11 |
12 |
16 |
20 |
24 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "website",
3 | "version": "0.0.0",
4 | "private": true,
5 | "type": "module",
6 | "scripts": {
7 | "dev": "vite",
8 | "build": "run-p type-check \"build-only {@}\" --",
9 | "preview": "vite preview",
10 | "test:unit": "vitest",
11 | "build-only": "vite build",
12 | "type-check": "vue-tsc --build --force",
13 | "lint": "eslint . --ext .vue,.js,.jsx,.cjs,.mjs,.ts,.tsx,.cts,.mts --fix --ignore-path .gitignore",
14 | "format": "prettier --write src/",
15 | "deploy": "node ./scripts/gh-pages-deploy.js"
16 | },
17 | "dependencies": {
18 | "@vercel/analytics": "1.2.2",
19 | "vue": "3.3.11",
20 | "vue-router": "4.2.5"
21 | },
22 | "devDependencies": {
23 | "@rushstack/eslint-patch": "1.3.3",
24 | "@tsconfig/node18": "18.2.2",
25 | "@types/jsdom": "21.1.6",
26 | "@types/node": "18.19.3",
27 | "@vitejs/plugin-vue": "4.5.2",
28 | "@vue/eslint-config-prettier": "8.0.0",
29 | "@vue/eslint-config-typescript": "12.0.0",
30 | "@vue/test-utils": "2.4.3",
31 | "@vue/tsconfig": "0.5.0",
32 | "eslint": "8.49.0",
33 | "eslint-plugin-vue": "9.17.0",
34 | "execa": "8.0.1",
35 | "jsdom": "23.0.1",
36 | "npm-run-all2": "6.1.1",
37 | "prettier": "3.0.3",
38 | "typescript": "~5.3.0",
39 | "vite": "5.1.5",
40 | "vitest": "1.0.4",
41 | "vue-tsc": "1.8.25"
42 | }
43 | }
44 |
--------------------------------------------------------------------------------
/public/favicon.ico:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/public/favicon.ico
--------------------------------------------------------------------------------
/public/fonts/hack-bold.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/public/fonts/hack-bold.woff
--------------------------------------------------------------------------------
/public/fonts/hack-bold.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/public/fonts/hack-bold.woff2
--------------------------------------------------------------------------------
/public/fonts/hack-regular.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/public/fonts/hack-regular.woff
--------------------------------------------------------------------------------
/public/fonts/hack-regular.woff2:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/public/fonts/hack-regular.woff2
--------------------------------------------------------------------------------
/public/packages.crvx.fr.gpg:
--------------------------------------------------------------------------------
1 | -----BEGIN PGP PUBLIC KEY BLOCK-----
2 |
3 | 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
52 | =5Hq2
53 | -----END PGP PUBLIC KEY BLOCK-----
54 |
--------------------------------------------------------------------------------
/public/raphael@crvx.fr.gpg:
--------------------------------------------------------------------------------
1 | -----BEGIN PGP PUBLIC KEY BLOCK-----
2 | Version: OpenPGP.js v4.10.10
3 | Comment: https://openpgpjs.org
4 |
5 | xjMEYa85WBYJKwYBBAHaRw8BAQdAfA1LnmElb1FlYCnWkgORMbDE1pNz8kpy
6 | diP6yB24D8XNIXJhcGhhZWxAY3J2eC5mciA8cmFwaGFlbEBjcnZ4LmZyPsKP
7 | BBAWCgAgBQJhrzlYBgsJBwgDAgQVCAoCBBYCAQACGQECGwMCHgEAIQkQEAzi
8 | eZ2XhGIWIQTmh4WnswF0N2z0ZukQDOJ5nZeEYqJIAQDPSOpAxurnHThMRDg6
9 | hTiFb6ifGuJbRMBqjuVJJB7s6gEA4lrocS1eCLOcxwK8pKsT7n5Qm3Ze66q/
10 | zAQ9sQIUYwHOOARhrzlYEgorBgEEAZdVAQUBAQdAue52rJFfw7+QsGvN/T4G
11 | t/ckS4WfSmMXh+GpmCrfe2EDAQgHwngEGBYIAAkFAmGvOVgCGwwAIQkQEAzi
12 | eZ2XhGIWIQTmh4WnswF0N2z0ZukQDOJ5nZeEYpacAQC/R34PHFAugKnieqMe
13 | E/U0/HLfNmPOJTag2O3yNsckpQEArrDRJvQRjZhfCBSPeEsmWsDqB+8mpGWa
14 | QfXb7xjogwQ=
15 | =+UKQ
16 | -----END PGP PUBLIC KEY BLOCK-----
17 |
--------------------------------------------------------------------------------
/public/robots.txt:
--------------------------------------------------------------------------------
1 | User-agent: *
2 | Disallow: /publickey.asc
3 |
--------------------------------------------------------------------------------
/public/social_icon.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/public/social_icon.jpg
--------------------------------------------------------------------------------
/scripts/gh-pages-deploy.js:
--------------------------------------------------------------------------------
1 | /* eslint-disable no-console */
2 | import { execa } from 'execa'
3 | import fs from 'fs'
4 |
5 | const baseBranch = 'master';
6 | const targetBranch = 'gh-pages';
7 |
8 | (async () => {
9 | try {
10 | await execa("git", ["checkout", "--orphan", targetBranch]);
11 | // eslint-disable-next-line no-console
12 | console.log("Building started...");
13 | await execa("npm", ["run", "build"]);
14 | // Understand if it's dist or build folder
15 | const folderName = fs.existsSync("dist") ? "dist" : "build";
16 | await execa("git", ["--work-tree", folderName, "add", "--all"]);
17 | await execa("git", ["--work-tree", folderName, "commit", "-m", targetBranch]);
18 | console.log(`Pushing to ${targetBranch}...`);
19 | await execa("git", ["push", "origin", "HEAD:gh-pages", "--force"]);
20 | await execa("rm", ["-r", folderName]);
21 | await execa("git", ["checkout", "-f", baseBranch]);
22 | await execa("git", ["branch", "-D", targetBranch]);
23 | console.log("Successfully deployed, check your settings");
24 | } catch (e) {
25 | // eslint-disable-next-line no-console
26 | console.log(e.message);
27 | process.exit(1);
28 | }
29 | })();
30 |
--------------------------------------------------------------------------------
/src/App.vue:
--------------------------------------------------------------------------------
1 |
5 |
6 |
36 |
37 |
38 |
39 | light mode
40 | dark mode
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
76 |
--------------------------------------------------------------------------------
/src/assets/avatar.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/src/assets/avatar.webp
--------------------------------------------------------------------------------
/src/assets/error.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/src/assets/error.gif
--------------------------------------------------------------------------------
/src/assets/fork-banner.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sundowndev/website/0e32a464936a6ecd74075acb17049ed3c7fcacdb/src/assets/fork-banner.png
--------------------------------------------------------------------------------
/src/assets/main.css:
--------------------------------------------------------------------------------
1 | .fade-enter-active,
2 | .fade-leave-active {
3 | transition: opacity 0.5s ease;
4 | }
5 | .fade-enter,
6 | .fade-leave-active {
7 | opacity: 0;
8 | }
9 |
10 | /* Reset style */
11 | html,
12 | body,
13 | div,
14 | span,
15 | applet,
16 | object,
17 | iframe,
18 | h1,
19 | h2,
20 | h3,
21 | h4,
22 | h5,
23 | h6,
24 | p,
25 | blockquote,
26 | pre,
27 | a,
28 | abbr,
29 | acronym,
30 | address,
31 | big,
32 | cite,
33 | code,
34 | del,
35 | dfn,
36 | em,
37 | img,
38 | ins,
39 | kbd,
40 | q,
41 | s,
42 | samp,
43 | small,
44 | strike,
45 | strong,
46 | sub,
47 | sup,
48 | tt,
49 | var,
50 | b,
51 | u,
52 | i,
53 | center,
54 | dl,
55 | dt,
56 | dd,
57 | ol,
58 | ul,
59 | li,
60 | fieldset,
61 | form,
62 | label,
63 | legend,
64 | table,
65 | caption,
66 | tbody,
67 | tfoot,
68 | thead,
69 | tr,
70 | th,
71 | td,
72 | article,
73 | aside,
74 | canvas,
75 | details,
76 | embed,
77 | figure,
78 | figcaption,
79 | footer,
80 | header,
81 | hgroup,
82 | menu,
83 | nav,
84 | output,
85 | ruby,
86 | section,
87 | summary,
88 | time,
89 | mark,
90 | audio,
91 | video {
92 | margin: 0;
93 | padding: 0;
94 | border: 0;
95 | font-size: 100%;
96 | font: inherit;
97 | vertical-align: baseline;
98 | }
99 |
100 | /* HTML5 display-role reset for older browsers */
101 | article,
102 | aside,
103 | details,
104 | figcaption,
105 | figure,
106 | footer,
107 | header,
108 | hgroup,
109 | menu,
110 | nav,
111 | section {
112 | display: block;
113 | }
114 |
115 | body {
116 | line-height: 1;
117 | }
118 |
119 | ol,
120 | ul {
121 | list-style: none;
122 | }
123 |
124 | blockquote,
125 | q {
126 | quotes: none;
127 | }
128 |
129 | blockquote:before,
130 | blockquote:after {
131 | content: "";
132 | content: none;
133 | }
134 |
135 | q:before,
136 | q:after {
137 | content: "";
138 | content: none;
139 | }
140 |
141 | table {
142 | border-collapse: collapse;
143 | border-spacing: 0;
144 | }
145 |
146 | /* FONT PATHS */
147 | @font-face {
148 | font-family: "Hack";
149 | src:
150 | url("/fonts/hack-regular.woff2") format("woff2"),
151 | url("/fonts/hack-regular.woff") format("woff");
152 | font-weight: 400;
153 | font-style: normal;
154 | }
155 |
156 | @font-face {
157 | font-family: "Hack";
158 | src:
159 | url("/fonts/hack-bold.woff2") format("woff2"),
160 | url("/fonts/hack-bold.woff") format("woff");
161 | font-weight: 700;
162 | font-style: normal;
163 | }
164 |
165 | /* Actual style */
166 | #top-mode-btn {
167 | padding: 5px;
168 | font-size: 0.8em;
169 | cursor: pointer;
170 | display: inline-block;
171 | }
172 |
173 | body {
174 | font-family: Hack, monospace;
175 | background-color: #f5f5f5;
176 | color: #161616;
177 | }
178 |
179 | body.dark {
180 | background-color: #161616;
181 | color: #f5f5f5;
182 | }
183 |
184 | .margin-top {
185 | margin-top: 15px;
186 | }
187 |
188 | .margin-top-30 {
189 | margin-top: 30px;
190 | }
191 |
192 | .margin-bottom {
193 | margin-bottom: 15px;
194 | }
195 |
196 | .margin-bottom-30 {
197 | margin-bottom: 30px;
198 | }
199 |
200 | .text-center {
201 | text-align: center;
202 | }
203 |
204 | img {
205 | max-width: 100%;
206 | }
207 |
208 | .section img.avatar {
209 | border-radius: 130px;
210 | margin-bottom: 30px;
211 | filter: drop-shadow(0 0 0.75rem rgba(0, 0, 0, 0.1));
212 | }
213 |
214 | body.dark .section img.avatar {
215 | filter: drop-shadow(0 0 0.75rem rgba(219, 196, 30, 0.1)) sepia(35%);
216 | }
217 |
218 | .container {
219 | z-index: 3;
220 | position: relative;
221 | }
222 |
223 | .container.main-content {
224 | width: 900px;
225 | margin: auto;
226 | min-height: 95vh;
227 | display: -webkit-box;
228 | display: -webkit-flex;
229 | display: -ms-flexbox;
230 | display: flex;
231 | -webkit-box-orient: vertical;
232 | -webkit-box-direction: normal;
233 | -webkit-flex-direction: column;
234 | -ms-flex-direction: column;
235 | flex-direction: column;
236 | -webkit-box-pack: center;
237 | -webkit-justify-content: center;
238 | -ms-flex-pack: center;
239 | justify-content: center;
240 | }
241 |
242 | @media (max-width: 900px) {
243 | .container {
244 | margin: 0 30px;
245 | }
246 | .container.main-content {
247 | width: 92%;
248 | min-height: 0;
249 | margin-top: 50px;
250 | margin-bottom: 50px;
251 | }
252 | .container.main-content .section {
253 | width: 100%;
254 | }
255 | #bottom-note {
256 | width: 100px;
257 | }
258 | }
259 |
260 | section {
261 | margin: auto;
262 | width: 100%;
263 | padding: 80px 0 80px 0;
264 | }
265 |
266 | section.active {
267 | display: block;
268 | }
269 |
270 | section h1 {
271 | font-size: 24px;
272 | font-weight: bold;
273 | padding: 15px 0;
274 | margin-bottom: 20px;
275 | }
276 |
277 | section h2 {
278 | font-size: 16px;
279 | font-weight: bold;
280 | margin-bottom: 20px;
281 | background: #393939;
282 | color: #ffffff;
283 | padding: 5px;
284 | width: max-content;
285 | }
286 |
287 | body.dark section h2 {
288 | background: #eee;
289 | color: #161616;
290 | }
291 |
292 | section h3,
293 | section ul.list li {
294 | font-size: 14px;
295 | font-weight: bold;
296 | margin-bottom: 20px;
297 | display: block;
298 | }
299 |
300 | section p {
301 | font-weight: 300;
302 | line-height: 32px;
303 | margin-bottom: 30px;
304 | }
305 |
306 | section .icon {
307 | font-size: 32px;
308 | }
309 |
310 | a {
311 | text-decoration: none;
312 | color: #000;
313 | padding-bottom: 3px;
314 | border-bottom: 2px solid #1616163b;
315 | -webkit-transition: 0.25s;
316 | transition: 0.25s;
317 | }
318 |
319 | body.dark a {
320 | color: #dbc41e;
321 | border-bottom: 2px solid rgba(219, 196, 30, 0.35);
322 | }
323 |
324 | a:hover {
325 | border-bottom: 2px solid #161616d2;
326 | }
327 |
328 | body.dark a:hover {
329 | border-bottom: 2px solid rgba(219, 196, 30, 0.9);
330 | }
331 |
332 | strong {
333 | font-weight: bold;
334 | }
335 |
--------------------------------------------------------------------------------
/src/components/ReturnLink.vue:
--------------------------------------------------------------------------------
1 |
2 | Back
3 |
4 |
5 |
11 |
--------------------------------------------------------------------------------
/src/config.ts:
--------------------------------------------------------------------------------
1 | export default {
2 | repository: "https://github.com/sundowndev/website",
3 | links: {
4 | social: {
5 | linkedin: "https://www.linkedin.com/in/thispersondoesnotexist/",
6 | medium: "https://medium.com/@SundownDEV",
7 | github: "https://github.com/sundowndev",
8 | gitlab: "https://gitlab.com/sundowndev1",
9 | },
10 | },
11 | };
12 |
--------------------------------------------------------------------------------
/src/main.ts:
--------------------------------------------------------------------------------
1 | import "./assets/main.css";
2 |
3 | import { createApp } from "vue";
4 | import App from "./App.vue";
5 | import router from "./router";
6 | import { inject } from "@vercel/analytics";
7 |
8 | const app = createApp(App);
9 |
10 | app.use(router);
11 |
12 | app.mount("#app");
13 |
14 | // Inject Vercel Analytics
15 | inject();
16 |
--------------------------------------------------------------------------------
/src/router/index.ts:
--------------------------------------------------------------------------------
1 | import { createRouter, createWebHistory } from "vue-router";
2 | import HomeView from "../views/HomeView.vue";
3 | import Articles from "@/views/ArticlesView.vue";
4 | import Work from "@/views/WorkView.vue";
5 | import Links from "@/views/LinksView.vue";
6 | import NotFound from "@/views/NotFound.vue";
7 | import Contact from "@/views/ContactView.vue";
8 | import Sponsors from "@/views/SponsorsView.vue";
9 | import Filmmaking from "@/views/FilmmakingView.vue";
10 |
11 | const router = createRouter({
12 | history: createWebHistory(import.meta.env.BASE_URL),
13 | routes: [
14 | { path: "/", name: "home", component: HomeView },
15 | { path: "/writeups", name: "articles", component: Articles },
16 | { path: "/work", name: "work", component: Work },
17 | { path: "/filmmaking", name: "fpv", component: Filmmaking },
18 | { path: "/links", name: "links", component: Links },
19 | { path: "/sponsors", name: "sponsors", component: Sponsors },
20 | { path: "/contact", name: "contact", component: Contact },
21 | { path: "/:pathMatch(.*)*", component: NotFound },
22 |
23 | // Handle legacy paths
24 | { path: "/articles", redirect: "/writeups" },
25 | { path: "/resources", redirect: "/links" },
26 | { path: "/fpv", redirect: "/filmmaking" },
27 | ],
28 | });
29 |
30 | export default router;
31 |
--------------------------------------------------------------------------------
/src/types.d.ts:
--------------------------------------------------------------------------------
1 | export interface Link {
2 | title: string;
3 | url: string;
4 | }
5 |
--------------------------------------------------------------------------------
/src/views/ArticlesView.vue:
--------------------------------------------------------------------------------
1 |
32 |
33 |
34 |
35 |
36 | Write-ups
37 |
38 |
39 | You can follow my stories on
40 | Medium .
41 |
42 |
43 | Highlights
44 |
45 |
50 |
51 |
52 |
53 |
59 |
--------------------------------------------------------------------------------
/src/views/ContactView.vue:
--------------------------------------------------------------------------------
1 |
15 |
16 |
17 |
18 |
19 | Contact
20 |
21 | Social media
22 |
23 | I'm not really into social media but you can find me on
24 | LinkedIn .
25 |
26 |
27 | Email
28 |
29 | {{ email }} --
30 | 🔑 PGP PUBLIC KEY
31 |
32 |
33 |
34 |
--------------------------------------------------------------------------------
/src/views/FilmmakingView.vue:
--------------------------------------------------------------------------------
1 |
11 |
12 |
13 |
14 |
15 | Filmmaking and FPV drones
16 |
17 |
18 | In 2023 I put my engineering career on stand-by to learn to fly drones and
19 | editing videos. This new hobby allowed me to try something new and create
20 | content while travelling. FPV (First Person View) drones are hand-crafted
21 | drones designed mainly for racing. They're also commonly used in the
22 | industry of filmmaking to make creative aerial shots. During this year, I
23 | learned a lot about video editing, color grading, and sound design.
24 |
25 |
26 |
27 | I'm willing to pursue my software engineering career while continuing to
28 | learn about drone engineering and flying.
29 |
30 |
31 |
32 | My content is available on
33 | YouTube
36 | and
37 | Instagram .
40 |
41 |
42 |
43 | Have a job opportunity in filmmaking for me ?
44 | Get in touch !
45 |
46 |
47 | Showreel 2024
48 | Here's my 2024 showreel showing up my best drone shots of 2024! 🏝️
49 |
50 |
57 |
58 |
59 | MMA gym showreel (2024)
60 | Small presentation clip for Kreol FC, martial arts gym.
61 |
62 |
69 |
70 |
71 | Showreel 2023
72 |
73 |
74 | Here's my 2023 showreel showing up my best drone shots of the year in
75 | Reunion Island and Australia.
76 |
77 |
78 |
79 |
86 |
87 |
88 |
89 |
90 |
111 |
--------------------------------------------------------------------------------
/src/views/HomeView.vue:
--------------------------------------------------------------------------------
1 |
2 |
3 |
10 |
11 | Raphaël Cerveaux
12 |
13 | Hi, I'm a Software Engineer and Filmmaker from Reunion Island 🇷🇪 🇫🇷
14 |
15 |
16 |
17 | Write-ups
18 |
19 |
20 | Softwares
21 |
22 |
23 | Filmmaking
24 |
25 |
26 | Sponsoring
27 |
28 |
29 | Contact
30 |
31 |
32 |
33 |
34 |
35 |
49 |
--------------------------------------------------------------------------------
/src/views/LinksView.vue:
--------------------------------------------------------------------------------
1 |
73 |
74 |
75 |
76 |
77 | Links
78 |
79 | Here, you can find a personal collection of awesome links.
80 |
81 | Privacy & security
82 |
83 |
88 |
89 | Open Source Intelligence
90 |
91 |
96 |
97 | Others
98 |
99 |
104 |
105 |
106 |
107 |
113 |
--------------------------------------------------------------------------------
/src/views/NotFound.vue:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Take me home, please
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/src/views/SponsorsView.vue:
--------------------------------------------------------------------------------
1 |
44 |
45 |
46 |
47 |
48 | Sponsors
49 |
50 |
51 | I love contributing to Open Source software! It has always been a goal to
52 | monetize my Open Source activity, so if you would like to support my
53 | future work, consider joining me as a sponsor!
54 |
55 |
56 | GitHub Sponsors
57 |
58 | The most effective way to support me is to become a sponsor on GitHub.
59 | This way, I can spend more and more time on open source projects. Starting
60 | at 5$ monthly or one-time, choose the amount you like, cancel at any time.
61 |
62 |
63 |
64 | Become a sponsor now!
67 |
68 |
69 |
70 |
Current sponsors
71 |
80 |
81 |
82 |
83 |
84 |
99 |
--------------------------------------------------------------------------------
/src/views/WorkView.vue:
--------------------------------------------------------------------------------
1 |
14 |
15 |
16 |
17 |
18 | Software engineering
19 |
20 |
21 | I'm highly involved into open source software and willing to make a living
22 | out of it. My interests are into
23 | OSINT , penetration testing, DevSecOps, cloud-native concepts, Kubernetes and
28 | Golang. Despite my interest for technical topics, I love working on
29 | impactful and meaningful products. What matters to me is providing value
30 | to people and industries through high quality software design.
31 |
32 |
33 | Code
34 |
35 | Most of my code is hosted on
36 | GitHub , but I
37 | also have a
38 | GitLab account
39 | mostly used for mirroring projects.
40 |
41 |
42 |
43 | Package releases are usually signed with this common
44 | 🔑 PGP key . This is
45 | the only purpose of this key.
46 |
47 |
48 | Are you available for hire ?
49 |
50 | I'm not actively looking for a job. If you have an opportunity you think
51 | would suit my profile, feel free to
52 | reach out .
53 |
54 |
55 | If you're interested into donating or sponsoring me, refer to
56 | the sponsoring page .
57 |
58 |
59 |
60 |
--------------------------------------------------------------------------------
/tsconfig.app.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "@vue/tsconfig/tsconfig.dom.json",
3 | "include": ["env.d.ts", "src/**/*", "src/**/*.vue"],
4 | "exclude": ["src/**/__tests__/*"],
5 | "compilerOptions": {
6 | "composite": true,
7 | "noEmit": true,
8 | "baseUrl": ".",
9 | "paths": {
10 | "@/*": ["./src/*"]
11 | }
12 | }
13 | }
14 |
--------------------------------------------------------------------------------
/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "files": [],
3 | "references": [
4 | {
5 | "path": "./tsconfig.node.json"
6 | },
7 | {
8 | "path": "./tsconfig.app.json"
9 | },
10 | {
11 | "path": "./tsconfig.vitest.json"
12 | }
13 | ]
14 | }
15 |
--------------------------------------------------------------------------------
/tsconfig.node.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "@tsconfig/node18/tsconfig.json",
3 | "include": [
4 | "vite.config.*",
5 | "vitest.config.*",
6 | "cypress.config.*",
7 | "nightwatch.conf.*",
8 | "playwright.config.*"
9 | ],
10 | "compilerOptions": {
11 | "composite": true,
12 | "noEmit": true,
13 | "module": "ESNext",
14 | "moduleResolution": "Bundler",
15 | "types": ["node"]
16 | }
17 | }
18 |
--------------------------------------------------------------------------------
/tsconfig.node.tsbuildinfo:
--------------------------------------------------------------------------------
1 | {"program":{"fileNames":["./node_modules/typescript/lib/lib.es5.d.ts","./node_modules/typescript/lib/lib.es2015.d.ts","./node_modules/typescript/lib/lib.es2016.d.ts","./node_modules/typescript/lib/lib.es2017.d.ts","./node_modules/typescript/lib/lib.es2018.d.ts","./node_modules/typescript/lib/lib.es2019.d.ts","./node_modules/typescript/lib/lib.es2020.d.ts","./node_modules/typescript/lib/lib.es2021.d.ts","./node_modules/typescript/lib/lib.es2022.d.ts","./node_modules/typescript/lib/lib.es2023.d.ts","./node_modules/typescript/lib/lib.es2015.core.d.ts","./node_modules/typescript/lib/lib.es2015.collection.d.ts","./node_modules/typescript/lib/lib.es2015.generator.d.ts","./node_modules/typescript/lib/lib.es2015.iterable.d.ts","./node_modules/typescript/lib/lib.es2015.promise.d.ts","./node_modules/typescript/lib/lib.es2015.proxy.d.ts","./node_modules/typescript/lib/lib.es2015.reflect.d.ts","./node_modules/typescript/lib/lib.es2015.symbol.d.ts","./node_modules/typescript/lib/lib.es2015.symbol.wellknown.d.ts","./node_modules/typescript/lib/lib.es2016.array.include.d.ts","./node_modules/typescript/lib/lib.es2017.date.d.ts","./node_modules/typescript/lib/lib.es2017.object.d.ts","./node_modules/typescript/lib/lib.es2017.sharedmemory.d.ts","./node_modules/typescript/lib/lib.es2017.string.d.ts","./node_modules/typescript/lib/lib.es2017.intl.d.ts","./node_modules/typescript/lib/lib.es2017.typedarrays.d.ts","./node_modules/typescript/lib/lib.es2018.asyncgenerator.d.ts","./node_modules/typescript/lib/lib.es2018.asynciterable.d.ts","./node_modules/typescript/lib/lib.es2018.intl.d.ts","./node_modules/typescript/lib/lib.es2018.promise.d.ts","./node_modules/typescript/lib/lib.es2018.regexp.d.ts","./node_modules/typescript/lib/lib.es2019.array.d.ts","./node_modules/typescript/lib/lib.es2019.object.d.ts","./node_modules/typescript/lib/lib.es2019.string.d.ts","./node_modules/typescript/lib/lib.es2019.symbol.d.ts","./node_modules/typescript/lib/lib.es2019.intl.d.ts","./node_modules/typescript/lib/lib.es2020.bigint.d.ts","./node_modules/typescript/lib/lib.es2020.date.d.ts","./node_modules/typescript/lib/lib.es2020.promise.d.ts","./node_modules/typescript/lib/lib.es2020.sharedmemory.d.ts","./node_modules/typescript/lib/lib.es2020.string.d.ts","./node_modules/typescript/lib/lib.es2020.symbol.wellknown.d.ts","./node_modules/typescript/lib/lib.es2020.intl.d.ts","./node_modules/typescript/lib/lib.es2020.number.d.ts","./node_modules/typescript/lib/lib.es2021.promise.d.ts","./node_modules/typescript/lib/lib.es2021.string.d.ts","./node_modules/typescript/lib/lib.es2021.weakref.d.ts","./node_modules/typescript/lib/lib.es2021.intl.d.ts","./node_modules/typescript/lib/lib.es2022.array.d.ts","./node_modules/typescript/lib/lib.es2022.error.d.ts","./node_modules/typescript/lib/lib.es2022.intl.d.ts","./node_modules/typescript/lib/lib.es2022.object.d.ts","./node_modules/typescript/lib/lib.es2022.sharedmemory.d.ts","./node_modules/typescript/lib/lib.es2022.string.d.ts","./node_modules/typescript/lib/lib.es2022.regexp.d.ts","./node_modules/typescript/lib/lib.es2023.array.d.ts","./node_modules/typescript/lib/lib.es2023.collection.d.ts","./node_modules/typescript/lib/lib.esnext.intl.d.ts","./node_modules/typescript/lib/lib.decorators.d.ts","./node_modules/typescript/lib/lib.decorators.legacy.d.ts","./node_modules/@vue/reactivity/node_modules/@vue/shared/dist/shared.d.ts","./node_modules/@vue/reactivity/dist/reactivity.d.ts","./node_modules/@vue/runtime-core/node_modules/@vue/shared/dist/shared.d.ts","./node_modules/@vue/runtime-core/dist/runtime-core.d.ts","./node_modules/csstype/index.d.ts","./node_modules/@vue/runtime-dom/dist/runtime-dom.d.ts","./node_modules/vue/jsx-runtime/index.d.ts","./node_modules/@babel/parser/typings/babel-parser.d.ts","./node_modules/source-map-js/source-map.d.ts","./node_modules/vue/node_modules/@vue/shared/dist/shared.d.ts","./node_modules/vue/node_modules/@vue/compiler-core/dist/compiler-core.d.ts","./node_modules/vue/node_modules/@vue/compiler-dom/dist/compiler-dom.d.ts","./node_modules/vue/jsx.d.ts","./node_modules/vue/dist/vue.d.mts","./__VLS_types.d.ts","./node_modules/@types/node/assert.d.ts","./node_modules/@types/node/assert/strict.d.ts","./node_modules/undici-types/header.d.ts","./node_modules/undici-types/readable.d.ts","./node_modules/undici-types/file.d.ts","./node_modules/undici-types/fetch.d.ts","./node_modules/undici-types/formdata.d.ts","./node_modules/undici-types/connector.d.ts","./node_modules/undici-types/client.d.ts","./node_modules/undici-types/errors.d.ts","./node_modules/undici-types/dispatcher.d.ts","./node_modules/undici-types/global-dispatcher.d.ts","./node_modules/undici-types/global-origin.d.ts","./node_modules/undici-types/pool-stats.d.ts","./node_modules/undici-types/pool.d.ts","./node_modules/undici-types/handlers.d.ts","./node_modules/undici-types/balanced-pool.d.ts","./node_modules/undici-types/agent.d.ts","./node_modules/undici-types/mock-interceptor.d.ts","./node_modules/undici-types/mock-agent.d.ts","./node_modules/undici-types/mock-client.d.ts","./node_modules/undici-types/mock-pool.d.ts","./node_modules/undici-types/mock-errors.d.ts","./node_modules/undici-types/proxy-agent.d.ts","./node_modules/undici-types/api.d.ts","./node_modules/undici-types/cookies.d.ts","./node_modules/undici-types/patch.d.ts","./node_modules/undici-types/filereader.d.ts","./node_modules/undici-types/diagnostics-channel.d.ts","./node_modules/undici-types/websocket.d.ts","./node_modules/undici-types/content-type.d.ts","./node_modules/undici-types/cache.d.ts","./node_modules/undici-types/interceptors.d.ts","./node_modules/undici-types/index.d.ts","./node_modules/@types/node/globals.d.ts","./node_modules/@types/node/async_hooks.d.ts","./node_modules/@types/node/buffer.d.ts","./node_modules/@types/node/child_process.d.ts","./node_modules/@types/node/cluster.d.ts","./node_modules/@types/node/console.d.ts","./node_modules/@types/node/constants.d.ts","./node_modules/@types/node/crypto.d.ts","./node_modules/@types/node/dgram.d.ts","./node_modules/@types/node/diagnostics_channel.d.ts","./node_modules/@types/node/dns.d.ts","./node_modules/@types/node/dns/promises.d.ts","./node_modules/@types/node/domain.d.ts","./node_modules/@types/node/dom-events.d.ts","./node_modules/@types/node/events.d.ts","./node_modules/@types/node/fs.d.ts","./node_modules/@types/node/fs/promises.d.ts","./node_modules/@types/node/http.d.ts","./node_modules/@types/node/http2.d.ts","./node_modules/@types/node/https.d.ts","./node_modules/@types/node/inspector.d.ts","./node_modules/@types/node/module.d.ts","./node_modules/@types/node/net.d.ts","./node_modules/@types/node/os.d.ts","./node_modules/@types/node/path.d.ts","./node_modules/@types/node/perf_hooks.d.ts","./node_modules/@types/node/process.d.ts","./node_modules/@types/node/punycode.d.ts","./node_modules/@types/node/querystring.d.ts","./node_modules/@types/node/readline.d.ts","./node_modules/@types/node/readline/promises.d.ts","./node_modules/@types/node/repl.d.ts","./node_modules/@types/node/stream.d.ts","./node_modules/@types/node/stream/promises.d.ts","./node_modules/@types/node/stream/consumers.d.ts","./node_modules/@types/node/stream/web.d.ts","./node_modules/@types/node/string_decoder.d.ts","./node_modules/@types/node/test.d.ts","./node_modules/@types/node/timers.d.ts","./node_modules/@types/node/timers/promises.d.ts","./node_modules/@types/node/tls.d.ts","./node_modules/@types/node/trace_events.d.ts","./node_modules/@types/node/tty.d.ts","./node_modules/@types/node/url.d.ts","./node_modules/@types/node/util.d.ts","./node_modules/@types/node/v8.d.ts","./node_modules/@types/node/vm.d.ts","./node_modules/@types/node/wasi.d.ts","./node_modules/@types/node/worker_threads.d.ts","./node_modules/@types/node/zlib.d.ts","./node_modules/@types/node/globals.global.d.ts","./node_modules/@types/node/index.d.ts","./node_modules/rollup/dist/rollup.d.ts","./node_modules/rollup/dist/parseAst.d.ts","./node_modules/vite/types/hmrPayload.d.ts","./node_modules/vite/types/customEvent.d.ts","./node_modules/vite/types/hot.d.ts","./node_modules/vite/dist/node/types.d-AKzkD8vd.d.ts","./node_modules/esbuild/lib/main.d.ts","./node_modules/postcss/lib/previous-map.d.ts","./node_modules/postcss/lib/input.d.ts","./node_modules/postcss/lib/css-syntax-error.d.ts","./node_modules/postcss/lib/declaration.d.ts","./node_modules/postcss/lib/root.d.ts","./node_modules/postcss/lib/warning.d.ts","./node_modules/postcss/lib/lazy-result.d.ts","./node_modules/postcss/lib/no-work-result.d.ts","./node_modules/postcss/lib/processor.d.ts","./node_modules/postcss/lib/result.d.ts","./node_modules/postcss/lib/document.d.ts","./node_modules/postcss/lib/rule.d.ts","./node_modules/postcss/lib/node.d.ts","./node_modules/postcss/lib/comment.d.ts","./node_modules/postcss/lib/container.d.ts","./node_modules/postcss/lib/at-rule.d.ts","./node_modules/postcss/lib/list.d.ts","./node_modules/postcss/lib/postcss.d.ts","./node_modules/postcss/lib/postcss.d.mts","./node_modules/vite/dist/node/runtime.d.ts","./node_modules/vite/types/importGlob.d.ts","./node_modules/vite/types/metadata.d.ts","./node_modules/vite/dist/node/index.d.ts","./node_modules/@vue/compiler-sfc/node_modules/@vue/compiler-core/dist/compiler-core.d.ts","./node_modules/magic-string/dist/magic-string.es.d.mts","./node_modules/typescript/lib/typescript.d.ts","./node_modules/@vue/reactivity-transform/dist/reactivity-transform.d.ts","./node_modules/@vue/compiler-sfc/dist/compiler-sfc.d.ts","./node_modules/vue/compiler-sfc/index.d.mts","./node_modules/@vitejs/plugin-vue/dist/index.d.mts","./vite.config.ts","./node_modules/@vitest/utils/dist/types.d.ts","./node_modules/@vitest/utils/dist/helpers.d.ts","./node_modules/@sinclair/typebox/typebox.d.ts","./node_modules/@jest/schemas/build/index.d.ts","./node_modules/pretty-format/build/index.d.ts","./node_modules/@vitest/utils/dist/index.d.ts","./node_modules/@vitest/runner/dist/tasks-rsXe_qLO.d.ts","./node_modules/@vitest/utils/dist/types-widbdqe5.d.ts","./node_modules/@vitest/utils/dist/diff.d.ts","./node_modules/@vitest/runner/dist/types.d.ts","./node_modules/@vitest/utils/dist/error.d.ts","./node_modules/@vitest/runner/dist/index.d.ts","./node_modules/vite-node/dist/trace-mapping.d-aA9jxPtH.d.ts","./node_modules/vite-node/dist/index-IeUJleJC.d.ts","./node_modules/vite-node/dist/index.d.ts","./node_modules/@vitest/snapshot/dist/environment-1emuyggI.d.ts","./node_modules/@vitest/snapshot/dist/index-K5cwkiJB.d.ts","./node_modules/@vitest/snapshot/dist/index.d.ts","./node_modules/@vitest/expect/dist/chai.d.cts","./node_modules/@vitest/expect/dist/index.d.ts","./node_modules/@vitest/expect/index.d.ts","./node_modules/@vitest/runner/dist/utils.d.ts","./node_modules/tinybench/dist/index.d.ts","./node_modules/vite-node/dist/client.d.ts","./node_modules/@vitest/snapshot/dist/manager.d.ts","./node_modules/vite-node/dist/server.d.ts","./node_modules/vitest/dist/reporters-OH1c16Kq.d.ts","./node_modules/vitest/dist/config.d.ts","./node_modules/vitest/config.d.ts","./vitest.config.ts"],"fileInfos":[{"version":"0","affectsGlobalScope":true},"0","0","0","0","0","0","0","0","0",{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},"0","0","0",{"version":"0","affectsGlobalScope":true},"0","0","0","0","0","0","0","0",{"version":"0","affectsGlobalScope":true},"0",{"version":"0","affectsGlobalScope":true},"0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0",{"version":"0","affectsGlobalScope":true},"0",{"version":"0","affectsGlobalScope":true},"0","0",{"version":"0","affectsGlobalScope":true},"0","0","0","0","0","0","0",{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},"0","0","0","0","0","0",{"version":"0","affectsGlobalScope":true},"0","0","0",{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},"0","0","0","0","0","0","0","0","0","0",{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},"0","0","0","0",{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},"0","0","0",{"version":"0","affectsGlobalScope":true},"0",{"version":"0","affectsGlobalScope":true},"0",{"version":"0","affectsGlobalScope":true},"0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0","0",{"version":"0","affectsGlobalScope":true},{"version":"0","affectsGlobalScope":true},"0","0","0","0","0","0",{"version":"0","affectsGlobalScope":true},"0","0","0"],"root":[75,199,229],"options":{"composite":true,"esModuleInterop":true,"module":99,"skipLibCheck":true,"strict":true,"target":9},"fileIdsList":[[64,66,67,74],[202],[76],[111],[112,117,145],[113,124,125,132,142,153],[113,114,124,132],[115,154],[116,117,125,133],[117,142,150],[118,120,124,132],[119],[120,121],[124],[122,124],[111,124],[124,125,126,142,153],[124,125,126,139,142,145],[109,158],[120,124,127,132,142,153],[124,125,127,128,132,142,150,153],[127,129,142,150,153],[76,77,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160],[124,130],[131,153,158],[120,124,132,142],[133],[134],[111,135],[136,152,158],[137],[138],[124,139,140],[139,141,154,156],[112,124,142,143,144,145],[112,142,144],[142,143],[145],[146],[111,142],[124,148,149],[148,149],[117,132,142,150],[151],[132,152],[112,127,138,153],[117,154],[142,155],[131,156],[157],[112,117,124,126,135,142,153,156,158],[142,159],[191,197,226],[205,208],[219],[205,206,208,209,210],[205],[205,206,208],[205,206],[204,215],[204,215,216],[204,207],[200],[200,201,204],[204],[68,69,71,187,193,194,195],[61,68,69],[68,193],[61],[61,62,64,66],[62,64,65],[183],[181,183],[172,180,181,182,184],[170],[173,178,183,186],[169,186],[173,174,177,178,179,186],[173,174,175,177,178,186],[170,171,172,173,174,178,179,180,182,183,184,186],[186],[69,170,171,172,173,174,175,177,178,179,180,181,182,183,184,185],[69,186],[173,175,176,178,179,186],[177,186],[178,179,183,186],[171,181],[203],[162,190],[69],[86,90,153],[86,142,153],[81],[83,86,150,153],[132,150],[161],[81,161],[83,86,132,153],[78,79,82,85,112,124,142,153],[78,84],[82,86,112,145,153,161],[112,161],[102,112,161],[80,81,161],[86],[80,81,82,83,84,85,86,87,88,90,91,92,93,94,95,96,97,98,99,100,101,103,104,105,106,107,108],[86,93,94],[84,86,94,95],[85],[78,81,86],[86,90,94,95],[90],[84,86,89,153],[78,83,84,86,90,93],[112,142],[81,86,102,112,158,161],[212,213],[212],[191,212,213,226],[124,125,127,128,129,132,142,150,153,159,161,162,163,164,165,166,167,168,187,188,189,190],[164,165,166,167],[164,165,166],[164],[165],[162],[227],[125,158,191,205,211,214,217,218,220,221,222,223,224,225,226],[196],[66,72,73],[66],[71],[153,191,198,226],[153,199,228]],"referencedMap":[[75,1],[203,2],[76,3],[77,3],[111,4],[112,5],[113,6],[114,7],[115,8],[116,9],[117,10],[118,11],[119,12],[120,13],[121,13],[123,14],[122,15],[124,16],[125,17],[126,18],[110,19],[127,20],[128,21],[129,22],[161,23],[130,24],[131,25],[132,26],[133,27],[134,28],[135,29],[136,30],[137,31],[138,32],[139,33],[140,33],[141,34],[142,35],[144,36],[143,37],[145,38],[146,39],[147,40],[148,41],[149,42],[150,43],[151,44],[152,45],[153,46],[154,47],[155,48],[156,49],[157,50],[158,51],[159,52],[198,53],[219,54],[220,55],[211,56],[206,57],[209,58],[221,59],[216,60],[217,61],[224,61],[208,62],[210,62],[201,63],[205,64],[207,65],[196,66],[192,67],[195,68],[62,69],[64,70],[66,71],[184,72],[182,73],[183,74],[171,75],[172,73],[179,76],[170,77],[175,78],[176,79],[181,80],[187,81],[186,82],[169,83],[177,84],[178,85],[173,86],[180,72],[174,87],[204,88],[163,89],[69,90],[93,91],[100,92],[92,91],[107,93],[84,94],[83,95],[106,96],[101,97],[104,98],[86,99],[85,100],[81,101],[80,102],[103,103],[82,104],[87,105],[91,105],[109,106],[108,105],[95,107],[96,108],[98,109],[94,110],[97,111],[102,96],[89,112],[90,113],[99,114],[79,115],[105,116],[223,117],[213,118],[214,117],[225,119],[191,120],[188,121],[167,122],[165,123],[166,124],[190,125],[228,126],[227,127],[226,127],[197,128],[74,129],[67,130],[73,130],[71,67],[72,131],[199,132],[229,133]],"exportedModulesMap":[[75,1],[203,2],[76,3],[77,3],[111,4],[112,5],[113,6],[114,7],[115,8],[116,9],[117,10],[118,11],[119,12],[120,13],[121,13],[123,14],[122,15],[124,16],[125,17],[126,18],[110,19],[127,20],[128,21],[129,22],[161,23],[130,24],[131,25],[132,26],[133,27],[134,28],[135,29],[136,30],[137,31],[138,32],[139,33],[140,33],[141,34],[142,35],[144,36],[143,37],[145,38],[146,39],[147,40],[148,41],[149,42],[150,43],[151,44],[152,45],[153,46],[154,47],[155,48],[156,49],[157,50],[158,51],[159,52],[198,53],[219,54],[220,55],[211,56],[206,57],[209,58],[221,59],[216,60],[217,61],[224,61],[208,62],[210,62],[201,63],[205,64],[207,65],[196,66],[192,67],[195,68],[62,69],[64,70],[66,71],[184,72],[182,73],[183,74],[171,75],[172,73],[179,76],[170,77],[175,78],[176,79],[181,80],[187,81],[186,82],[169,83],[177,84],[178,85],[173,86],[180,72],[174,87],[204,88],[163,89],[69,90],[93,91],[100,92],[92,91],[107,93],[84,94],[83,95],[106,96],[101,97],[104,98],[86,99],[85,100],[81,101],[80,102],[103,103],[82,104],[87,105],[91,105],[109,106],[108,105],[95,107],[96,108],[98,109],[94,110],[97,111],[102,96],[89,112],[90,113],[99,114],[79,115],[105,116],[223,117],[213,118],[214,117],[225,119],[191,120],[188,121],[167,122],[165,123],[166,124],[190,125],[228,126],[227,127],[226,127],[197,128],[74,129],[67,130],[73,130],[71,67],[72,131],[199,132],[229,133]],"semanticDiagnosticsPerFile":[75,68,203,202,76,77,111,112,113,114,115,116,117,118,119,120,121,123,122,124,125,126,110,160,127,128,129,161,130,131,132,133,134,135,136,137,138,139,140,141,142,144,143,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,198,218,219,220,211,206,209,221,215,216,217,224,208,210,201,205,207,200,196,192,195,62,61,64,63,66,65,168,193,184,182,183,171,172,179,170,175,185,176,181,187,186,169,177,178,173,180,174,204,163,162,69,222,59,60,12,11,2,13,14,15,16,17,18,19,20,3,4,21,25,22,23,24,26,27,28,5,29,30,31,32,6,36,33,34,35,37,7,38,43,44,39,40,41,42,8,48,45,46,47,49,9,50,51,52,55,53,54,56,57,10,1,58,194,93,100,92,107,84,83,106,101,104,86,85,81,80,103,82,87,88,91,78,109,108,95,96,98,94,97,102,89,90,99,79,105,223,213,214,225,212,191,188,167,165,164,166,189,190,228,227,226,197,74,67,73,71,72,70,199,229],"affectedFilesPendingEmit":[199,229],"emitSignatures":[199,229]},"version":"5.3.3"}
--------------------------------------------------------------------------------
/tsconfig.vitest.json:
--------------------------------------------------------------------------------
1 | {
2 | "extends": "./tsconfig.app.json",
3 | "exclude": [],
4 | "compilerOptions": {
5 | "composite": true,
6 | "lib": [],
7 | "types": ["node", "jsdom"]
8 | }
9 | }
10 |
--------------------------------------------------------------------------------
/vercel.json:
--------------------------------------------------------------------------------
1 | {
2 | "rewrites": [{ "source": "/(.*)", "destination": "/" }]
3 | }
4 |
--------------------------------------------------------------------------------
/vite.config.ts:
--------------------------------------------------------------------------------
1 | import { fileURLToPath, URL } from 'node:url'
2 |
3 | import { defineConfig } from 'vite'
4 | import vue from '@vitejs/plugin-vue'
5 |
6 | // https://vitejs.dev/config/
7 | export default defineConfig({
8 | plugins: [
9 | vue(),
10 | ],
11 | resolve: {
12 | alias: {
13 | '@': fileURLToPath(new URL('./src', import.meta.url))
14 | }
15 | }
16 | })
17 |
--------------------------------------------------------------------------------
/vitest.config.ts:
--------------------------------------------------------------------------------
1 | import { fileURLToPath } from 'node:url'
2 | import { mergeConfig, defineConfig, configDefaults } from 'vitest/config'
3 | import viteConfig from './vite.config'
4 |
5 | export default mergeConfig(
6 | viteConfig,
7 | defineConfig({
8 | test: {
9 | environment: 'jsdom',
10 | exclude: [...configDefaults.exclude, 'e2e/*'],
11 | root: fileURLToPath(new URL('./', import.meta.url))
12 | }
13 | })
14 | )
15 |
--------------------------------------------------------------------------------