Writing a package in Julia

Nov 3, 2021

In tandem with one of my projects, I wrote a Julia package implementing its central solution methods. This undertaking was the first time I wrote a Julia package (the larger project itself the first time I really used Julia).

Since I had never written a package in Julia (or indeed in any other language), it was a learning experience — especially for the under-the-hood processes with which software engineers are undoubtedly familiar: wrangling workflows; git and version control; packages and dependencies; documenting and testing. While I learned a lot, I will focus only on the mechanics of starting and developing a Julia package here. (Maybe more to come on the other topics later!)

A package is functionally no different from any code project in the sense that it just runs code. Conceptually, packages tend to be centred around building and making available a core set of functionalities to use repeatedly — hopefully for yourself, your collaborators, or even strangers trying to solve similar problems. For this reason, code for a package should be written in Julia modules, exporting only the key functionalities for general use.

For brevity, I'll first list the basic steps to get a new package going, then discuss them in more detail.

  1. Open Julia, enter Pkg mode (by typing ]).
  2. Initiate your package, say "NewPackage", by typing generate NewPackage. Doing so will create a NewPackage folder in the current working directory.
  3. Create a git repository at some online host like GitHub, probably called NewPackage.jl, and push the contents of the NewPackage folder.
  4. NewPackage can now be added to Julia's default environment — tell Julia about it by typing something like add https://github.com/your_username/NewPackage.jl in Pkg mode. Julia now knows to get NewPackage from the online git repository.
  5. We probably want to make changes to NewPackage locally before publishing them online. In Pkg mode, type dev NewPackage. Julia will copy the package files for local development (usually somewhere like ~/.julia/dev/NewPackage), then tell the default environment to load NewPackage from this local version rather than the version hosted online.
  6. We now have two local versions on the package: one we created with generate and one we created with dev. At this point, the first serves no purpose (it isn't being watched by Julia, for example) so we can delete it. I personally created a symbolic link from this location to the local development copy, since the original location was more convenient for my file management purposes.
  7. Now, we can make any changes we want to the local copy. To incorporate the changes, update the package by typing something like up NewPackage in Pkg mode, then restart Julia. When satisfied with changes, commit and push them so they can be available for everyone from the online hosted location.

The process above is a bit convoluted. For me, the multiple copies (created with generate and dev) were very confusing. I am not sure if there is a way to get the balling rolling in a more efficient way in Julia, or if it's standard with other languages to create multiple local copies of a project during the initiation process.

I'll close with a few final comments on the practicalities of package development.

send a comment