Hi everyone,
I put together a template for pure Roc packages:
https://github.com/ageron/roc-package-template
It sets up a standard directory structure, basic module exports, tests, and CI/release workflows out of the box so you don’t have to wire up boilerplate every time you want to build a new package. You may also find it useful for your existing packages, to get extra workflows and tools.
Hope it saves people some time! Feedback and PRs are very welcome.
This repo reuses components from various other packages: roc-lang/unicode, roc-lang/http, imclerran/roc-isodate, lukewilliamboswell/roc-parser, and kili-ilo/roc-random.
Why not put the Roc files in src/ just like any other language? It's shorter to type for CLI users, and its also in muscle memory for developers who use other languages too.
Good question, I just followed the existing convention. I'm not sure what the original rationale was. It's package for packages, platform for platforms. For platforms, since there are two languages (Roc + host language), maybe it helps to separate out the Roc code in the platform directory, the host code in src? It might allow the Rust/Zig build tools to work out of the box without tweaks. For pure Roc packages, perhaps src would work just as well. But maybe you can have a project containing a platform and a pure Roc package? I'm not sure...
I tried it a few different ways, and I found the convention of using platform/main.roc package/main.roc to be clearer that src/main.roc
My thoughts were at a glance of the top-level directories this gives you more information about what is inside
Host code in src/ makes sense as a contrast to platform/
The alternative would be to keep src/ for either Roc package code or platform host code, and keep platform/ for Roc glue. The upside is Roc does not "yield" src/ to other languages, the downside is you don't know whether src/ contains code in Roc or some other language without knowing whether you look at a platform or a package. This downside is arguably not that significant.
@Luke Boswell would package/main.roc also be used for a program? Or just for a package in the meaning of a library?
would
package/main.rocalso be used for a program?
No, just for packages.
@Aurélien Geron I noticed you did not use roc-lang/release-package, was that a deliberate choice?
Ah no, not deliberate, just ignorance! :sweat_smile:
I just updated the template to use roc-lang/release-package. Thanks @Anton
I think there's value in having a template, to make it easier to create a new package. However, perhaps some of the features I've included in the template could be extracted to a separate project (similar to roc-lang/release-package), such as the compiler-update workflow: this way, updating the workflow would only need to be done in one place, rather than in every package based on the template. Wdyt?
Yeah, feel free to experiment, we can move it under the roc-lang org later if you want that.
I tried to use the template to make my own package but I get the following error on github. My formatting is correct and the all_test.sh script seems to work fine when I run it locally. Any idea on how to fix that ?
Run ./scripts/all_tests.sh
./scripts/all_tests.sh
shell: C:\Program Files\Git\bin\bash.EXE --noprofile --norc -e -o pipefail {0}
Roc compiler version nightly-2026-10-06-c34079d
The following file(s) failed `roc fmt --check`: package\Constants.roc
package\main.roc
examples\getting-started.roc
You can fix this with `roc fmt FILENAME.roc`.Took 1.7 ms.
Error: Process completed with exit code 1.
Do you happen to be running a different version of Roc locally?
Locally I use nightly-2026-10-09-258ab27
On github you are using nightly-2026-10-06-c34079d and I know there were some changes to the formatting recently so I would recommend changing your github workflow to use nightly-2026-10-09-258ab27 as well.
Last updated: Oct 15 2026 at 17:56 UTC