php.buildEnv: Provide a list of currently enabled extensions
Rework withExtensions / buildEnv to handle currently enabled extensions better and make them compatible with override. They now accept a function with the named arguments enabled and all, where enabled is a list of currently enabled extensions and all is the set of all extensions. This gives us several nice properties: - You always get the right version of the list of currently enabled extensions - Invocations chain - It works well with overridden PHP packages - you always get the correct versions of extensions As a contrived example of what's possible, you can add ImageMagick, then override the version and disable fpm, then disable cgi, and lastly remove the zip extension like this: { pkgs ? (import <nixpkgs>) {} }: with pkgs; let phpWithImagick = php74.withExtensions ({ all, enabled }: enabled ++ [ all.imagick ]); phpWithImagickWithoutFpm743 = phpWithImagick.override { version = "7.4.3"; sha256 = "wVF7pJV4+y3MZMc6Ptx21PxQfEp6xjmYFYTMfTtMbRQ="; fpmSupport = false; }; phpWithImagickWithoutFpmZip743 = phpWithImagickWithoutFpm743.withExtensions ( { enabled, all }: lib.filter (e: e != all.zip) enabled); phpWithImagickWithoutFpmZipCgi743 = phpWithImagickWithoutFpmZip743.override { cgiSupport = false; }; in phpWithImagickWithoutFpmZipCgi743
This commit is contained in:
parent
abedfadd73
commit
2ba7926959
5 changed files with 68 additions and 47 deletions
|
@ -30,7 +30,7 @@ opcache extension shipped with PHP is available at
|
|||
`php.extensions.opcache` and the third-party ImageMagick extension at
|
||||
`php.extensions.imagick`.
|
||||
|
||||
The different versions of PHP that nixpkgs provides is located under
|
||||
The different versions of PHP that nixpkgs provides are located under
|
||||
attributes named based on major and minor version number; e.g.,
|
||||
`php74` is PHP 7.4 with commonly used extensions installed,
|
||||
`php74base` is the same PHP runtime without extensions.
|
||||
|
@ -39,28 +39,31 @@ attributes named based on major and minor version number; e.g.,
|
|||
|
||||
A PHP package with specific extensions enabled can be built using
|
||||
`php.withExtensions`. This is a function which accepts an anonymous
|
||||
function as its only argument; the function should take one argument,
|
||||
the set of all extensions, and return a list of wanted extensions. For
|
||||
example, a PHP package with the opcache and ImageMagick extensions
|
||||
enabled:
|
||||
function as its only argument; the function should accept two named
|
||||
parameters: `enabled` - a list of currently enabled extensions and
|
||||
`all` - the set of all extensions, and return a list of wanted
|
||||
extensions. For example, a PHP package with all default extensions and
|
||||
ImageMagick enabled:
|
||||
|
||||
```nix
|
||||
php.withExtensions (e: with e; [ imagick opcache ])
|
||||
php.withExtensions ({ enabled, all }:
|
||||
enabled ++ [ all.imagick ])
|
||||
```
|
||||
|
||||
Note that this will give you a package with _only_ opcache and
|
||||
ImageMagick, none of the other extensions which are enabled by default
|
||||
in the `php` package will be available.
|
||||
|
||||
To enable building on a previous PHP package, the currently enabled
|
||||
extensions are made available in its `enabledExtensions`
|
||||
attribute. For example, to generate a package with all default
|
||||
extensions enabled, except opcache, but with ImageMagick:
|
||||
To exclude some, but not all, of the default extensions, you can
|
||||
filter the `enabled` list like this:
|
||||
|
||||
```nix
|
||||
php.withExtensions (e:
|
||||
(lib.filter (e: e != php.extensions.opcache) php.enabledExtensions)
|
||||
++ [ e.imagick ])
|
||||
php.withExtensions ({ enabled, all }:
|
||||
(lib.filter (e: e != php.extensions.opcache) enabled)
|
||||
++ [ all.imagick ])
|
||||
```
|
||||
|
||||
To build your list of extensions from the ground up, you can simply
|
||||
ignore `enabled`:
|
||||
|
||||
```nix
|
||||
php.withExtensions ({ all, ... }: with all; [ opcache imagick ])
|
||||
```
|
||||
|
||||
If you want a PHP build with extra configuration in the `php.ini`
|
||||
|
@ -73,7 +76,7 @@ and ImageMagick extensions enabled, and `memory_limit` set to `256M`:
|
|||
|
||||
```nix
|
||||
php.buildEnv {
|
||||
extensions = e: with e; [ imagick opcache ];
|
||||
extensions = { all, ... }: with all; [ imagick opcache ];
|
||||
extraConfig = "memory_limit=256M";
|
||||
}
|
||||
```
|
||||
|
@ -85,7 +88,7 @@ follows:
|
|||
|
||||
```nix
|
||||
let
|
||||
myPhp = php.withExtensions (e: with e; [ imagick opcache ]);
|
||||
myPhp = php.withExtensions ({ all, ... }: with all; [ opcache imagick ]);
|
||||
in {
|
||||
services.phpfpm.pools."foo".phpPackage = myPhp;
|
||||
};
|
||||
|
@ -94,7 +97,7 @@ in {
|
|||
```nix
|
||||
let
|
||||
myPhp = php.buildEnv {
|
||||
extensions = e: with e; [ imagick opcache ];
|
||||
extensions = { all, ... }: with all; [ imagick opcache ];
|
||||
extraConfig = "memory_limit=256M";
|
||||
};
|
||||
in {
|
||||
|
@ -105,8 +108,8 @@ in {
|
|||
##### Example usage with `nix-shell`
|
||||
|
||||
This brings up a temporary environment that contains a PHP interpreter
|
||||
with the extensions `imagick` and `opcache` enabled.
|
||||
with the extensions `imagick` and `opcache` enabled:
|
||||
|
||||
```sh
|
||||
nix-shell -p 'php.buildEnv { extensions = e: with e; [ imagick opcache ]; }'
|
||||
nix-shell -p 'php.withExtensions ({ all, ... }: with all; [ imagick opcache ])'
|
||||
```
|
||||
|
|
|
@ -135,18 +135,23 @@
|
|||
</listitem>
|
||||
<listitem>
|
||||
<para>
|
||||
Since this release there's an easy way to customize your PHP install to get a much smaller
|
||||
base PHP with only wanted extensions enabled. See the following snippet installing a smaller PHP
|
||||
with the extensions <literal>imagick</literal>, <literal>opcache</literal> and
|
||||
Since this release there's an easy way to customize your PHP
|
||||
install to get a much smaller base PHP with only wanted
|
||||
extensions enabled. See the following snippet installing a
|
||||
smaller PHP with the extensions <literal>imagick</literal>,
|
||||
<literal>opcache</literal>, <literal>pdo</literal> and
|
||||
<literal>pdo_mysql</literal> loaded:
|
||||
|
||||
<programlisting>
|
||||
environment.systemPackages = [
|
||||
(pkgs.php.buildEnv { extensions = pp: with pp; [
|
||||
imagick
|
||||
opcache
|
||||
pdo_mysql
|
||||
]; })
|
||||
(pkgs.php.withExtensions
|
||||
({ all, ... }: with all; [
|
||||
imagick
|
||||
opcache
|
||||
pdo
|
||||
pdo_mysql
|
||||
])
|
||||
)
|
||||
];</programlisting>
|
||||
|
||||
The default <literal>php</literal> attribute hasn't lost any extensions -
|
||||
|
|
|
@ -7,7 +7,7 @@ let
|
|||
fpm = config.services.phpfpm.pools.roundcube;
|
||||
localDB = cfg.database.host == "localhost";
|
||||
user = cfg.database.username;
|
||||
phpWithPspell = pkgs.php.withExtensions (e: [ e.pspell ] ++ pkgs.php.enabledExtensions);
|
||||
phpWithPspell = pkgs.php.withExtensions ({ enabled, all }: [ all.pspell ] ++ enabled);
|
||||
in
|
||||
{
|
||||
options.services.roundcube = {
|
||||
|
|
|
@ -11,8 +11,8 @@ let
|
|||
base = pkgs.php74;
|
||||
in
|
||||
base.buildEnv {
|
||||
extensions = e: with e;
|
||||
base.enabledExtensions ++ [
|
||||
extensions = { enabled, all }: with all;
|
||||
enabled ++ [
|
||||
apcu redis memcached imagick
|
||||
];
|
||||
extraConfig = phpOptionsStr;
|
||||
|
|
|
@ -43,8 +43,16 @@ let
|
|||
phpWithExtensions = self.withExtensions defaultPhpExtensions;
|
||||
});
|
||||
|
||||
mkBuildEnv = prevArgs: lib.makeOverridable (
|
||||
{ extensions ? (_: []), extraConfig ? "", ... }@innerArgs:
|
||||
# buildEnv wraps php to provide additional extensions and
|
||||
# configuration. Its usage is documented in
|
||||
# doc/languages-frameworks/php.section.md.
|
||||
#
|
||||
# Create a buildEnv with earlier overridden values and
|
||||
# extensions functions in its closure. This is necessary for
|
||||
# consecutive calls to buildEnv and overrides to work as
|
||||
# expected.
|
||||
mkBuildEnv = prevArgs: prevExtensionFunctions: lib.makeOverridable (
|
||||
{ extensions ? ({...}: []), extraConfig ? "", ... }@innerArgs:
|
||||
let
|
||||
allArgs = args // prevArgs // innerArgs;
|
||||
filteredArgs = builtins.removeAttrs allArgs [ "extensions" "extraConfig" ];
|
||||
|
@ -54,8 +62,15 @@ let
|
|||
inherit php phpWithExtensions;
|
||||
});
|
||||
|
||||
allExtensionFunctions = prevExtensionFunctions ++ [ extensions ];
|
||||
enabledExtensions =
|
||||
builtins.foldl'
|
||||
(state: f:
|
||||
f { enabled = state; all = php-packages.extensions; })
|
||||
[]
|
||||
allExtensionFunctions;
|
||||
|
||||
getExtName = ext: lib.removePrefix "php-" (builtins.parseDrvName ext.name).name;
|
||||
enabledExtensions = extensions php-packages.extensions;
|
||||
|
||||
# Generate extension load configuration snippets from the
|
||||
# extension parameter. This is an attrset suitable for use
|
||||
|
@ -89,9 +104,8 @@ let
|
|||
inherit (php) version;
|
||||
nativeBuildInputs = [ makeWrapper ];
|
||||
passthru = {
|
||||
buildEnv = mkBuildEnv allArgs;
|
||||
withExtensions = mkWithExtensions allArgs;
|
||||
inherit enabledExtensions;
|
||||
buildEnv = mkBuildEnv allArgs allExtensionFunctions;
|
||||
withExtensions = mkWithExtensions allArgs allExtensionFunctions;
|
||||
inherit (php-packages) packages extensions;
|
||||
};
|
||||
paths = [ php ];
|
||||
|
@ -108,8 +122,8 @@ let
|
|||
in
|
||||
phpWithExtensions);
|
||||
|
||||
mkWithExtensions = prevArgs: extensions:
|
||||
mkBuildEnv prevArgs { inherit extensions; };
|
||||
mkWithExtensions = prevArgs: prevExtensionFunctions: extensions:
|
||||
mkBuildEnv prevArgs prevExtensionFunctions { inherit extensions; };
|
||||
|
||||
pcre' = if (lib.versionAtLeast version "7.3") then pcre2 else pcre;
|
||||
in
|
||||
|
@ -218,9 +232,8 @@ let
|
|||
outputs = [ "out" "dev" ];
|
||||
|
||||
passthru = {
|
||||
enabledExtensions = [];
|
||||
buildEnv = mkBuildEnv {};
|
||||
withExtensions = mkWithExtensions {};
|
||||
buildEnv = mkBuildEnv {} [];
|
||||
withExtensions = mkWithExtensions {} [];
|
||||
inherit (php-packages) packages extensions;
|
||||
};
|
||||
|
||||
|
@ -258,7 +271,7 @@ let
|
|||
inherit defaultPhpExtensions;
|
||||
});
|
||||
|
||||
defaultPhpExtensions = extensions: with extensions; ([
|
||||
defaultPhpExtensions = { all, ... }: with all; ([
|
||||
bcmath calendar curl ctype dom exif fileinfo filter ftp gd
|
||||
gettext gmp iconv intl json ldap mbstring mysqli mysqlnd opcache
|
||||
openssl pcntl pdo pdo_mysql pdo_odbc pdo_pgsql pdo_sqlite pgsql
|
||||
|
@ -266,8 +279,8 @@ let
|
|||
tokenizer xmlreader xmlwriter zip zlib
|
||||
] ++ lib.optionals (!stdenv.isDarwin) [ imap ]);
|
||||
|
||||
defaultPhpExtensionsWithHash = extensions:
|
||||
(defaultPhpExtensions extensions) ++ [ extensions.hash ];
|
||||
defaultPhpExtensionsWithHash = { all, ... }:
|
||||
(defaultPhpExtensions { inherit all; }) ++ [ all.hash ];
|
||||
|
||||
php74 = php74base.withExtensions defaultPhpExtensions;
|
||||
php73 = php73base.withExtensions defaultPhpExtensionsWithHash;
|
||||
|
|
Loading…
Reference in a new issue