@anja.codes/create-vitakit 0.0.0-stage → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (43) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +47 -2
  3. package/deployments.mjs +178 -0
  4. package/index.mjs +99 -0
  5. package/package.json +40 -4
  6. package/scaffold.mjs +124 -0
  7. package/template/.gitignore.template +19 -0
  8. package/template/_forgejo/workflows/codeberg.yml +37 -0
  9. package/template/_forgejo/workflows/deploy.yml +31 -0
  10. package/template/_github/workflows/cloudflare.yml +33 -0
  11. package/template/_github/workflows/cv.yml +36 -0
  12. package/template/_github/workflows/deploy.yml +53 -0
  13. package/template/_github/workflows/workers.yml +39 -0
  14. package/template/app/app.vue +5 -0
  15. package/template/app/assets/css/main.css +129 -0
  16. package/template/app/layouts/default.vue +39 -0
  17. package/template/app/pages/[...slug].vue +30 -0
  18. package/template/app/pages/cv.vue +34 -0
  19. package/template/app/pages/index.vue +62 -0
  20. package/template/app/pages/publications.vue +27 -0
  21. package/template/content/education.yml +18 -0
  22. package/template/content/employment.yml +18 -0
  23. package/template/content/pages/cv.md +9 -0
  24. package/template/content/pages/index.md +11 -0
  25. package/template/content/pages/publications.md +8 -0
  26. package/template/content/pages/research.md +32 -0
  27. package/template/content/profile.yml +33 -0
  28. package/template/content/publications.bib +43 -0
  29. package/template/content/supervision.yml +12 -0
  30. package/template/content/talks.yml +17 -0
  31. package/template/content/teaching.yml +17 -0
  32. package/template/cv-tex/cv.tex +39 -0
  33. package/template/cv-tex/cv.yml +7 -0
  34. package/template/cv-tex/latexmkrc +5 -0
  35. package/template/cv-tex/preamble.tex +7 -0
  36. package/template/cv-tex/prose/research-statement.tex +17 -0
  37. package/template/gitlab-ci.yml.template +28 -0
  38. package/template/nuxt.config.ts +32 -0
  39. package/template/package.json.template +33 -0
  40. package/template/public/img/portrait.svg +6 -0
  41. package/template/public/img/tree.svg +10 -0
  42. package/template/tsconfig.json +9 -0
  43. package/template/wrangler.json.template +10 -0
@@ -0,0 +1,36 @@
1
+ # Builds the PDF CV and attaches it to the workflow run.
2
+ #
3
+ # The PDF is an artifact, not part of the website: it may contain entries
4
+ # marked `visibility: cv` (address, phone, referees). Download it from the run
5
+ # summary. Runs on demand, and on pushes that touch CV material.
6
+ name: CV
7
+
8
+ on:
9
+ workflow_dispatch:
10
+ push:
11
+ branches: [main]
12
+ paths: ['content/**', 'cv-tex/**']
13
+
14
+ jobs:
15
+ build:
16
+ runs-on: ubuntu-latest
17
+ steps:
18
+ - uses: actions/checkout@v7
19
+ - uses: pnpm/action-setup@v6
20
+ - uses: actions/setup-node@v7
21
+ with:
22
+ node-version: 22
23
+ cache: pnpm
24
+ - run: pnpm install --frozen-lockfile
25
+ # Generate the .tex files here: the LaTeX action runs in its own container,
26
+ # without Node. cv-tex/latexmkrc lets it find the generated document class.
27
+ - run: pnpm pdf --tex-only
28
+ - uses: xu-cheng/latex-action@v4
29
+ with:
30
+ working_directory: cv-tex
31
+ root_file: cv.tex
32
+ latexmk_use_lualatex: false
33
+ - uses: actions/upload-artifact@v5
34
+ with:
35
+ name: cv
36
+ path: cv-tex/*.pdf
@@ -0,0 +1,53 @@
1
+ # Builds the site and publishes it to GitHub Pages.
2
+ #
3
+ # Setup: Settings -> Pages -> Source: "GitHub Actions".
4
+ #
5
+ # NUXT_APP_BASE_URL must match where the site is served from. For a project
6
+ # site at https://<user>.github.io/<repo>/ keep the line below; for a user site
7
+ # or a custom domain, delete it. A wrong value breaks every asset URL.
8
+ name: Deploy
9
+
10
+ on:
11
+ push:
12
+ branches: [main]
13
+ workflow_dispatch:
14
+
15
+ permissions:
16
+ contents: read
17
+ pages: write
18
+ id-token: write
19
+
20
+ concurrency:
21
+ group: pages
22
+ cancel-in-progress: true
23
+
24
+ jobs:
25
+ build:
26
+ runs-on: ubuntu-latest
27
+ env:
28
+ NUXT_APP_BASE_URL: /${{ github.event.repository.name }}/
29
+ steps:
30
+ - uses: actions/checkout@v7
31
+ # No `version:` here: the pnpm version comes from `packageManager` in
32
+ # package.json. Setting both fails with ERR_PNPM_BAD_PM_VERSION.
33
+ - uses: pnpm/action-setup@v6
34
+ - uses: actions/setup-node@v7
35
+ with:
36
+ node-version: 22 # keep in sync with engines.node
37
+ cache: pnpm
38
+ - run: pnpm install --frozen-lockfile
39
+ # typecheck + generate + assertions on the generated HTML
40
+ - run: pnpm check
41
+ - uses: actions/upload-pages-artifact@v5
42
+ with:
43
+ path: .output/public
44
+
45
+ deploy:
46
+ needs: build
47
+ runs-on: ubuntu-latest
48
+ environment:
49
+ name: github-pages
50
+ url: ${{ steps.deployment.outputs.page_url }}
51
+ steps:
52
+ - id: deployment
53
+ uses: actions/deploy-pages@v5
@@ -0,0 +1,39 @@
1
+ # Builds the site and deploys static assets to Cloudflare Workers (not Pages).
2
+ # wrangler.json points exclusively to .output/public. No Worker script or SSR.
3
+ # Setup: enable your account's workers.dev subdomain and choose an available
4
+ # Worker name in wrangler.json, or configure a custom domain there.
5
+ # Secrets: CLOUDFLARE_API_TOKEN (Workers Scripts edit permission),
6
+ # CLOUDFLARE_ACCOUNT_ID. The source repository can stay private.
7
+ name: Deploy (Cloudflare Workers)
8
+
9
+ on:
10
+ push:
11
+ branches: [main]
12
+ workflow_dispatch:
13
+
14
+ permissions:
15
+ contents: read
16
+
17
+ concurrency:
18
+ group: cloudflare-workers
19
+ cancel-in-progress: true
20
+
21
+ jobs:
22
+ deploy:
23
+ if: ${{ github.ref == 'refs/heads/main' }}
24
+ runs-on: ubuntu-latest
25
+ steps:
26
+ - uses: actions/checkout@v7
27
+ - uses: pnpm/action-setup@v6
28
+ - uses: actions/setup-node@v7
29
+ with:
30
+ node-version: 22
31
+ cache: pnpm
32
+ - run: pnpm install --frozen-lockfile
33
+ - run: pnpm check
34
+ - uses: cloudflare/wrangler-action@v4
35
+ with:
36
+ apiToken: ${{ secrets.CLOUDFLARE_API_TOKEN }}
37
+ accountId: ${{ secrets.CLOUDFLARE_ACCOUNT_ID }}
38
+ wranglerVersion: '4'
39
+ command: deploy
@@ -0,0 +1,5 @@
1
+ <template>
2
+ <NuxtLayout>
3
+ <NuxtPage />
4
+ </NuxtLayout>
5
+ </template>
@@ -0,0 +1,129 @@
1
+ @import "tailwindcss";
2
+
3
+ /* Design tokens: the first stop for restyling. Tailwind v4 reads these, so
4
+ `text-primary` and `font-serif` follow from here. */
5
+ @theme {
6
+ --font-sans: "Inter", ui-sans-serif, system-ui, sans-serif;
7
+ --font-serif: "Lora", ui-serif, Georgia, serif;
8
+ --color-primary: oklch(48% 0.13 250);
9
+ }
10
+
11
+ body {
12
+ @apply font-sans text-neutral-900 antialiased;
13
+ }
14
+
15
+ a {
16
+ @apply text-primary underline underline-offset-2 hover:no-underline;
17
+ }
18
+
19
+ /* --- vitakit components ------------------------------------------------ */
20
+
21
+ .vita-entry {
22
+ @apply grid gap-1 py-2 sm:grid-cols-[8rem_1fr] sm:gap-4;
23
+ }
24
+ .vita-entry__date {
25
+ @apply text-sm text-neutral-500 tabular-nums;
26
+ }
27
+ .vita-entry__title {
28
+ @apply font-medium;
29
+ }
30
+ .vita-entry__meta,
31
+ .vita-entry__note {
32
+ @apply text-sm text-neutral-600;
33
+ }
34
+ .vita-section {
35
+ @apply divide-y divide-neutral-100;
36
+ }
37
+ .vita-section-group {
38
+ @apply mt-10;
39
+ }
40
+ .vita-section-group__title {
41
+ @apply text-xl font-semibold;
42
+ }
43
+ .vita-section-group > .vita-section {
44
+ @apply mt-3;
45
+ }
46
+ .vita-section-group__subtitle {
47
+ @apply mt-6 text-sm font-semibold text-neutral-600;
48
+ }
49
+ .vita-links {
50
+ @apply flex flex-wrap gap-x-4 gap-y-1;
51
+ }
52
+ .vita-publications__group + .vita-publications__group {
53
+ @apply mt-8;
54
+ }
55
+ .vita-publications__heading {
56
+ @apply text-xl font-semibold;
57
+ }
58
+ .vita-bib {
59
+ @apply mt-3 list-decimal space-y-3 pl-6;
60
+ }
61
+ .vita-badge {
62
+ @apply ml-1 rounded bg-neutral-100 px-1.5 py-0.5 text-xs no-underline hover:bg-neutral-200;
63
+ }
64
+ .vita-issues {
65
+ @apply border-b border-red-300 bg-red-50 px-4 py-3 text-sm text-red-900;
66
+ }
67
+ .vita-issues__title {
68
+ @apply font-semibold;
69
+ }
70
+ .vita-issues pre {
71
+ @apply whitespace-pre-wrap font-sans;
72
+ }
73
+
74
+ /* --- Markdown output --------------------------------------------------- */
75
+
76
+ .vita-prose {
77
+ @apply leading-relaxed;
78
+ }
79
+ .vita-prose :where(p, ul, ol, blockquote, pre, table) {
80
+ @apply my-4;
81
+ }
82
+ .vita-prose :where(h2) {
83
+ @apply mt-8 mb-2 text-xl font-semibold;
84
+ }
85
+ .vita-prose :where(h3) {
86
+ @apply mt-6 mb-2 text-lg font-semibold;
87
+ }
88
+ .vita-prose :where(ul) {
89
+ @apply list-disc pl-6;
90
+ }
91
+ .vita-prose :where(ol) {
92
+ @apply list-decimal pl-6;
93
+ }
94
+ .vita-prose :where(code) {
95
+ @apply rounded bg-neutral-100 px-1 py-0.5 text-sm;
96
+ }
97
+ .vita-prose :where(pre) {
98
+ @apply overflow-x-auto rounded bg-neutral-100 p-4 text-sm;
99
+ }
100
+ .vita-prose :where(blockquote) {
101
+ @apply border-l-4 border-neutral-200 pl-4 text-neutral-600;
102
+ }
103
+ .vita-prose :where(figure) {
104
+ @apply my-4;
105
+ }
106
+ .vita-prose :where(figcaption) {
107
+ @apply mt-1 text-xs text-neutral-500;
108
+ }
109
+ /* A figure beside the text on wide screens, above it on narrow ones. */
110
+ .vita-prose :where(figure.figure-right) {
111
+ @apply sm:float-right sm:ml-6 sm:mt-0 sm:w-56;
112
+ }
113
+ .vita-prose :where(figure.figure-right) img {
114
+ @apply w-full rounded border border-neutral-200 bg-white p-2;
115
+ }
116
+ .vita-prose :where(table) {
117
+ @apply w-full border-collapse text-left text-sm;
118
+ }
119
+ .vita-prose :where(th, td) {
120
+ @apply border-b border-neutral-200 py-2 pr-4 align-top;
121
+ }
122
+ .vita-prose :where(th) {
123
+ @apply font-semibold;
124
+ }
125
+
126
+ /* Wide display formulas must not blow up the layout on narrow screens. */
127
+ .katex-display {
128
+ @apply overflow-x-auto overflow-y-hidden py-1;
129
+ }
@@ -0,0 +1,39 @@
1
+ <script setup lang="ts">
2
+ const profile = useProfile()
3
+ </script>
4
+
5
+ <template>
6
+ <div class="min-h-screen flex flex-col">
7
+ <!-- Shows content problems while developing; a build fails on them instead. -->
8
+ <VitaIssues />
9
+
10
+ <header class="border-b border-neutral-200">
11
+ <div class="mx-auto flex max-w-3xl flex-wrap items-baseline gap-x-6 gap-y-2 px-4 py-6">
12
+ <NuxtLink to="/" class="text-lg font-semibold no-underline">
13
+ {{ profile.name }}
14
+ </NuxtLink>
15
+ <nav class="ml-auto flex gap-4 text-sm">
16
+ <NuxtLink
17
+ v-for="item in profile.nav"
18
+ :key="item.url"
19
+ :to="item.url"
20
+ class="no-underline hover:underline"
21
+ >
22
+ {{ item.label }}
23
+ </NuxtLink>
24
+ </nav>
25
+ </div>
26
+ </header>
27
+
28
+ <main class="mx-auto w-full max-w-3xl flex-1 px-4 py-10">
29
+ <slot />
30
+ </main>
31
+
32
+ <footer class="border-t border-neutral-200">
33
+ <div class="mx-auto flex max-w-3xl flex-wrap items-baseline gap-2 px-4 py-6 text-sm text-neutral-600">
34
+ <p>&copy; {{ new Date().getFullYear() }} {{ profile.name }}</p>
35
+ <VitaMarkdown class="ml-auto text-xs text-neutral-400" :html="profile.footerHtml" />
36
+ </div>
37
+ </footer>
38
+ </div>
39
+ </template>
@@ -0,0 +1,30 @@
1
+ <script setup lang="ts">
2
+ /**
3
+ * Renders every Markdown page in `content/pages/`.
4
+ *
5
+ * Adding a page means adding a file. When a page needs more than prose, create
6
+ * `app/pages/<name>.vue`: a concrete route always wins over this catch-all.
7
+ */
8
+ const profile = useProfile()
9
+ const route = useRoute()
10
+ const page = usePage(route.path)
11
+
12
+ if (!page) {
13
+ throw createError({ statusCode: 404, statusMessage: `No page for ${route.path}`, fatal: true })
14
+ }
15
+
16
+ useHead({
17
+ title: page.route === '/' ? profile.name : `${page.title} – ${profile.name}`,
18
+ meta: [{ name: 'description', content: page.description ?? profile.summary }],
19
+ })
20
+ </script>
21
+
22
+ <template>
23
+ <article>
24
+ <h1 class="text-3xl font-semibold" v-html="page!.titleHtml" />
25
+ <p v-if="page!.description" class="mt-2 text-neutral-600">
26
+ {{ page!.description }}
27
+ </p>
28
+ <VitaMarkdown class="mt-6" :html="page!.bodyHtml" />
29
+ </article>
30
+ </template>
@@ -0,0 +1,34 @@
1
+ <script setup lang="ts">
2
+ /**
3
+ * The CV page: several sections composed in the order you want them.
4
+ *
5
+ * Section order, headings and which sections appear are decided here, not in
6
+ * the data — exactly as `cv-tex/cv.tex` decides them for the PDF. One line per
7
+ * section: move a line to move a section, delete it to leave the section out.
8
+ * A section without entries is not shown, heading included.
9
+ */
10
+ const profile = useProfile()
11
+ const page = usePage('/cv/')
12
+
13
+ if (!page) {
14
+ throw createError({ statusCode: 404, statusMessage: 'No page for /cv/ (expected content/pages/cv.md)', fatal: true })
15
+ }
16
+
17
+ useHead({
18
+ title: `${page.title} – ${profile.name}`,
19
+ meta: [{ name: 'description', content: page.description ?? profile.summary }],
20
+ })
21
+ </script>
22
+
23
+ <template>
24
+ <article>
25
+ <h1 class="text-3xl font-semibold" v-html="page.titleHtml" />
26
+ <VitaMarkdown class="mt-6" :html="page.bodyHtml" />
27
+
28
+ <VitaSection id="employment" title="Employment" />
29
+ <VitaSection id="education" title="Education" />
30
+ <VitaSection id="teaching" title="Teaching" />
31
+ <VitaSection id="supervision" title="Supervised theses" />
32
+ <VitaSection id="talks" title="Talks" />
33
+ </article>
34
+ </template>
@@ -0,0 +1,62 @@
1
+ <script setup lang="ts">
2
+ /**
3
+ * The landing page: who you are, then the prose from
4
+ * `content/pages/index.md`, then a few recent items.
5
+ *
6
+ * This file is yours — reorder it, delete parts, add your own markup.
7
+ */
8
+ const profile = useProfile()
9
+ const page = usePage('/')
10
+ const talks = useSection('talks')
11
+
12
+ useHead({
13
+ title: profile.name,
14
+ meta: [{ name: 'description', content: profile.summary }],
15
+ })
16
+ </script>
17
+
18
+ <template>
19
+ <div>
20
+ <header class="flex flex-wrap items-start gap-6 sm:flex-nowrap">
21
+ <img
22
+ v-if="profile.avatar"
23
+ :src="profile.avatar"
24
+ alt=""
25
+ width="128"
26
+ height="128"
27
+ class="size-32 shrink-0 rounded-full object-cover ring-1 ring-neutral-200"
28
+ >
29
+ <div>
30
+ <h1 class="text-3xl font-semibold">
31
+ {{ profile.name }}
32
+ </h1>
33
+ <p v-if="profile.title || profile.affiliation" class="text-neutral-600">
34
+ {{ profile.title }}
35
+ <template v-if="profile.title && profile.affiliation"> · </template>
36
+ <template v-if="profile.affiliation">
37
+ <a v-if="profile.affiliation.url" :href="profile.affiliation.url">{{ profile.affiliation.label }}</a>
38
+ <template v-else>{{ profile.affiliation.label }}</template>
39
+ </template>
40
+ </p>
41
+ <p v-if="profile.email" class="mt-1 text-sm">
42
+ <a :href="`mailto:${profile.email}`">{{ profile.email }}</a>
43
+ </p>
44
+ <VitaLinks :links="profile.links" class="mt-2 text-sm" />
45
+ </div>
46
+ </header>
47
+
48
+ <VitaMarkdown v-if="page" class="mt-8" :html="page.bodyHtml" />
49
+
50
+ <section v-if="talks.length" class="mt-10">
51
+ <h2 class="text-xl font-semibold">
52
+ Recent talks
53
+ </h2>
54
+ <VitaSection :entries="talks" :limit="3" class="mt-3" />
55
+ <p class="mt-3 text-sm">
56
+ <NuxtLink to="/cv/#talks">
57
+ All talks →
58
+ </NuxtLink>
59
+ </p>
60
+ </section>
61
+ </div>
62
+ </template>
@@ -0,0 +1,27 @@
1
+ <script setup lang="ts">
2
+ /**
3
+ * Prose from `content/pages/publications.md`, then the generated list.
4
+ *
5
+ * This page shadows the Markdown catch-all for `/publications/` — the general
6
+ * escape hatch when a page needs prose *and* components.
7
+ */
8
+ const profile = useProfile()
9
+ const page = usePage('/publications/')
10
+
11
+ if (!page) {
12
+ throw createError({ statusCode: 404, statusMessage: 'No page for /publications/ (expected content/pages/publications.md)', fatal: true })
13
+ }
14
+
15
+ useHead({
16
+ title: `${page.title} – ${profile.name}`,
17
+ meta: [{ name: 'description', content: page.description ?? profile.summary }],
18
+ })
19
+ </script>
20
+
21
+ <template>
22
+ <article>
23
+ <h1 class="text-3xl font-semibold" v-html="page.titleHtml" />
24
+ <VitaMarkdown class="mt-6" :html="page.bodyHtml" />
25
+ <VitaPublications class="mt-8" />
26
+ </article>
27
+ </template>
@@ -0,0 +1,18 @@
1
+ - date: { from: 2016, to: 2020 }
2
+ degree: PhD in Mathematics
3
+ institution: { name: University of Klagenfurt, url: https://www.aau.at }
4
+ thesis:
5
+ title: Cutting down random trees
6
+ type: Doctoral thesis
7
+ supervisor: { label: A. Supervisor, url: https://example.org/supervisor }
8
+
9
+ - date: { from: 2014, to: 2016 }
10
+ degree: MSc in Mathematics (with distinction)
11
+ institution: University of Klagenfurt
12
+ thesis:
13
+ title: Ascent sequences and their asymptotics
14
+ type: Master's thesis
15
+
16
+ - date: { from: 2011, to: 2014 }
17
+ degree: BSc in Technical Mathematics
18
+ institution: University of Klagenfurt
@@ -0,0 +1,18 @@
1
+ - date: { from: 2023, to: present }
2
+ position: Postdoctoral Researcher
3
+ institution: { name: University of Graz, url: https://www.uni-graz.at }
4
+ project:
5
+ title: Asymptotics of random discrete structures
6
+ funder: FWF
7
+ grant: P 12345
8
+ url: https://www.fwf.ac.at
9
+
10
+ - date: { from: 2020, to: 2023 }
11
+ position: University Assistant
12
+ institution: University of Klagenfurt
13
+
14
+ - date: { from: 2019, to: 2019 }
15
+ position: Visiting Researcher
16
+ institution: Uppsala University
17
+ note: Three-month research stay with the combinatorics group.
18
+ visibility: cv
@@ -0,0 +1,9 @@
1
+ ---
2
+ title: Curriculum Vitae
3
+ description: The same data that produces the PDF.
4
+ order: 30
5
+ ---
6
+
7
+ Build the PDF version with `pnpm pdf`. The sections below come from the
8
+ YAML files in `content/`; their order is decided in `app/pages/cv.vue`, and the
9
+ order in the PDF in `cv-tex/cv.tex`.
@@ -0,0 +1,11 @@
1
+ ---
2
+ title: __YAML_NAME__
3
+ order: 0
4
+ ---
5
+
6
+ Replace this page with a few sentences about yourself: it lives in
7
+ `content/pages/index.md`, and the heading above comes from its front matter.
8
+
9
+ Everything on this site comes from the files in `content/`, and the same data
10
+ produces `cv-tex/cv.pdf`. Add a page by adding a Markdown file; add a CV
11
+ section by adding a YAML file — `pnpm vitakit add section outreach` sets one up.
@@ -0,0 +1,8 @@
1
+ ---
2
+ title: Publications
3
+ description: Grouped by status, generated from a single BibTeX file.
4
+ order: 20
5
+ ---
6
+
7
+ Preprints are on [arXiv](https://arxiv.org/a/doe_j_1). The list below is
8
+ generated from `content/publications.bib` at build time.
@@ -0,0 +1,32 @@
1
+ ---
2
+ title: Research
3
+ description: Analytic combinatorics and random discrete structures.
4
+ order: 10
5
+ ---
6
+
7
+ <figure class="figure-right">
8
+ <img src="/img/tree.svg" alt="A simulated random tree" width="240" height="140">
9
+ <figcaption>A random tree on eight nodes.</figcaption>
10
+ </figure>
11
+
12
+ My work concerns the asymptotic behaviour of large random trees. A simple
13
+ family is described by the equation $T(z) = z\,\phi(T(z))$, whose singular
14
+ expansion determines almost everything about the limit shape:
15
+
16
+ $$
17
+ T(z) = \tau - \gamma \sqrt{1 - z/\rho} + O(1 - z/\rho).
18
+ $$
19
+
20
+ From this, the expected height of a random tree with $n$ nodes satisfies
21
+
22
+ $$
23
+ \mathbb{E}[H_n] \sim c \sqrt{n}, \qquad n \to \infty.
24
+ $$
25
+
26
+ ## Tools
27
+
28
+ | Technique | Used for |
29
+ | --- | --- |
30
+ | Singularity analysis | asymptotics of coefficients |
31
+ | Analytic combinatorics in several variables | multivariate limit laws |
32
+ | Simulation | checking conjectures before proving them |
@@ -0,0 +1,33 @@
1
+ # You, and the shape of your site. The only file that is not a CV section.
2
+ name: __YAML_NAME__
3
+ title: __YAML_TITLE__
4
+ affiliation:
5
+ name: __YAML_AFFILIATION__
6
+ email: __YAML_EMAIL__
7
+
8
+ # Where the site is published. Only the PDF needs it, to link files on the
9
+ # site such as /slides/talk.pdf; delete the # once you know the address.
10
+ # url: https://yourname.github.io/
11
+
12
+ # Portrait, from public/. Delete the line if you would rather not have one.
13
+ avatar: /img/portrait.svg
14
+
15
+ links:
16
+ - { label: ORCID, url: https://orcid.org/0000-0002-1825-0097 }
17
+ # - { label: GitHub, url: https://github.com/yourname }
18
+ # - { label: arXiv, url: https://arxiv.org/a/yourname }
19
+
20
+ # One or two sentences for search engines and link previews. What visitors
21
+ # read is content/pages/index.md, not this.
22
+ summary: __YAML_SUMMARY__
23
+
24
+ # Navigation, in the order it should appear. Adding a page does not change
25
+ # this list: the wording and the order are yours.
26
+ nav:
27
+ - { label: About, to: / }
28
+ - { label: Research, to: /research/ }
29
+ - { label: Publications, to: /publications/ }
30
+ - { label: CV, to: /cv/ }
31
+
32
+ # Inline Markdown, shown quietly at the bottom of every page.
33
+ footer: Built with [vitakit](https://github.com/anja-codes/vitakit).
@@ -0,0 +1,43 @@
1
+ % Your publication list. Export it from Zotero, JabRef or arXiv and replace the
2
+ % examples below.
3
+ %
4
+ % The non-standard `status` field decides the grouping on /publications/ and in
5
+ % the PDF: published, accepted, preprint, software or other; without it, an
6
+ % entry is published. To change the groups:
7
+ % pnpm vitakit customize publications # -> schemas/publications.ts
8
+ %
9
+ % `doi`, `arxiv`, `mrnumber` and `zbl` become links; `eprint` with
10
+ % `eprinttype = {arxiv}` (or `archivePrefix`) works as `arxiv` does, so exports
11
+ % from Zotero, JabRef or arXiv need no editing. Mathematics in titles works:
12
+ % write $...$ as usual.
13
+ %
14
+ % The website formats this list with a CSL style. To change it:
15
+ % pnpm vitakit eject publications.csl # -> content/publications.csl
16
+ % or save any CSL style under that name.
17
+
18
+ @article{example-published,
19
+ author = {Doe, Jane and Roe, Richard},
20
+ title = {The shape of large random $k$-ary trees},
21
+ journal = {Random Structures \& Algorithms},
22
+ volume = {64},
23
+ pages = {201--240},
24
+ year = {2024},
25
+ doi = {10.5555/12345678},
26
+ status = {published},
27
+ }
28
+
29
+ @misc{example-preprint,
30
+ author = {Doe, Jane},
31
+ title = {Sharp bounds for ascent sequences of height $h$},
32
+ year = {2025},
33
+ arxiv = {2501.01234},
34
+ status = {preprint},
35
+ }
36
+
37
+ @software{example-software,
38
+ author = {Doe, Jane},
39
+ title = {treetools: utilities for random tree simulation},
40
+ url = {https://github.com/yourname/treetools},
41
+ year = {2025},
42
+ status = {software},
43
+ }
@@ -0,0 +1,12 @@
1
+ - date: 2025
2
+ student: A. Student
3
+ ongoing: true # still in progress
4
+ title: Simulating random trees with $n$ nodes
5
+ degree: Master's thesis
6
+ institution: University of Graz
7
+
8
+ - date: 2024
9
+ student: B. Student
10
+ title: Ascent sequences in combinatorics
11
+ degree: Bachelor's thesis
12
+ institution: University of Graz
@@ -0,0 +1,17 @@
1
+ - date: 2025-06-16
2
+ title: The shape of large random $k$-ary trees
3
+ event: AofA 2025
4
+ location: Bath, UK
5
+ kind: invited
6
+
7
+ - date: 2024-09-03
8
+ title: Cutting down trees, one leaf at a time
9
+ event: Austrian Mathematical Society Meeting
10
+ location: Graz, Austria
11
+ kind: contributed
12
+
13
+ - date: 2024-03-12
14
+ title: What is a random tree?
15
+ event: Mathematics for schools
16
+ location: Klagenfurt, Austria
17
+ kind: outreach