1# Lua {#lua} 2 3## Using Lua {#lua-userguide} 4 5### Overview of Lua {#lua-overview} 6 7Several versions of the Lua interpreter are available: luajit, lua 5.1, 5.2, 5.3. 8The attribute `lua` refers to the default interpreter, it is also possible to refer to specific versions, e.g. `lua5_2` refers to Lua 5.2. 9 10Lua libraries are in separate sets, with one set per interpreter version. 11 12The interpreters have several common attributes. One of these attributes is 13`pkgs`, which is a package set of Lua libraries for this specific 14interpreter. E.g., the `busted` package corresponding to the default interpreter 15is `lua.pkgs.busted`, and the lua 5.2 version is `lua5_2.pkgs.busted`. 16The main package set contains aliases to these package sets, e.g. 17`luaPackages` refers to `lua5_1.pkgs` and `lua52Packages` to 18`lua5_2.pkgs`. 19 20Note that nixpkgs patches the non-luajit interpreters to avoid referring to 21`/usr` and have `;;` (a [placeholder](https://www.lua.org/manual/5.1/manual.html#pdf-package.path) replaced with the default LUA_PATH) work correctly. 22 23### Installing Lua and packages {#installing-lua-and-packages} 24 25#### Lua environment defined in separate `.nix` file {#lua-environment-defined-in-separate-.nix-file} 26 27Create a file, e.g. `build.nix`, with the following expression 28 29```nix 30with import <nixpkgs> { }; 31 32lua5_2.withPackages ( 33 ps: with ps; [ 34 busted 35 luafilesystem 36 ] 37) 38``` 39 40and install it in your profile with 41 42```shell 43nix-env -if build.nix 44``` 45Now you can use the Lua interpreter, as well as the extra packages (`busted`, 46`luafilesystem`) that you added to the environment. 47 48#### Lua environment defined in `~/.config/nixpkgs/config.nix` {#lua-environment-defined-in-.confignixpkgsconfig.nix} 49 50If you prefer to, you could also add the environment as a package override to the Nixpkgs set, e.g. 51using `config.nix`, 52 53```nix 54{ 55 # ... 56 57 packageOverrides = 58 pkgs: with pkgs; { 59 myLuaEnv = lua5_2.withPackages ( 60 ps: with ps; [ 61 busted 62 luafilesystem 63 ] 64 ); 65 }; 66} 67``` 68 69and install it in your profile with 70 71```shell 72nix-env -iA nixpkgs.myLuaEnv 73``` 74The environment is installed by referring to the attribute, and considering 75the `nixpkgs` channel was used. 76 77#### Lua environment defined in `/etc/nixos/configuration.nix` {#lua-environment-defined-in-etcnixosconfiguration.nix} 78 79For the sake of completeness, here's another example how to install the environment system-wide. 80 81```nix 82{ 83 # ... 84 85 environment.systemPackages = with pkgs; [ 86 (lua.withPackages ( 87 ps: with ps; [ 88 busted 89 luafilesystem 90 ] 91 )) 92 ]; 93} 94``` 95 96### How to override a Lua package using overlays? {#how-to-override-a-lua-package-using-overlays} 97 98Use the following overlay template: 99 100```nix 101final: prev: { 102 103 lua = prev.lua.override { 104 packageOverrides = luaself: luaprev: { 105 106 luarocks-nix = luaprev.luarocks-nix.overrideAttrs (oa: { 107 pname = "luarocks-nix"; 108 src = /home/my_luarocks/repository; 109 }); 110 }; 111 }; 112 113 luaPackages = lua.pkgs; 114} 115``` 116 117### Temporary Lua environment with `nix-shell` {#temporary-lua-environment-with-nix-shell} 118 119 120There are two methods for loading a shell with Lua packages. The first and recommended method 121is to create an environment with `lua.buildEnv` or `lua.withPackages` and load that. E.g. 122 123```sh 124$ nix-shell -p 'lua.withPackages(ps: with ps; [ busted luafilesystem ])' 125``` 126 127opens a shell from which you can launch the interpreter 128 129```sh 130[nix-shell:~] lua 131``` 132 133The other method, which is not recommended, does not create an environment and requires you to list the packages directly, 134 135```sh 136$ nix-shell -p lua.pkgs.busted lua.pkgs.luafilesystem 137``` 138Again, it is possible to launch the interpreter from the shell. 139The Lua interpreter has the attribute `pkgs` which contains all Lua libraries for that specific interpreter. 140 141 142## Developing with lua {#lua-developing} 143 144Now that you know how to get a working Lua environment with Nix, it is time 145to go forward and start actually developing with Lua. There are two ways to 146package lua software, either it is on luarocks and most of it can be taken care 147of by the luarocks2nix converter or the packaging has to be done manually. 148Let's present the luarocks way first and the manual one in a second time. 149 150### Packaging a library on luarocks {#packaging-a-library-on-luarocks} 151 152[Luarocks.org](https://luarocks.org/) is the main repository of lua packages. 153The site proposes two types of packages, the `rockspec` and the `src.rock` 154(equivalent of a [rockspec](https://github.com/luarocks/luarocks/wiki/Rockspec-format) but with the source). 155 156Luarocks-based packages are generated in [pkgs/development/lua-modules/generated-packages.nix](https://github.com/NixOS/nixpkgs/tree/master/pkgs/development/lua-modules/generated-packages.nix) from 157the whitelist maintainers/scripts/luarocks-packages.csv and updated by running 158the package `luarocks-packages-updater`: 159 160```sh 161 162nix-shell -p luarocks-packages-updater --run luarocks-packages-updater 163``` 164 165[luarocks2nix](https://github.com/nix-community/luarocks) is a tool capable of generating nix derivations from both rockspec and src.rock (and favors the src.rock). 166The automation only goes so far though and some packages need to be customized. 167These customizations go in [pkgs/development/lua-modules/overrides.nix](https://github.com/NixOS/nixpkgs/tree/master/pkgs/development/lua-modules/overrides.nix). 168For instance if the rockspec defines `external_dependencies`, these need to be manually added to the overrides.nix. 169 170You can try converting luarocks packages to nix packages with the command `nix-shell -p luarocks-nix` and then `luarocks nix PKG_NAME`. 171 172#### Packaging a library manually {#packaging-a-library-manually} 173 174You can develop your package as you usually would, just don't forget to wrap it 175within a `toLuaModule` call, for instance 176 177```nix 178{ 179 mynewlib = toLuaModule ( 180 stdenv.mkDerivation { 181 # ... 182 } 183 ); 184} 185``` 186 187There is also the `buildLuaPackage` function that can be used when lua modules 188are not packaged for luarocks. You can see a few examples at `pkgs/top-level/lua-packages.nix`. 189 190## Lua Reference {#lua-reference} 191 192### Lua interpreters {#lua-interpreters} 193 194Versions 5.1, 5.2, 5.3 and 5.4 of the lua interpreter are available as 195respectively `lua5_1`, `lua5_2`, `lua5_3` and `lua5_4`. Luajit is available too. 196The Nix expressions for the interpreters can be found in `pkgs/development/interpreters/lua-5`. 197 198#### Attributes on lua interpreters packages {#attributes-on-lua-interpreters-packages} 199 200Each interpreter has the following attributes: 201 202- `interpreter`. Alias for `${pkgs.lua}/bin/lua`. 203- `buildEnv`. Function to build lua interpreter environments with extra packages bundled together. See section *lua.buildEnv function* for usage and documentation. 204- `withPackages`. Simpler interface to `buildEnv`. 205- `pkgs`. Set of Lua packages for that specific interpreter. The package set can be modified by overriding the interpreter and passing `packageOverrides`. 206 207#### `buildLuarocksPackage` function {#buildluarockspackage-function} 208 209The `buildLuarocksPackage` function is implemented in `pkgs/development/interpreters/lua-5/build-luarocks-package.nix` 210The following is an example: 211```nix 212{ 213 luaposix = buildLuarocksPackage { 214 pname = "luaposix"; 215 version = "34.0.4-1"; 216 217 src = fetchurl { 218 url = "https://raw.githubusercontent.com/rocks-moonscript-org/moonrocks-mirror/master/luaposix-34.0.4-1.src.rock"; 219 hash = "sha256-4mLJG8n4m6y4Fqd0meUDfsOb9RHSR0qa/KD5KCwrNXs="; 220 }; 221 disabled = (luaOlder "5.1") || (luaAtLeast "5.4"); 222 propagatedBuildInputs = [ 223 bit32 224 lua 225 std_normalize 226 ]; 227 228 meta = { 229 homepage = "https://github.com/luaposix/luaposix/"; 230 description = "Lua bindings for POSIX"; 231 maintainers = with lib.maintainers; [ 232 vyp 233 lblasc 234 ]; 235 license.fullName = "MIT/X11"; 236 }; 237 }; 238} 239``` 240 241The `buildLuarocksPackage` delegates most tasks to luarocks: 242 243* it adds `luarocks` as an unpacker for `src.rock` files (zip files really). 244* `configurePhase` writes a temporary luarocks configuration file which location 245is exported via the environment variable `LUAROCKS_CONFIG`. 246* the `buildPhase` does nothing. 247* `installPhase` calls `luarocks make --deps-mode=none --tree $out` to build and 248install the package 249* In the `postFixup` phase, the `wrapLuaPrograms` bash function is called to 250 wrap all programs in the `$out/bin/*` directory to include `$PATH` 251 environment variable and add dependent libraries to script's `LUA_PATH` and 252 `LUA_CPATH`. 253 254It accepts as arguments: 255 256* 'luarocksConfig': a nix value that directly maps to the luarocks config used during 257 the installation 258 259By default `meta.platforms` is set to the same value as the interpreter unless overridden otherwise. 260 261#### `buildLuaApplication` function {#buildluaapplication-function} 262 263The `buildLuaApplication` function is practically the same as `buildLuaPackage`. 264The difference is that `buildLuaPackage` by default prefixes the names of the packages with the version of the interpreter. 265Because with an application we're not interested in multiple version the prefix is dropped. 266 267#### lua.withPackages function {#lua.withpackages-function} 268 269The `lua.withPackages` takes a function as an argument that is passed the set of lua packages and returns the list of packages to be included in the environment. 270Using the `withPackages` function, the previous example for the luafilesystem environment can be written like this: 271 272```nix 273lua.withPackages (ps: [ ps.luafilesystem ]) 274``` 275 276`withPackages` passes the correct package set for the specific interpreter version as an argument to the function. In the above example, `ps` equals `luaPackages`. 277But you can also easily switch to using `lua5_1`: 278 279```nix 280lua5_1.withPackages (ps: [ ps.lua ]) 281``` 282 283Now, `ps` is set to `lua5_1.pkgs`, matching the version of the interpreter. 284 285### Lua Contributing guidelines {#lua-contributing} 286 287Following rules should be respected: 288 289* Commit names of Lua libraries should reflect that they are Lua libraries, so write for example `luaPackages.luafilesystem: 1.11 -> 1.12`.