1<chapter xmlns="http://docbook.org/ns/docbook"
2 xmlns:xlink="http://www.w3.org/1999/xlink"
3 xml:id="chap-functions">
4
5<title>Functions reference</title>
6
7<para>
8 The nixpkgs repository has several utility functions to manipulate Nix expressions.
9</para>
10
11<section xml:id="sec-pkgs-overridePackages">
12 <title>pkgs.overridePackages</title>
13
14 <para>
15 This function inside the nixpkgs expression (<varname>pkgs</varname>)
16 can be used to override the set of packages itself.
17 </para>
18 <para>
19 Warning: this function is expensive and must not be used from within
20 the nixpkgs repository.
21 </para>
22 <para>
23 Example usage:
24
25 <programlisting>let
26 pkgs = import <nixpkgs> {};
27 newpkgs = pkgs.overridePackages (self: super: {
28 foo = super.foo.override { ... };
29 };
30in ...</programlisting>
31 </para>
32
33 <para>
34 The resulting <varname>newpkgs</varname> will have the new <varname>foo</varname>
35 expression, and all other expressions depending on <varname>foo</varname> will also
36 use the new <varname>foo</varname> expression.
37 </para>
38
39 <para>
40 The behavior of this function is similar to <link
41 linkend="sec-modify-via-packageOverrides">config.packageOverrides</link>.
42 </para>
43
44 <para>
45 The <varname>self</varname> parameter refers to the final package set with the
46 applied overrides. Using this parameter may lead to infinite recursion if not
47 used consciously.
48 </para>
49
50 <para>
51 The <varname>super</varname> parameter refers to the old package set.
52 It's equivalent to <varname>pkgs</varname> in the above example.
53 </para>
54
55</section>
56
57<section xml:id="sec-pkg-override">
58 <title><pkg>.override</title>
59
60 <para>
61 The function <varname>override</varname> is usually available for all the
62 derivations in the nixpkgs expression (<varname>pkgs</varname>).
63 </para>
64 <para>
65 It is used to override the arguments passed to a function.
66 </para>
67 <para>
68 Example usages:
69
70 <programlisting>pkgs.foo.override { arg1 = val1; arg2 = val2; ... }</programlisting>
71 <programlisting>pkgs.overridePackages (self: super: {
72 foo = super.foo.override { barSupport = true ; };
73})</programlisting>
74 <programlisting>mypkg = pkgs.callPackage ./mypkg.nix {
75 mydep = pkgs.mydep.override { ... };
76})</programlisting>
77 </para>
78
79 <para>
80 In the first example, <varname>pkgs.foo</varname> is the result of a function call
81 with some default arguments, usually a derivation.
82 Using <varname>pkgs.foo.override</varname> will call the same function with
83 the given new arguments.
84 </para>
85
86</section>
87
88<section xml:id="sec-pkg-overrideDerivation">
89 <title><pkg>.overrideDerivation</title>
90
91 <para>
92 The function <varname>overrideDerivation</varname> is usually available for all the
93 derivations in the nixpkgs expression (<varname>pkgs</varname>).
94 </para>
95 <para>
96 It is used to create a new derivation by overriding the attributes of
97 the original derivation according to the given function.
98 </para>
99
100 <para>
101 Example usage:
102
103 <programlisting>mySed = pkgs.gnused.overrideDerivation (oldAttrs: {
104 name = "sed-4.2.2-pre";
105 src = fetchurl {
106 url = ftp://alpha.gnu.org/gnu/sed/sed-4.2.2-pre.tar.bz2;
107 sha256 = "11nq06d131y4wmf3drm0yk502d2xc6n5qy82cg88rb9nqd2lj41k";
108 };
109 patches = [];
110});</programlisting>
111 </para>
112
113 <para>
114 In the above example, the name, src and patches of the derivation
115 will be overridden, while all other attributes will be retained from the
116 original derivation.
117 </para>
118
119 <para>
120 The argument <varname>oldAttrs</varname> is used to refer to the attribute set of
121 the original derivation.
122 </para>
123
124</section>
125
126<section xml:id="sec-lib-makeOverridable">
127 <title>lib.makeOverridable</title>
128
129 <para>
130 The function <varname>lib.makeOverridable</varname> is used to make the result
131 of a function easily customizable. This utility only makes sense for functions
132 that accept an argument set and return an attribute set.
133 </para>
134
135 <para>
136 Example usage:
137
138 <programlisting>f = { a, b }: { result = a+b; }
139c = lib.makeOverridable f { a = 1; b = 2; }</programlisting>
140
141 </para>
142
143 <para>
144 The variable <varname>c</varname> is the value of the <varname>f</varname> function
145 applied with some default arguments. Hence the value of <varname>c.result</varname>
146 is <literal>3</literal>, in this example.
147 </para>
148
149 <para>
150 The variable <varname>c</varname> however also has some additional functions, like
151 <link linkend="sec-pkg-override">c.override</link> which can be used to
152 override the default arguments. In this example the value of
153 <varname>(c.override { a = 4; }).result</varname> is 6.
154 </para>
155
156</section>
157
158
159<section xml:id="sec-fhs-environments">
160 <title>buildFHSChrootEnv/buildFHSUserEnv</title>
161
162 <para>
163 <function>buildFHSChrootEnv</function> and
164 <function>buildFHSUserEnv</function> provide a way to build and run
165 FHS-compatible lightweight sandboxes. They get their own isolated root with
166 binded <filename>/nix/store</filename>, so their footprint in terms of disk
167 space needed is quite small. This allows one to run software which is hard or
168 unfeasible to patch for NixOS -- 3rd-party source trees with FHS assumptions,
169 games distributed as tarballs, software with integrity checking and/or external
170 self-updated binaries.
171 </para>
172
173 <para>
174 <function>buildFHSChrootEnv</function> allows to create persistent
175 environments, which can be constructed, deconstructed and entered by
176 multiple users at once. A downside is that it requires
177 <literal>root</literal> access for both those who create and destroy and
178 those who enter it. It can be useful to create environments for daemons that
179 one can enter and observe.
180 </para>
181
182 <para>
183 <function>buildFHSUserEnv</function> uses Linux namespaces feature to create
184 temporary lightweight environments which are destroyed after all child
185 processes exit. It does not require root access, and can be useful to create
186 sandboxes and wrap applications.
187 </para>
188
189 <para>
190 Those functions both rely on <function>buildFHSEnv</function>, which creates
191 an actual directory structure given a list of necessary packages and extra
192 build commands.
193 <function>buildFHSChrootEnv</function> and <function>buildFHSUserEnv</function>
194 both accept those arguments which are passed to
195 <function>buildFHSEnv</function>:
196 </para>
197
198 <variablelist>
199 <varlistentry>
200 <term><literal>name</literal></term>
201
202 <listitem><para>Environment name.</para></listitem>
203 </varlistentry>
204
205 <varlistentry>
206 <term><literal>targetPkgs</literal></term>
207
208 <listitem><para>Packages to be installed for the main host's architecture
209 (i.e. x86_64 on x86_64 installations).</para></listitem>
210 </varlistentry>
211
212 <varlistentry>
213 <term><literal>multiPkgs</literal></term>
214
215 <listitem><para>Packages to be installed for all architectures supported by
216 a host (i.e. i686 and x86_64 on x86_64 installations).</para></listitem>
217 </varlistentry>
218
219 <varlistentry>
220 <term><literal>extraBuildCommands</literal></term>
221
222 <listitem><para>Additional commands to be executed for finalizing the
223 directory structure.</para></listitem>
224 </varlistentry>
225
226 <varlistentry>
227 <term><literal>extraBuildCommandsMulti</literal></term>
228
229 <listitem><para>Like <literal>extraBuildCommandsMulti</literal>, but
230 executed only on multilib architectures.</para></listitem>
231 </varlistentry>
232 </variablelist>
233
234 <para>
235 Additionally, <function>buildFHSUserEnv</function> accepts
236 <literal>runScript</literal> parameter, which is a command that would be
237 executed inside the sandbox and passed all the command line arguments. It
238 default to <literal>bash</literal>.
239 </para>
240 <para>
241 It also uses <literal>CHROOTENV_EXTRA_BINDS</literal> environment variable
242 for binding extra directories in the sandbox to outside places. The format of
243 the variable is <literal>/mnt=test-mnt:/data</literal>, where
244 <literal>/mnt</literal> would be mounted as <literal>/test-mnt</literal>
245 and <literal>/data</literal> would be mounted as <literal>/data</literal>.
246 <literal>extraBindMounts</literal> array argument to
247 <function>buildFHSUserEnv</function> function is prepended to this variable.
248 Latter entries take priority if defined several times -- i.e. in case of
249 <literal>/data=data1:/data=data2</literal> the actual bind path would be
250 <literal>/data2</literal>.
251 </para>
252 <para>
253 One can create a simple environment using a <literal>shell.nix</literal>
254 like that:
255 </para>
256
257<programlisting><![CDATA[
258{ pkgs ? import <nixpkgs> {} }:
259
260(pkgs.buildFHSUserEnv {
261 name = "simple-x11-env";
262 targetPkgs = pkgs: (with pkgs;
263 [ udev
264 alsaLib
265 ]) ++ (with pkgs.xorg;
266 [ libX11
267 libXcursor
268 libXrandr
269 ]);
270 multiPkgs = pkgs: (with pkgs;
271 [ udev
272 alsaLib
273 ]) ++ (with [];
274 runScript = "bash";
275}).env
276]]></programlisting>
277
278 <para>
279 Running <literal>nix-shell</literal> would then drop you into a shell with
280 these libraries and binaries available. You can use this to run
281 closed-source applications which expect FHS structure without hassles:
282 simply change <literal>runScript</literal> to the application path,
283 e.g. <filename>./bin/start.sh</filename> -- relative paths are supported.
284 </para>
285</section>
286
287</chapter>