Repository: loqusion/typix
Branch: main
Commit: f3dd958107de
Files: 104
Total size: 120.5 KB
Directory structure:
gitextract_u9nhbyq8/
├── .editorconfig
├── .envrc
├── .github/
│ ├── FUNDING.yml
│ ├── ISSUE_TEMPLATE/
│ │ ├── 1-bug_report.md
│ │ ├── 2-feature_request.md
│ │ └── 3-typst_packages.md
│ └── workflows/
│ ├── pages.yml
│ ├── publish.yml
│ ├── test.yml
│ └── update-lockfile.yml
├── .gitignore
├── .markdownlint-cli2.jsonc
├── .markdownlint.json
├── .prettierignore
├── CHANGELOG.md
├── LICENSE
├── README.md
├── checks/
│ ├── .gitignore
│ ├── build-local.nix
│ ├── check-emojis.py
│ ├── clean/
│ │ ├── bad.c
│ │ ├── lib.typ
│ │ ├── metadata.toml
│ │ ├── sub/
│ │ │ ├── bad.py
│ │ │ ├── sub.typ
│ │ │ └── typst.toml
│ │ ├── typst.toml
│ │ └── works.bib
│ ├── clean-expected/
│ │ ├── lib.typ
│ │ ├── metadata.toml
│ │ ├── sub/
│ │ │ ├── sub.typ
│ │ │ └── typst.toml
│ │ ├── typst.toml
│ │ └── works.bib
│ ├── date/
│ │ └── main.typ
│ ├── default.nix
│ ├── emoji/
│ │ └── main.typ
│ ├── overlapping-virtual-paths/
│ │ └── main.typ
│ ├── simple/
│ │ └── main.typ
│ ├── simple-with-fonts/
│ │ └── main.typ
│ ├── simple-with-multiple-parameters/
│ │ └── main.typ
│ ├── simple-with-virtual-paths/
│ │ └── main.typ
│ ├── typst-packages/
│ │ └── main.typ
│ ├── virtual-paths.nix
│ └── watch.nix
├── docs/
│ ├── .gitignore
│ ├── SUMMARY.md
│ ├── api/
│ │ ├── derivations/
│ │ │ ├── build-typst-project-local.md
│ │ │ ├── build-typst-project.md
│ │ │ ├── common/
│ │ │ │ ├── emoji-font.md
│ │ │ │ ├── font-paths-example.md
│ │ │ │ ├── font-paths.md
│ │ │ │ ├── install-phase-command.md
│ │ │ │ ├── script-name.md
│ │ │ │ ├── src.md
│ │ │ │ ├── typst-compile-command.md
│ │ │ │ ├── typst-opts-example.md
│ │ │ │ ├── typst-opts.md
│ │ │ │ ├── typst-packages.md
│ │ │ │ ├── typst-project-output.md
│ │ │ │ ├── typst-project-source.md
│ │ │ │ ├── virtual-paths-example.md
│ │ │ │ └── virtual-paths.md
│ │ │ ├── dev-shell.md
│ │ │ ├── mk-typst-derivation.md
│ │ │ └── watch-typst-project.md
│ │ ├── derivations.md
│ │ ├── utilities/
│ │ │ └── clean-typst-source.md
│ │ └── utilities.md
│ ├── book.toml
│ ├── getting-started.md
│ └── recipes/
│ ├── adding-dependencies.md
│ ├── declaring-a-shell-environment.md
│ ├── specifying-sources.md
│ └── using-typst-packages.md
├── examples/
│ ├── .gitignore
│ ├── quick-start/
│ │ ├── .gitignore
│ │ ├── flake.nix
│ │ └── main.typ
│ ├── typst-packages/
│ │ ├── flake.nix
│ │ └── main.typ
│ └── typst-packages-unpublished/
│ ├── flake.nix
│ └── main.typ
├── flake.nix
├── lib/
│ ├── buildTypstProject.nix
│ ├── buildTypstProjectLocal.nix
│ ├── cleanTypstSource.nix
│ ├── coerceVirtualPathAttr.nix
│ ├── default.nix
│ ├── devShell.nix
│ ├── emojiFontPathFromString.nix
│ ├── fetchTypstPackages.nix
│ ├── inferTypstProjectOutput.nix
│ ├── linkVirtualPaths.nix
│ ├── mkTypstDerivation.nix
│ ├── setupHooks/
│ │ ├── copyVirtualPaths.nix
│ │ ├── copyVirtualPathsHook.sh
│ │ ├── unsetSourceDateEpoch.nix
│ │ ├── unsetSourceDateEpochHook.sh
│ │ └── unsetSourceDateEpochScript.sh
│ ├── typstOptsFromArgs.nix
│ └── watchTypstProject.nix
├── pkgs.nix
└── release.nix
================================================
FILE CONTENTS
================================================
================================================
FILE: .editorconfig
================================================
root = true
[*]
charset = utf-8
env_of_line = lf
indent_style = space
trim_trailing_whitespace = true
insert_final_newline = true
[*.nix]
indent_size = 2
================================================
FILE: .envrc
================================================
use flake . --impure
================================================
FILE: .github/FUNDING.yml
================================================
ko_fi: loqusion
================================================
FILE: .github/ISSUE_TEMPLATE/1-bug_report.md
================================================
---
name: Bug report
about: Create a report to help us improve
title: ''
labels: bug
assignees: ''
---
**Describe the bug**
A clear and concise description of what the bug is.
**To Reproduce**
Steps to reproduce the behavior:
1. Go to '...'
2. Click on '....'
3. Scroll down to '....'
4. See error
**Expected behavior**
A clear and concise description of what you expected to happen.
**Versions**
- OS:
**Additional context**
Add any other context about the problem here.
================================================
FILE: .github/ISSUE_TEMPLATE/2-feature_request.md
================================================
---
name: Feature request
about: Suggest an idea for this project
title: ''
labels: ''
assignees: ''
---
**Is your feature request related to a problem? Please describe.**
A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
**Describe the solution you'd like**
A clear and concise description of what you want to happen.
**Describe alternatives you've considered**
A clear and concise description of any alternative solutions or features you've considered.
**Additional context**
Add any other context or screenshots about the feature request here.
================================================
FILE: .github/ISSUE_TEMPLATE/3-typst_packages.md
================================================
---
name: Typst packages
about: For issues related to Typst packages
title: "[Typst packages]: "
labels: typst packages
assignees: ''
---
================================================
FILE: .github/workflows/pages.yml
================================================
name: Build and deploy documentation
on:
push:
branches:
- main
workflow_dispatch:
permissions:
contents: read
pages: write
id-token: write
concurrency:
group: pages
cancel-in-progress: false
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- uses: cachix/install-nix-action@v31
- uses: cachix/cachix-action@v16
with:
name: typst-nix
authToken: ${{ secrets.CACHIX_AUTH_TOKEN }}
- name: Setup Pages
id: pages
uses: actions/configure-pages@v5
- name: Build with mdBook
run: |
nix build --accept-flake-config .#docs --out-link result --print-build-logs
cp -RLT result book
- name: Upload artifact
uses: actions/upload-pages-artifact@v4
with:
path: ./book
deploy:
environment:
name: github-pages
url: ${{ steps.deployment.outputs.page_url }}
runs-on: ubuntu-latest
needs: build
steps:
- name: Deploy to GitHub Pages
id: deployment
uses: actions/deploy-pages@v4
================================================
FILE: .github/workflows/publish.yml
================================================
name: Publish flake to FlakeHub
on:
release:
types: [published]
workflow_dispatch:
inputs:
tag:
description: "The existing tag to publish to FlakeHub"
type: "string"
required: true
jobs:
publish-flakehub:
runs-on: ubuntu-latest
permissions:
id-token: write
contents: read
steps:
- name: Get git tag
id: git-tag
run: |
if [ -z "$TAG" ]; then
echo "::error::Could not determine git tag"
exit 1
fi
echo "tag=$TAG" >>"$GITHUB_OUTPUT"
env:
TAG: ${{ inputs.tag || github.ref_name }}
- uses: actions/checkout@v4
with:
ref: ${{ format('refs/tags/{0}', steps.git-tag.outputs.tag) }}
- uses: cachix/install-nix-action@v31
- uses: DeterminateSystems/flakehub-push@v6
with:
visibility: public
name: loqusion/typix
tag: ${{ steps.git-tag.outputs.tag }}
================================================
FILE: .github/workflows/test.yml
================================================
name: Run flake checks
on:
pull_request:
types: [opened, reopened, synchronize]
push:
branches:
- main
- "ci*"
permissions:
contents: read
jobs:
checks:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: cachix/install-nix-action@v31
- name: flake check
run: nix flake check
examples:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: cachix/install-nix-action@v31
- name: check examples
run: |
set -euo pipefail
for f in $(find ./examples -maxdepth 1 -mindepth 1 -type d | sort -u); do
nix flake check --no-write-lock-file "$f"
done
================================================
FILE: .github/workflows/update-lockfile.yml
================================================
name: Update flake lockfile
on:
workflow_dispatch:
schedule:
- cron: "39 8 7,22 * *"
permissions:
contents: read
jobs:
update:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: cachix/install-nix-action@v31
- uses: cachix/cachix-action@v16
with:
name: typst-nix
authToken: ${{ secrets.CACHIX_AUTH_TOKEN }}
- name: Update flake.lock
id: update
uses: DeterminateSystems/update-flake-lock@v27
with:
token: ${{ secrets.GH_TOKEN_FOR_UPDATES }}
commit-msg: "chore: update flake.lock"
pr-title: "chore: update flake.lock"
pr-body: |
Automated changes by the [update-flake-lock](https://github.com/DeterminateSystems/update-flake-lock) GitHub Action.
```
{{ env.GIT_COMMIT_MESSAGE }}
```
pr-labels: |
dependencies
automated
nix-options: --accept-flake-config
- name: Merge PR
run: |
gh pr merge --squash --delete-branch --auto "$PR_NUMBER"
env:
GH_TOKEN: ${{ secrets.GH_TOKEN_FOR_UPDATES }}
PR_NUMBER: ${{ steps.update.outputs.pull-request-number }}
================================================
FILE: .gitignore
================================================
/result
.direnv/
*.pdf
================================================
FILE: .markdownlint-cli2.jsonc
================================================
{
"ignores": ["CHANGELOG.md"],
}
================================================
FILE: .markdownlint.json
================================================
{
"no-inline-html": false
}
================================================
FILE: .prettierignore
================================================
docs/book
docs/theme
flake.lock
================================================
FILE: CHANGELOG.md
================================================
# [0.3.2] (June 27, 2025)
### Added
- `typstOpts` repeatable flags ([#59])
[#59]: https://github.com/loqusion/typix/pull/59
# [0.3.1] (April 02, 2025)
### Added
- Typst packages support (unstable) ([#51])
- `with-typst-packages-unpublished` template ([#51])
### Changed
- Use `unstable_typstPackages` in `with-typst-packages` template ([#51])
[#51]: https://github.com/loqusion/typix/pull/51
# [0.3.0] (January 27, 2025)
### Added
- **BREAKING CHANGE:** Include an emoji font in all derivations by default ([#44])
- Add `emojiFont` attribute in all derivations ([#44])
[#44]: https://github.com/loqusion/typix/pull/44
# [0.2.0] (January 3, 2025)
### Fixed
- **BREAKING CHANGE:** Unset `SOURCE_DATE_EPOCH` environment variable in all derivations
([#40])
[#40]: https://github.com/loqusion/typix/pull/40
# [0.1.7] (December 29, 2024)
### Changed
- Improve build times ([#38])
[#38]: https://github.com/loqusion/typix/pull/38
# [0.1.6] (October 30, 2024)
### Fixed
- Include `metadata.toml` in `cleanTypstSource` ([#29])
[#29]: https://github.com/loqusion/typix/pull/29
# [0.1.5] (July 13, 2024)
### Fixed
- Include `typst.toml` in `cleanTypstSource` ([#20])
[#20]: https://github.com/loqusion/typix/pull/20
# [0.1.4] (May 2, 2024)
### Fixed
- Handle `src` attribute correctly in `virtualPaths` ([#12])
[#12]: https://github.com/loqusion/typix/pull/12
# [0.1.3] (March 26, 2024)
### Fixed
- Include missing dependencies in `buildTypstProjectLocal` and `watchTypstProject`
# [0.1.2] (February 29, 2024)
- Test release
# [0.1.1] (February 29, 2024)
- Add release script
- Add `description` attribute to `flake.nix`
# [0.1.0] (February 29, 2024)
- First release
[0.3.2]: https://github.com/loqusion/typix/compare/0.3.1...0.3.2
[0.3.1]: https://github.com/loqusion/typix/compare/0.3.0...0.3.1
[0.3.0]: https://github.com/loqusion/typix/compare/0.2.0...0.3.0
[0.2.0]: https://github.com/loqusion/typix/compare/0.1.7...0.2.0
[0.1.7]: https://github.com/loqusion/typix/compare/0.1.6...0.1.7
[0.1.6]: https://github.com/loqusion/typix/compare/0.1.5...0.1.6
[0.1.5]: https://github.com/loqusion/typix/compare/0.1.4...0.1.5
[0.1.4]: https://github.com/loqusion/typix/compare/0.1.3...0.1.4
[0.1.3]: https://github.com/loqusion/typix/compare/0.1.2...0.1.3
[0.1.2]: https://github.com/loqusion/typix/compare/0.1.1...0.1.2
[0.1.1]: https://github.com/loqusion/typix/compare/0.1.0...0.1.1
[0.1.0]: https://github.com/loqusion/typix/commits/0.1.0-1/
================================================
FILE: LICENSE
================================================
MIT License
Copyright (c) 2023 loqusion
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
================================================
FILE: README.md
================================================
Typix
Typix aims to make it easier to use [Nix](https://nixos.org/) in
[Typst](https://github.com/typst/typst) projects.
- **Dependency management**: supports arbitrary dependencies including fonts,
images, and data
- **Reproducible**: via a hermetically sealed build environment
- **Extensible**: full support for [Typst packages](https://loqusion.github.io/typix/recipes/using-typst-packages.html)
## Features
- Automatically fetch dependencies and compile in a single command (`nix run
.#build`)
- Watch input files and recompile on changes (`nix run .#watch`)
- Set up a shell environment with all dependencies made available via
environment variables and symlinks
- Extensible via
[`mkTypstDerivation`](https://loqusion.github.io/typix/api/derivations/mk-typst-derivation.html)
- Support for dependencies such as [fonts](https://typst.app/docs/reference/text/text/#parameters-font),
[images](https://typst.app/docs/reference/visualize/image/), and [data](https://typst.app/docs/reference/data-loading/)
- [Typst packages](https://loqusion.github.io/typix/recipes/using-typst-packages.html)
fetched from the official Typst packages CDN
## Getting Started
After [installing Nix](https://github.com/DeterminateSystems/nix-installer) and
[enabling
flakes](https://nixos.wiki/wiki/Flakes#Enable_flakes_permanently_in_NixOS), you
can initialize a flake from the default template:
```bash
nix flake init --refresh -t github:loqusion/typix
```
> Alternatively, you can use a template demonstrating [Typst packages](https://loqusion.github.io/typix/recipes/using-typst-packages.html)
> usage:
>
> ```bash
> nix flake init --refresh -t 'github:loqusion/typix#with-typst-packages'
> ```
Here are some commands you can run from any template:
- `nix run .#watch` — watch the input files and recompile on changes
- `nix run .#build` — compile and copy the output to the current directory
---
For more information, check out [the docs](https://loqusion.github.io/typix/).
================================================
FILE: checks/.gitignore
================================================
*.pdf
================================================
FILE: checks/build-local.nix
================================================
{
lib,
pkgs,
buildTypstProjectLocal,
}: runCommandDrvAttr: args: let
build-local-drv = buildTypstProjectLocal ({
name = "build-local-check";
}
// args
// runCommandDrvAttr);
in
pkgs.runCommand "build-local" (runCommandDrvAttr
// {
nativeBuildInputs =
(runCommandDrvAttr.nativeBuildInputs or [])
++ [
build-local-drv
];
}) ''
${lib.getExe build-local-drv} "$out"
''
================================================
FILE: checks/check-emojis.py
================================================
"""
Checks if emoji characters in a PDF file are rendered with an appropriate font face.
This script is dumb, and only checks if the font face name for text with an
emoji matches one of a set of patterns given on the command line. This
assumption is naive, and may not hold if the font names change, or if a font
name not supporting emoji happens to match any of the patterns.
"""
import re
import sys
from collections.abc import Iterator
from dataclasses import dataclass
from typing import Final
import emoji
import pdfplumber
@dataclass
class TextElement:
text: str
font: str
class InvalidEmojiFontException(Exception):
def __init__(self, text_element: TextElement, font_patterns: list[re.Pattern]):
self.text_element = text_element
self.font_patterns = font_patterns
self.message = (
f'Detected invalid font for text containing emoji character: "{text_element.text}"\n'
f'Font: "{text_element.font}"\n'
f"Font did not match any of the following patterns: {', '.join((f"'{pat.pattern}'" for pat in font_patterns))}"
)
super().__init__(self.message)
class PDFChecker:
pdf_path: str
def __init__(self, pdf_path: str):
self.pdf_path = pdf_path
def check_emojis(self, font_patterns: list[re.Pattern]):
text_elements = self._extract_text_elements()
for text_element in text_elements:
if emoji.emoji_count(text_element.text) == 0:
continue
if not any(pat.search(text_element.font) for pat in font_patterns):
raise InvalidEmojiFontException(text_element, font_patterns)
def _extract_text_elements(self) -> Iterator[TextElement]:
with pdfplumber.open(self.pdf_path) as pdf:
for page in pdf.pages:
words = page.extract_words(
keep_blank_chars=True,
use_text_flow=True,
extra_attrs=["fontname"],
)
for word in words:
yield TextElement(
text=word["text"],
font=word["fontname"],
)
class InvalidArgumentException(Exception):
USAGE: Final = f"usage: {sys.argv[0]} [...]"
def __init__(self, message: str):
self.message = message + "\n" + InvalidArgumentException.USAGE
super().__init__(self.message)
def main():
pdf_path = sys.argv[1]
checker = PDFChecker(pdf_path)
font_patterns = list(map(lambda pat: re.compile(pat, re.IGNORECASE), sys.argv[2:]))
if len(font_patterns) == 0:
raise InvalidArgumentException(
"expected one or more patterns given as arguments"
)
checker.check_emojis(font_patterns)
if __name__ == "__main__":
try:
main()
except InvalidEmojiFontException as err:
print(f"test failed: {err}", file=sys.stderr)
sys.exit(1)
except InvalidArgumentException as err:
print(f"error: {err}", file=sys.stderr)
sys.exit(2)
except Exception:
raise
================================================
FILE: checks/clean/bad.c
================================================
#include
int main(void) {
printf("Hello, World!\n");
return 0;
}
================================================
FILE: checks/clean/lib.typ
================================================
#bibliography("works.bib")
================================================
FILE: checks/clean/metadata.toml
================================================
#:schema https://raw.githubusercontent.com/mintyfrankie/brilliant-CV/main/metadata.toml.schema.json
# Set the output language
# INFO: value must matches folder suffix; i.e "zh" -> "./modules_zh"
language = "en"
[layout]
# Optional values: skyblue, red, nephritis, concrete, darknight
# You can also use a custom color by hex code i.e. "#1E90FF"
awesome_color = "skyblue"
# Skips are for controlling the spacing between sections and entries
before_section_skip = "1pt"
before_entry_skip = "1pt"
before_entry_description_skip = "1pt"
[layout.fonts]
regular_fonts = ["Source Sans Pro", "Source Sans 3"]
header_font = "Roboto"
[layout.header]
# Optional values: left, center, right
header_align = "left"
# Decide if you want to display profile photo or not
display_profile_photo = true
[layout.entry]
# Decide if you want to put your company in bold or your position in bold
display_entry_society_first = true
# Decide if you want to display organisation logo or not
display_logo = true
[inject]
# Decide if you want to inject AI prompt or not
inject_ai_prompt = false
# Decide if you want to inject keywords or not
inject_keywords = true
injected_keywords_list = ["Data Analyst", "GCP", "Python", "SQL", "Tableau"]
[personal]
first_name = "John"
last_name = "Doe"
# The order of this section will affect how the entries are displayed
# The custom value is for any additional information you want to add, name it as custom-1, custom-2, etc.
[personal.info]
github = "mintyfrankie"
phone = "+33 6 12 34 56 78"
email = "john.doe@me.org"
linkedin = "johndoe"
# gitlab = "mintyfrankie"
# homepage = "jd.me.org"
# orcid = "0000-0000-0000-0000"
# researchgate = "John-Doe"
# extraInfo = "I am a cool kid"
[personal.info.custom-1]
# image = "" # Example: image("./path/to/image.png")
awesomeIcon = "graduation-cap" # Example: "graduation-cap" see https://typst.app/universe/package/fontawesome/
text = "PhD"
link = "https://www.example.com"
# add a new section if you want to include the language of your choice
# i.e. [[lang.ru]]
# each section must contains the following fields
[lang.en]
header_quote = "Experienced Data Analyst looking for a full time job starting from now"
cv_footer = "Curriculum vitae"
letter_footer = "Cover letter"
[lang.fr]
header_quote = "Analyste de données expérimenté à la recherche d'un emploi à temps plein disponible dès maintenant"
cv_footer = "Résumé"
letter_footer = "Lettre de motivation"
[lang.zh]
header_quote = "具有丰富经验的数据分析师,随时可入职"
cv_footer = "简历"
letter_footer = "申请信"
# For languages that are not written in Latin script
# Currently supported non-latin language codes: ("zh", "ja", "ko", "ru")
[lang.non_latin]
name = "王道尔"
font = "Heiti SC"
================================================
FILE: checks/clean/sub/bad.py
================================================
if __name__ == "__main__":
print("Hello, World!")
================================================
FILE: checks/clean/sub/sub.typ
================================================
================================================
FILE: checks/clean/sub/typst.toml
================================================
[package]
name = "sub"
version = "0.1.0"
entrypoint = "sub.typ"
================================================
FILE: checks/clean/typst.toml
================================================
[package]
name = "clean"
version = "0.1.0"
entrypoint = "lib.typ"
================================================
FILE: checks/clean/works.bib
================================================
\begin{thebibliography}{9}
\bibitem{texbook}
Donald E. Knuth (1986) \emph{The \TeX{} Book}, Addison-Wesley Professional.
\bibitem{lamport94}
Leslie Lamport (1994) \emph{\LaTeX: a document preparation system}, Addison
Wesley, Massachusetts, 2nd ed.
\end{thebibliography}
================================================
FILE: checks/clean-expected/lib.typ
================================================
#bibliography("works.bib")
================================================
FILE: checks/clean-expected/metadata.toml
================================================
#:schema https://raw.githubusercontent.com/mintyfrankie/brilliant-CV/main/metadata.toml.schema.json
# Set the output language
# INFO: value must matches folder suffix; i.e "zh" -> "./modules_zh"
language = "en"
[layout]
# Optional values: skyblue, red, nephritis, concrete, darknight
# You can also use a custom color by hex code i.e. "#1E90FF"
awesome_color = "skyblue"
# Skips are for controlling the spacing between sections and entries
before_section_skip = "1pt"
before_entry_skip = "1pt"
before_entry_description_skip = "1pt"
[layout.fonts]
regular_fonts = ["Source Sans Pro", "Source Sans 3"]
header_font = "Roboto"
[layout.header]
# Optional values: left, center, right
header_align = "left"
# Decide if you want to display profile photo or not
display_profile_photo = true
[layout.entry]
# Decide if you want to put your company in bold or your position in bold
display_entry_society_first = true
# Decide if you want to display organisation logo or not
display_logo = true
[inject]
# Decide if you want to inject AI prompt or not
inject_ai_prompt = false
# Decide if you want to inject keywords or not
inject_keywords = true
injected_keywords_list = ["Data Analyst", "GCP", "Python", "SQL", "Tableau"]
[personal]
first_name = "John"
last_name = "Doe"
# The order of this section will affect how the entries are displayed
# The custom value is for any additional information you want to add, name it as custom-1, custom-2, etc.
[personal.info]
github = "mintyfrankie"
phone = "+33 6 12 34 56 78"
email = "john.doe@me.org"
linkedin = "johndoe"
# gitlab = "mintyfrankie"
# homepage = "jd.me.org"
# orcid = "0000-0000-0000-0000"
# researchgate = "John-Doe"
# extraInfo = "I am a cool kid"
[personal.info.custom-1]
# image = "" # Example: image("./path/to/image.png")
awesomeIcon = "graduation-cap" # Example: "graduation-cap" see https://typst.app/universe/package/fontawesome/
text = "PhD"
link = "https://www.example.com"
# add a new section if you want to include the language of your choice
# i.e. [[lang.ru]]
# each section must contains the following fields
[lang.en]
header_quote = "Experienced Data Analyst looking for a full time job starting from now"
cv_footer = "Curriculum vitae"
letter_footer = "Cover letter"
[lang.fr]
header_quote = "Analyste de données expérimenté à la recherche d'un emploi à temps plein disponible dès maintenant"
cv_footer = "Résumé"
letter_footer = "Lettre de motivation"
[lang.zh]
header_quote = "具有丰富经验的数据分析师,随时可入职"
cv_footer = "简历"
letter_footer = "申请信"
# For languages that are not written in Latin script
# Currently supported non-latin language codes: ("zh", "ja", "ko", "ru")
[lang.non_latin]
name = "王道尔"
font = "Heiti SC"
================================================
FILE: checks/clean-expected/sub/sub.typ
================================================
================================================
FILE: checks/clean-expected/sub/typst.toml
================================================
[package]
name = "sub"
version = "0.1.0"
entrypoint = "sub.typ"
================================================
FILE: checks/clean-expected/typst.toml
================================================
[package]
name = "clean"
version = "0.1.0"
entrypoint = "lib.typ"
================================================
FILE: checks/clean-expected/works.bib
================================================
\begin{thebibliography}{9}
\bibitem{texbook}
Donald E. Knuth (1986) \emph{The \TeX{} Book}, Addison-Wesley Professional.
\bibitem{lamport94}
Leslie Lamport (1994) \emph{\LaTeX: a document preparation system}, Addison
Wesley, Massachusetts, 2nd ed.
\end{thebibliography}
================================================
FILE: checks/date/main.typ
================================================
#let UNIX_EPOCH = datetime(
year: 1980,
month: 1,
day: 1,
)
#assert.ne(
datetime.today(),
UNIX_EPOCH,
)
================================================
FILE: checks/default.nix
================================================
{
pkgs,
myLib,
}: let
inherit (pkgs) lib;
inherit (lib.strings) escapeShellArg concatMapStringsSep;
onlyDrvs = lib.filterAttrs (_: lib.isDerivation);
in
onlyDrvs (lib.makeScope myLib.newScope (self: let
callPackage = self.newScope {};
typstSource = "main.typ";
fontPaths = [
"${pkgs.roboto}/share/fonts/truetype"
];
virtualPaths = [
{
src = ./fixtures/icons;
dest = "icons";
}
];
unstable_typstPackages = [
{
name = "example";
version = "0.1.0";
hash = "sha256-R18Xv3AoZsTtMycRasczTsje5yIfiURIxtDICQ4mvho=";
}
{
name = "cetz";
version = "0.3.4";
hash = "sha256-5w3UYRUSdi4hCvAjrp9HslzrUw7BhgDdeCiDRHGvqd4=";
}
{
name = "polylux";
version = "0.4.0";
hash = "sha256-4owP2KiyaaASS1YZ0Hs58k6UEVAqsRR3YdGF26ikosk=";
}
# Required by cetz
{
name = "oxifmt";
version = "0.2.1";
hash = "sha256-8PNPa9TGFybMZ1uuJwb5ET0WGIInmIgg8h24BmdfxlU=";
}
];
in rec {
buildLocal = callPackage ./build-local.nix {};
buildLocalSimple = buildLocal {} {
inherit typstSource;
src = myLib.cleanTypstSource ./simple;
};
buildLocalSimpleWithFonts = buildLocal {} {
inherit fontPaths typstSource;
src = myLib.cleanTypstSource ./simple-with-fonts;
};
buildLocalSimpleWithVirtualPaths = buildLocal {} {
inherit virtualPaths typstSource;
src = myLib.cleanTypstSource ./simple-with-virtual-paths;
};
buildLocalWithMultipleParameters = buildLocal {} {
inherit typstSource;
src = myLib.cleanTypstSource ./simple-with-multiple-parameters;
typstOpts = {
input = ["key1=value1" "key2=value2" "key3= --spaces-are-properly-escaped" "key4='quotes-are-properly-escaped\""];
};
};
buildLocalWithTypstPackages = buildLocal {} {
inherit typstSource;
src = myLib.cleanTypstSource ./typst-packages;
inherit unstable_typstPackages;
};
clean = myLib.mkTypstDerivation {
src = myLib.cleanTypstSource ./clean;
EXPECTED_SRC = ./clean-expected;
buildPhaseTypstCommand = ''
diff -r "$src" "$EXPECTED_SRC"
touch $out
'';
};
date = myLib.buildTypstProject {
inherit typstSource;
src = myLib.cleanTypstSource ./date;
};
dateWatch = watch {} {
inherit typstSource;
src = myLib.cleanTypstSource ./date;
};
devShell = myLib.devShell {
inherit virtualPaths;
checks = {
simple = myLib.buildTypstProject {
inherit virtualPaths typstSource;
src = myLib.cleanTypstSource ./simple;
};
};
};
checkEmojiScript = {
inputs =
(with pkgs; [
python312
python312Packages.emoji
])
++ (
with pkgs.python312Packages; [
# Referencing `emoji` doesn't work here because an attribute of that
# name already exists in a recursive attribute set (`rec {...}`)
pdfplumber
]
);
script = patterns: ''
python3.12 ${./check-emojis.py} "$out" ${concatMapStringsSep " " escapeShellArg patterns}
'';
};
emoji = {
emojiFont,
fontPaths ? [],
patterns,
}: (myLib.buildTypstProject ({
inherit typstSource fontPaths;
src = myLib.cleanTypstSource ./emoji;
doCheck = true;
nativeCheckInputs = checkEmojiScript.inputs;
checkPhase = checkEmojiScript.script patterns;
}
// lib.optionalAttrs (emojiFont != "__OMIT__") {
inherit emojiFont;
}));
emojiOmit = emoji {
emojiFont = "__OMIT__";
patterns = ["emoji"];
};
emojiTwemoji = emoji {
emojiFont = "twemoji";
patterns = ["emoji"];
};
emojiTwemojiCbdt = emoji {
emojiFont = "twemoji-cbdt";
patterns = ["emoji"];
};
emojiNoto = emoji {
emojiFont = "noto";
patterns = ["emoji"];
};
emojiNotoMonochrome = emoji {
emojiFont = "noto-monochrome";
patterns = ["emoji"];
};
# FIXME: https://github.com/loqusion/typix/issues/79
# emojiEmojiOne = emoji {
# emojiFont = "emojione";
# patterns = ["emoji"];
# };
emojiFontOverride = emoji {
emojiFont = null;
fontPaths = ["${pkgs.noto-fonts-color-emoji}/share/fonts/noto"];
patterns = ["emoji"];
};
emojiWatch = {
emojiFont,
fontPaths ? [],
patterns,
}: (watch {
nativeBuildInputs = checkEmojiScript.inputs;
postBuild = checkEmojiScript.script patterns;
} ({
inherit typstSource fontPaths;
src = myLib.cleanTypstSource ./emoji;
}
// lib.optionalAttrs (emojiFont != "__OMIT__") {
inherit emojiFont;
}));
emojiWatchOmit = emojiWatch {
emojiFont = "__OMIT__";
patterns = ["emoji"];
};
emojiWatchTwemoji = emojiWatch {
emojiFont = "twemoji";
patterns = ["emoji"];
};
emojiWatchTwemojiCbdt = emojiWatch {
emojiFont = "twemoji-cbdt";
patterns = ["emoji"];
};
emojiWatchNoto = emojiWatch {
emojiFont = "noto";
patterns = ["emoji"];
};
emojiWatchNotoMonochrome = emojiWatch {
emojiFont = "noto-monochrome";
patterns = ["emoji"];
};
# FIXME: https://github.com/loqusion/typix/issues/79
# emojiWatchEmojiOne = emojiWatch {
# emojiFont = "emojione";
# patterns = ["emoji"];
# };
emojiWatchFontOverride = emojiWatch {
emojiFont = null;
fontPaths = ["${pkgs.noto-fonts-color-emoji}/share/fonts/noto"];
patterns = ["emoji"];
};
overlappingVirtualPaths = isInvariant: util: file:
util (let
op =
if isInvariant
then "!="
else "=";
errorMsg =
if isInvariant
then ''$FILE_TO_CHECK was overwritten\; it should stay the same when forceVirtualPaths is false''
else ''$FILE_TO_CHECK was not overwritten\; it should be overwritten when forceVirtualPaths is true'';
in {
FILE_TO_CHECK = file;
preBuild = ''
if [ ! -e "$FILE_TO_CHECK" ]; then
echo "$FILE_TO_CHECK does not exist; unable to run check"
exit 1
fi
hash=$(sha256sum "$FILE_TO_CHECK" | awk '{ print $1 }')
if [ -z "$hash" ]; then
echo "unable to obtain hash for $FILE_TO_CHECK"
exit 1
fi
'';
postBuild = ''
hash=''${hash:?not defined}
new_hash=$(sha256sum "$FILE_TO_CHECK" | awk '{ print $1 }')
if [ -z "$new_hash" ]; then
echo "unable to obtain hash for $FILE_TO_CHECK"
exit 1
fi
if [ "$hash" ${op} "$new_hash" ]; then
echo ${errorMsg}
echo
echo "old hash: $hash"
echo "new hash: $new_hash"
exit 1
fi
'';
}) {
inherit virtualPaths typstSource;
src = ./overlapping-virtual-paths;
forceVirtualPaths = !isInvariant;
};
overlappingVirtualPathsInvariant = overlappingVirtualPaths true;
overlappingVirtualPathsForce = overlappingVirtualPaths false;
simple = myLib.buildTypstProject {
inherit typstSource;
src = myLib.cleanTypstSource ./simple;
};
simpleWithFonts = myLib.buildTypstProject {
inherit fontPaths typstSource;
src = myLib.cleanTypstSource ./simple-with-fonts;
};
simpleWithMultipleParameters = myLib.buildTypstProject {
inherit typstSource;
src = myLib.cleanTypstSource ./simple-with-multiple-parameters;
typstOpts = {
input = ["key1=value1" "key2=value2" "key3= --spaces-are-properly-escaped" "key4='quotes-are-properly-escaped\""];
};
};
simpleWithVirtualPaths = myLib.buildTypstProject {
inherit virtualPaths typstSource;
src = myLib.cleanTypstSource ./simple-with-virtual-paths;
};
withTypstPackages = myLib.buildTypstProject {
inherit typstSource;
src = myLib.cleanTypstSource ./typst-packages;
inherit unstable_typstPackages;
};
virtualPathsChecks = callPackage ./virtual-paths.nix {};
watch = callPackage ./watch.nix {};
watchSimple = watch {} {
inherit typstSource;
src = myLib.cleanTypstSource ./simple;
};
watchSimpleWithFonts = watch {} {
inherit fontPaths typstSource;
src = myLib.cleanTypstSource ./simple-with-fonts;
};
watchWithMultipleParameters = watch {} {
inherit typstSource;
src = myLib.cleanTypstSource ./simple-with-multiple-parameters;
typstOpts = {
input = ["key1=value1" "key2=value2" "key3= --spaces-are-properly-escaped" "key4='quotes-are-properly-escaped\""];
};
};
# TODO: see above
# watchSimpleWithTypstPackages = watch {} {
# inherit typstSource;
# src = myLib.cleanTypstSource ./simple-with-typst-packages;
# };
watchSimpleWithVirtualPaths = watch {} {
inherit virtualPaths typstSource;
src = myLib.cleanTypstSource ./simple-with-virtual-paths;
};
watchOverlappingVirtualPaths = overlappingVirtualPathsInvariant watch "icons/link.svg";
watchOverlappingVirtualPathsForce = overlappingVirtualPathsForce watch "icons/link.svg";
}))
================================================
FILE: checks/emoji/main.typ
================================================
#(emoji.tangerine)hell#(emoji.o) w#(emoji.o)rld#(emoji.face)
================================================
FILE: checks/overlapping-virtual-paths/main.typ
================================================
#lorem(100)
#image("icons/link.svg")
================================================
FILE: checks/simple/main.typ
================================================
#lorem(100)
================================================
FILE: checks/simple-with-fonts/main.typ
================================================
#set text(font: "Roboto")
#lorem(100)
================================================
FILE: checks/simple-with-multiple-parameters/main.typ
================================================
#sys.inputs.key1
#sys.inputs.key2
================================================
FILE: checks/simple-with-virtual-paths/main.typ
================================================
#lorem(100)
#image("icons/link.svg")
#image("icons/paper-plane-tilt.svg")
================================================
FILE: checks/typst-packages/main.typ
================================================
#import "@preview/example:0.1.0": add
#import "@preview/cetz:0.3.4"
#import "@preview/polylux:0.4.0": slide, uncover
// example
2 + 2 = #[add(2 + 2)]
// cetz
#cetz.canvas({
import cetz.draw: *
circle((0, 0))
line((0, 0), (2, 1))
})
// polylux
// Make the paper dimensions fit for a presentation and the text larger
#set page(paper: "presentation-16-9")
#set text(size: 25pt)
// Use #slide to create a slide and style it using your favourite Typst functions
#slide[
#set align(horizon)
= Very minimalist slides
A lazy author
July 23, 2023
]
#slide[
== First slide
Some static text on this slide.
]
#slide[
== This slide changes!
You can always see this.
// Make use of features like #uncover, #only, and others to create dynamic content
#uncover(2)[But this appears later!]
]
================================================
FILE: checks/virtual-paths.nix
================================================
{
cleanTypstSource,
copyVirtualPathsHook,
lib,
linkFarmFromDrvs,
linkVirtualPaths,
pkgs,
}: let
inherit (lib.attrsets) filterAttrs mapAttrsToList;
inherit (lib.lists) all;
inherit (lib.strings) toShellVars;
cleanArgs = args:
builtins.removeAttrs args [
"virtualPaths"
"assertionCommand"
"linkAssertionCommnad"
];
copyVirtualPathsHookAssertion = args @ {
virtualPaths,
assertionCommand,
...
}:
pkgs.stdenvNoCC.mkDerivation ((cleanArgs args)
// {
src = cleanTypstSource ./simple;
nativeBuildInputs = [
(copyVirtualPathsHook virtualPaths)
];
buildPhase = ''
runHook preBuild
runHook postBuild
'';
postBuild = ''
set -euo pipefail
assertionCommand() {
${assertionCommand}
}
if ! assertionCommand; then
${toShellVars {assertionText = assertionCommand;}}
echo "assertion \`$assertionText\` failed"
exit 1
fi
touch "$out"
'';
});
linkVirtualPathsAssertion = args @ {
virtualPaths,
assertionCommand,
linkAssertionCommand ? "true",
...
}:
pkgs.stdenvNoCC.mkDerivation ((cleanArgs args)
// {
src = cleanTypstSource ./simple;
buildPhase = ''
${linkVirtualPaths {inherit virtualPaths;}}
runHook postBuild
'';
postBuild = ''
set -euo pipefail
assertionCommand() {
${assertionCommand}
}
linkAssertionCommand() {
${linkAssertionCommand}
}
if ! assertionCommand; then
${toShellVars {assertionText = assertionCommand;}}
echo "assertion \`$assertionText\` failed"
exit 1
fi
if ! linkAssertionCommand; then
${toShellVars {assertionText = linkAssertionCommand;}}
echo "assertion \`$assertionText\` failed"
exit 1
fi
touch "$out"
'';
});
virtualPathsTestAttrs = {
fileSource = {
virtualPaths = ["${./fixtures/icons}/link.svg"];
assertionCommand = ''[ -f ./link.svg ]'';
linkAssertionCommand = ''[ -L ./link.svg ]'';
};
directorySource = {
virtualPaths = [./fixtures/icons];
assertionCommand = ''[ -f ./main.typ ] && [ -f ./link.svg ]'';
linkAssertionCommand = ''[ -L ./link.svg ]'';
};
fileSourceWithDest = {
virtualPaths = [
{
src = ./fixtures/icons/link.svg;
dest = "link.svg";
}
];
assertionCommand = ''[ -f ./link.svg ]'';
linkAssertionCommand = ''[ -L ./link.svg ]'';
};
directorySourceWithDest = {
virtualPaths = [
{
src = ./fixtures/icons;
dest = "icons";
}
];
assertionCommand = ''[ -d ./icons ] && [ -f ./icons/link.svg ]'';
linkAssertionCommand = ''[ ! -L ./icons ] && [ -L ./icons/link.svg ]'';
};
fileSourceWithDeepDest = {
virtualPaths = [
{
src = ./fixtures/icons/link.svg;
dest = "assets/icons/link.svg";
}
];
assertionCommand = ''[ -d ./assets/icons ] && [ -f ./assets/icons/link.svg ]'';
linkAssertionCommand = ''[ ! -L ./assets ] && [ ! -L ./assets/icons ] && [ -L ./assets/icons/link.svg ]'';
};
directorySourceWithDeepDest = {
virtualPaths = [
{
src = ./fixtures/icons;
dest = "assets/icons";
}
];
assertionCommand = ''[ -d ./assets/icons ] && [ -f ./assets/icons/link.svg ]'';
linkAssertionCommand = ''[ ! -L ./assets ] && [ ! -L ./assets/icons ] && [ -L ./assets/icons/link.svg ]'';
};
mergedSources = {
virtualPaths = [
{
src = ./fixtures/icons;
dest = "icons";
}
{
src = ./fixtures/more-icons;
dest = "icons";
}
];
assertionCommand = ''[ -d ./icons ] && [ -f ./icons/link.svg ] && [ -f ./icons/another-link.svg ]'';
linkAssertionCommand = ''[ ! -L ./icons ] && [ -L ./icons/link.svg ] && [ -L ./icons/another-link.svg ]'';
};
};
skip = {
copyVirtualPathsHook = [];
linkVirtualPaths = [];
};
filterSkip = skipNames:
filterAttrs
(name: _: all (skipName: name != skipName) skipNames);
mapTestAttrs = f: skipAttrs: testGroupName:
mapAttrsToList
(name: attrs: f (attrs // {name = "${testGroupName}-${name}";}))
(filterSkip skipAttrs virtualPathsTestAttrs);
in
linkFarmFromDrvs "virtualPathsTests"
(
(mapTestAttrs copyVirtualPathsHookAssertion skip.copyVirtualPathsHook "copyVirtualPathsHook")
++ (mapTestAttrs linkVirtualPathsAssertion skip.linkVirtualPaths "linkVirtualPaths")
)
================================================
FILE: checks/watch.nix
================================================
{
lib,
pkgs,
watchTypstProject,
}: runCommandDrvAttr: args: let
cleanedArgs = builtins.removeAttrs args [
"src"
];
watch-drv = watchTypstProject ({
name = "watch-check";
# `typst watch` will never exit itself, but we can still check the exit status of `typst compile` for errors
typstWatchCommand = "typst compile";
}
// cleanedArgs);
in
pkgs.runCommand "watch" (runCommandDrvAttr
// {
nativeBuildInputs =
(runCommandDrvAttr.nativeBuildInputs or [])
++ [
watch-drv
];
}) ''
# This is needed to imitate a user's project directory
cp -RLT --no-preserve=mode ${args.src} .
runHook preBuild
${lib.getExe watch-drv} "$out"
runHook postBuild
''
================================================
FILE: docs/.gitignore
================================================
book
================================================
FILE: docs/SUMMARY.md
================================================
# Summary
- [Introduction](README.md)
- [Getting Started](getting-started.md)
# Recipes
- [Adding dependencies](recipes/adding-dependencies.md)
- [Specifying sources](recipes/specifying-sources.md)
- [Declaring a shell environment](recipes/declaring-a-shell-environment.md)
- [Using Typst packages](recipes/using-typst-packages.md)
# API Reference
- [Derivations](api/derivations.md)
- [buildTypstProject](api/derivations/build-typst-project.md)
- [buildTypstProjectLocal](api/derivations/build-typst-project-local.md)
- [devShell](api/derivations/dev-shell.md)
- [mkTypstDerivation](api/derivations/mk-typst-derivation.md)
- [watchTypstProject](api/derivations/watch-typst-project.md)
- [Utilities](api/utilities.md)
- [cleanTypstSource](api/utilities/clean-typst-source.md)
================================================
FILE: docs/api/derivations/build-typst-project-local.md
================================================
# buildTypstProjectLocal
Returns a derivation for compiling a Typst project and copying the output to the
current directory.
This is essentially a script which wraps
[`buildTypstProject`](build-typst-project.md).
Using this derivation requires
[`allow-import-from-derivation`](https://nixos.org/manual/nix/stable/command-ref/conf-file#conf-allow-import-from-derivation)
to be `true` (which is the default at the time of writing).
More info:
Invoking the script produced by this derivation directly is currently
unsupported. Instead, use `nix run`.
See [this issue](https://github.com/loqusion/typix/issues/2) for more
information.
## Parameters
All parameters accepted by
[`buildTypstProject`](build-typst-project.md#parameters) are also accepted by
`buildTypstProjectLocal`. They are repeated below for convenience.
### `src`
{{#include common/src.md}}
### `emojiFont` optional { #emojifont }
{{#include common/emoji-font.md}}
### `fontPaths` optional { #fontpaths }
{{#include common/font-paths.md}}
#### Example { #fontpaths-example }
{{#include common/font-paths-example.md:buildtypstprojectlocal_example}}
### `installPhaseCommand` optional { #installphasecommand }
{{#include common/install-phase-command.md}}
### `scriptName` optional { #scriptname }
{{#include common/script-name.md}}
Default is `typst-build`.
### `typstCompileCommand` optional { #typstcompilecommand }
{{#include common/typst-compile-command.md}}
Default is `typst compile`.
### `typstOpts` optional { #typstopts }
{{#include common/typst-opts.md:head}}
These are in addition to any options you manually pass in
[`typstCompileCommand`](#typstcompilecommand).
{{#include common/typst-opts.md:tail}}
#### Example { #typstopts-example }
{{#include common/typst-opts-example.md:buildtypstprojectlocal}}
{{#include common/typst-opts-example.md:typstcompile}}
### `typstOutput` optional { #typstoutput }
{{#include common/typst-project-output.md:head}}
{{#include common/typst-project-output.md:buildtypstprojectlocal}}
### `typstSource` optional { #typstsource }
{{#include common/typst-project-source.md}}
Default is `main.typ`.
### `unstable_typstPackages` optional { #typstpackages }
{{#include common/typst-packages.md:body}}
#### Example { #typstpackages-example }
{{#include common/typst-packages.md:example_buildtypstprojectlocal}}
{{#include common/typst-packages.md:example_typst}}
### `virtualPaths` optional { #virtualpaths }
{{#include common/virtual-paths.md}}
#### Example { #virtualpaths-example }
{{#include common/virtual-paths-example.md:head}}
{{#include common/virtual-paths-example.md:buildtypstprojectlocal_example}}
{{#include common/virtual-paths-example.md:tail}}
## Source
- [`buildTypstProjectLocal`](https://github.com/loqusion/typix/blob/main/lib/buildTypstProjectLocal.nix)
================================================
FILE: docs/api/derivations/build-typst-project.md
================================================
# buildTypstProject
Returns a derivation for compiling a Typst project.
If you want to build to the project directory, use
[`buildTypstProjectLocal`](build-typst-project-local.md) instead.
## Parameters
All parameters accepted by
[`mkTypstDerivation`](mk-typst-derivation.md#parameters) are also accepted by
`buildTypstProject`. They are repeated below for convenience.
### `src`
{{#include common/src.md}}
### `emojiFont` optional { #emojifont }
{{#include common/emoji-font.md}}
### `fontPaths` optional { #fontpaths }
{{#include common/font-paths.md}}
#### Example { #fontpaths-example }
{{#include common/font-paths-example.md:buildtypstproject_example}}
### `installPhaseCommand` optional { #installphasecommand }
{{#include common/install-phase-command.md}}
### `typstCompileCommand` optional { #typstcompilecommand }
{{#include common/typst-compile-command.md}}
Default is `typst compile`.
### `typstOpts` optional { #typstopts }
{{#include common/typst-opts.md:head}}
These are in addition to any options you manually pass in
[`typstCompileCommand`](#typstcompilecommand).
{{#include common/typst-opts.md:tail}}
#### Example { #typstopts-example }
{{#include common/typst-opts-example.md:buildtypstproject}}
{{#include common/typst-opts-example.md:typstcompile}}
### `typstSource` optional { #typstsource }
{{#include common/typst-project-source.md}}
Default is `main.typ`.
### `unstable_typstPackages` optional { #typstpackages }
{{#include common/typst-packages.md:body}}
#### Example { #typstpackages-example }
{{#include common/typst-packages.md:example_buildtypstproject}}
{{#include common/typst-packages.md:example_typst}}
### `virtualPaths` optional { #virtualpaths }
{{#include common/virtual-paths.md}}
#### Example { #virtualpaths-example }
{{#include common/virtual-paths-example.md:head}}
{{#include common/virtual-paths-example.md:buildtypstproject_example}}
{{#include common/virtual-paths-example.md:tail}}
## Source
- [`buildTypstProject`](https://github.com/loqusion/typix/blob/main/lib/buildTypstProject.nix)
================================================
FILE: docs/api/derivations/common/emoji-font.md
================================================
Specify which emoji font to use. If `emojiFont` is `null`, no emoji font will
be included.
May be any of the following:
- [`"twemoji"`](https://search.nixos.org/packages?channel=unstable&show=twemoji-color-font) (default)
- [`"twemoji-cbdt"`](https://search.nixos.org/packages?channel=unstable&show=twitter-color-emoji)
- [`"noto"`](https://search.nixos.org/packages?channel=unstable&show=noto-fonts-color-emoji)
- [`"noto-monochrome"`](https://search.nixos.org/packages?channel=unstable&show=noto-fonts-monochrome-emoji)
- [`"emojione"`](https://search.nixos.org/packages?channel=unstable&show=emojione)
- `null` — Don't include any emoji font (e.g. so you can include your own)
Note about difference between "twemoji" and "twemoji-cbdt"
The default Twemoji font displays color emojis using the SVG [font format],
which may not be supported by some systems. If emojis aren't displaying
properly, using `"twemoji-cbdt"` may fix it.
[font format]: https://www.colorfonts.wtf/
================================================
FILE: docs/api/derivations/common/font-paths-example.md
================================================
```nix
{
outputs = { nixpkgs, typix }: let
system = "x86_64-linux";
pkgs = nixpkgs.legacyPackages.${system};
inherit (pkgs) lib;
build-script = typix.lib.${system}.buildTypstProjectLocal {
fontPaths = [
"${pkgs.roboto}/share/fonts/truetype"
];
};
in {
apps.${system}.default = {
type = "app";
program = lib.getExe build-script;
};
};
}
```
```nix
{
outputs = { nixpkgs, typix }: let
system = "x86_64-linux";
pkgs = nixpkgs.legacyPackages.${system};
in {
packages.${system}.default = typix.lib.${system}.buildTypstProject {
fontPaths = [
"${pkgs.roboto}/share/fonts/truetype"
];
};
};
}
```
```nix
{
outputs = { nixpkgs, typix }: let
system = "x86_64-linux";
pkgs = nixpkgs.legacyPackages.${system};
in {
devShells.${system}.default = typix.lib.${system}.devShell {
fontPaths = [
"${pkgs.roboto}/share/fonts/truetype"
];
};
};
}
```
```nix
{
outputs = { nixpkgs, typix }: let
system = "x86_64-linux";
pkgs = nixpkgs.legacyPackages.${system};
in {
packages.${system}.default = typix.lib.${system}.mkTypstDerivation {
fontPaths = [
"${pkgs.roboto}/share/fonts/truetype"
];
};
};
}
```
```nix
{
outputs = { nixpkgs, typix }: let
system = "x86_64-linux";
pkgs = nixpkgs.legacyPackages.${system};
inherit (pkgs) lib;
watch-script = typix.lib.${system}.watchTypstProject {
fontPaths = [
"${pkgs.roboto}/share/fonts/truetype"
];
};
in {
apps.${system}.default = {
type = "app";
program = lib.getExe watch-script;
};
};
}
```
================================================
FILE: docs/api/derivations/common/font-paths.md
================================================
List of sources specifying paths to font files that will be made available to
your Typst project. With this, you can compile Typst projects even when the
fonts it uses are not available on your system.
Used for setting `TYPST_FONT_PATHS` (see [`text#font`][typst-ref-text--font]).
[typst-ref-text--font]: https://typst.app/docs/reference/text/text/#parameters-font
================================================
FILE: docs/api/derivations/common/install-phase-command.md
================================================
Command (or commands) to run during
[`installPhase`][nixpkgs-installphase].
[nixpkgs-installphase]: https://nixos.org/manual/nixpkgs/stable/#ssec-install-phase
================================================
FILE: docs/api/derivations/common/script-name.md
================================================
Name of the script that will be added to the Nix store. You can use this name
after entering a development shell to invoke the script.
================================================
FILE: docs/api/derivations/common/src.md
================================================
[Source](../../recipes/specifying-sources.md) containing all local files
needed in your Typst project.
================================================
FILE: docs/api/derivations/common/typst-compile-command.md
================================================
Base Typst command to run to compile the project. Other arguments will be
appended based on the parameters you supply.
================================================
FILE: docs/api/derivations/common/typst-opts-example.md
================================================
```nix
{
format = "png";
ppi = 300;
input = ["key1=value1" "key2=value2"];
}
```
...will result in a command like:
```nix
{
outputs = { typix }: let
system = "x86_64-linux";
in {
packages.${system}.default = typix.lib.${system}.buildTypstProject {
typstOpts = {
format = "png";
ppi = 300;
input = ["key1=value1" "key2=value2"];
};
};
};
}
```
...will result in a command like:
```nix
{
outputs = { typix }: let
system = "x86_64-linux";
inherit (nixpkgs) lib;
build-script = typix.lib.${system}.buildTypstProjectLocal {
typstOpts = {
format = "png";
ppi = 300;
input = ["key1=value1" "key2=value2"];
};
};
in {
apps.${system}.default = {
type = "app";
program = lib.getExe build-script;
};
};
}
```
...will result in a command like:
```nix
{
outputs = { typix }: let
system = "x86_64-linux";
inherit (nixpkgs) lib;
watch-script = typix.lib.${system}.watchTypstProject {
typstOpts = {
format = "png";
ppi = 300;
input = ["key1=value1" "key2=value2"];
};
};
in {
apps.${system}.default = {
type = "app";
program = lib.getExe watch-script;
};
};
}
```
...will result in a command like:
```sh
typst compile --format png --ppi 300 --input key1=value1 --input key2=value2