Skip to content

Instantly share code, notes, and snippets.

@gustavderdrache
Created December 10, 2019 17:30
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save gustavderdrache/d289ce47cffa0dfe12b289469afbdb48 to your computer and use it in GitHub Desktop.
Save gustavderdrache/d289ce47cffa0dfe12b289469afbdb48 to your computer and use it in GitHub Desktop.

Example usage:

{ pkgs ? import <nixpkgs> {} }:
let
  php = import ./default.nix { pkgs = pkgs; };
in
php.withExtensions [ "opcache" "ldap" "gmp" ]
{ pkgs ? import <nixpkgs> {} }:
let
inherit (pkgs) pkgconfig stdenv;
common = import ./common.nix { pkgs = pkgs; };
php = import ./php.nix { pkgs = pkgs; };
extensionName = name: builtins.substring 4 (builtins.stringLength name) name;
mkExtension =
{ name
, buildInputs ? []
, configureFlags ? "--enable-${name}"
}:
assert builtins.isList buildInputs;
assert builtins.isString configureFlags;
assert builtins.isString name;
stdenv.mkDerivation {
name = "php-${name}";
src = common.src;
sourceRoot = "php-${common.version}/ext/${name}";
buildInputs = [ php pkgs.autoconf pkgs.pkg-config ] ++ buildInputs;
configureFlags = configureFlags;
enableParallelBuilding = true;
preConfigure = ''
phpize
'';
setupHooks = pkgconfig.setupHook;
installPhase = ''
mkdir -p $out/lib
cp modules/${name}.so $out/lib/
'';
};
extensionData =
with (pkgs);
[
{
name = "bcmath";
}
{
name = "bz2";
buildInputs = [ bzip2 ];
configureFlags = "--with-bz2=${bzip2.dev}";
}
{
name = "calendar";
}
{
name = "ctype";
}
{
name = "curl";
buildInputs = [ curl ];
configureFlags = "--with-curl=${curl.dev}";
}
{
name = "dom";
buildInputs = [ libxml2 ];
configureFlags = "--enable-dom CFLAGS=-I../..";
}
{
name = "enchant";
buildInputs = [ enchant1 ];
configureFlags = "--with-enchant=${enchant1}";
}
{
name = "exif";
}
{
name = "ffi";
buildInputs = [ libffi pkg-config ];
configureFlags = "--with-ffi=${libffi.dev}";
}
{
name = "fileinfo";
}
{
name = "filter";
}
{
name = "ftp";
}
{
name = "gd";
buildInputs = [ zlib libpng libjpeg freetype ];
configureFlags = "--enable-gd --with-jpeg --with-freetype";
}
# XXX: Needs intl patch
# {
# name = "gettext";
# buildInputs = [gettext libintl];
# configureFlags = "--with-gettext=${gettext}";
# }
{
name = "gmp";
buildInputs = [ gmp5 ];
configureFlags = "--with-gmp=${gmp5.dev}";
}
{
name = "iconv";
configureFlags = "--with-iconv";
}
{
name = "imap";
buildInputs = [ openssl.dev uwimap pam ];
# Fix weird openssl detection
configureFlags = "--with-imap=${uwimap} --with-imap-ssl PHP_OPENSSL=yes";
}
# XXX: Needs intl patch
# {
# name = "intl";
# buildInputs = [libintl];
# }
{
name = "json";
}
{
name = "ldap";
buildInputs = [ openldap cyrus_sasl ];
configureFlags = "--with-ldap=lol --with-ldap-sasl=${cyrus_sasl.dev} LDAP_DIR=${openldap.dev} LDAP_INCDIR=${openldap.dev}/include LDAP_LIBDIR=${openldap}/lib";
}
{
name = "mbstring";
buildInputs = [ oniguruma ];
}
# XXX:
# {
# name = "mysqli";
# # XXX needed?
# buildInputs = [mysql];
# configureFlags = "--with-mysqli";
# }
{
name = "opcache";
}
{
name = "pcntl";
}
{
name = "pdo";
}
{
name = "phar";
}
{
name = "posix";
}
{
name = "pspell";
buildInputs = [aspell];
configureFlags = "--with-pspell=${aspell}";
}
{
name = "session";
}
{
name = "shmop";
}
{
name = "simplexml";
buildInputs = [libxml2];
configureFlags = "--enable-simplexml CFLAGS=-I../..";
}
{
name = "soap";
buildInputs = [libxml2];
configureFlags = "--enable-soap CFLAGS=-I../..";
}
{
name = "sockets";
}
{
name = "sodium";
buildInputs = [libsodium];
configureFlags = "--with-sodium=${libsodium}";
}
{
name = "sysvmsg";
}
{
name = "sysvsem";
}
{
name = "sysvshm";
}
{
name = "tidy";
buildInputs = [libtidy];
configureFlags = "--with-tidy=${libtidy}";
}
{
name = "tokenizer";
}
{
name = "xml";
buildInputs = [expat libxml2];
configureFlags = "--enable-xml --with-expat-dir=${expat.dev} CFLAGS=-I../..";
}
{
name = "xmlreader";
buildInputs = [libxml2];
configureFlags = "--enable-xmlreader CFLAGS=-I../..";
}
# XXX missing some other buildInput
# {
# name = "xmlrpc";
# buildInputs = [expat libxml2];
# configureFlags = "--with-xmlrpc --with-expat-dir=${expat.dev} CFLAGS=-I../..";
# }
{
name = "xmlwriter";
buildInputs = [libxml2];
configureFlags = "--enable-xmlwriter CFLAGS=-I../..";
}
# XXX may need to phpize the dom extension
# {
# name = "xsl";
# buildInputs = [libxml2 libxslt];
# configureFlags = "--with-xsl=${libxslt.dev} CFLAGS=-I../..";
# }
{
name = "zip";
buildInputs = [libzip];
configureFlags = "--enable-zip --with-libzip=${libzip.dev}";
}
];
extensions = builtins.map mkExtension extensionData;
namedExtensions = builtins.map (drv: { name = drv.name; value = drv; }) extensions;
in
builtins.listToAttrs namedExtensions
{ pkgs ? import <nixpkgs> {} }:
let
inherit (pkgs) fetchurl;
version = "7.4.0";
src = fetchurl {
url = "https://www.php.net/distributions/php-${version}.tar.gz";
sha256 = "004a1a8176176ee1b5c112e73d705977507803f425f9e48cb4a84f42b22abf22";
};
disableAllSapis = "--disable-cgi --disable-phpdbg";
disableAllExtensions = "--disable-all";
configureFlags = "${disableAllSapis} ${disableAllExtensions}";
in
{
src = src;
disableAllSapis = disableAllSapis;
disableAllExtensions = disableAllExtensions;
configureFlags = configureFlags;
version = version;
}
{ pkgs ? import <nixpkgs> {} }:
let
php = import ./php.nix { pkgs = pkgs; };
exts = import ./builtins.nix { pkgs = pkgs; };
withExtensions = names:
let
inherit (pkgs) stdenv;
inherit (pkgs.lib) generators;
paths =
let nameToSoPath = name:
let drv = exts."php-${name}";
in "${drv}/lib/${name}.so";
in
builtins.concatStringsSep " " (builtins.map nameToSoPath names);
in
pkgs.runCommand
"php-with-extensions"
{
buildInputs = [pkgs.binutils-unwrapped pkgs.makeWrapper];
MODULE_PATHS = paths;
}
''
# Create PHP symlinks
mkdir -p $out/bin
for exe in php php-fpm; do
makeWrapper \
${php}/bin/$exe \
$out/bin/$exe \
--add-flags "-c $out/etc/modules.ini"
done
# Advertise all requested modules
mkdir -p $out/etc
for module in $MODULE_PATHS; do
type=extension
if readelf --wide --syms "$module" | grep ' zend_extension_entry$' >/dev/null; then
type=zend_extension
fi
echo "$type=$module" >> $out/etc/modules.ini
done
'';
in
{ php = php; withExtensions = withExtensions; } // exts
{ pkgs ? import <nixpkgs> {} }:
let
inherit (pkgs) stdenv;
common = import ./common.nix { pkgs = pkgs; };
in
stdenv.mkDerivation {
name = "php";
src = common.src;
enableParallelBuilding = true;
buildInputs = [ pkgs.autoconf pkgs.libxml2 ];
preConfigure = ''
for offender in main/build-defs.h.in scripts/php-config.in; do
substituteInPlace $offender \
--replace '@CONFIGURE_COMMAND@' '(haha no)' \
--replace '@CONFIGURE_OPTIONS@' ""
done
addToSearchPath PATH $libxml2/bin
configureFlags+=(--includedir=$dev/include)
./buildconf --force
'';
configureFlags = "${common.configureFlags} --with-libxml-dir=${pkgs.libxml2}";
postInstall = ''
mkdir -p $dev/bin
for tool in phpize php-config; do
mv $out/bin/$tool $dev/bin/$tool
done
'';
outputs = [ "out" "dev" ];
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment