PhpBrew\VariantBuilder::__construct PHP Method

__construct() public method

public __construct ( )
    public function __construct()
    {
        // init variant builders
        $this->variants['all'] = '--enable-all';
        $this->variants['dba'] = '--enable-dba';
        $this->variants['ipv6'] = '--enable-ipv6';
        $this->variants['dom'] = '--enable-dom';
        $this->variants['calendar'] = '--enable-calendar';
        $this->variants['wddx'] = '--enable-wddx';
        $this->variants['static'] = '--enable-static';
        $this->variants['inifile'] = '--enable-inifile';
        $this->variants['inline'] = '--enable-inline-optimization';
        $this->variants['cli'] = '--enable-cli';
        $this->variants['ftp'] = '--enable-ftp';
        $this->variants['filter'] = '--enable-filter';
        $this->variants['gcov'] = '--enable-gcov';
        $this->variants['zts'] = '--enable-maintainer-zts';
        $this->variants['json'] = '--enable-json';
        $this->variants['hash'] = '--enable-hash';
        $this->variants['exif'] = '--enable-exif';
        $this->variants['mbstring'] = '--enable-mbstring';
        $this->variants['mbregex'] = '--enable-mbregex';
        $this->variants['libgcc'] = '--enable-libgcc';
        // $this->variants['gd-jis'] = '--enable-gd-jis-conv';
        $this->variants['pdo'] = '--enable-pdo';
        $this->variants['posix'] = '--enable-posix';
        $this->variants['embed'] = '--enable-embed';
        $this->variants['sockets'] = '--enable-sockets';
        $this->variants['debug'] = '--enable-debug';
        $this->variants['phpdbg'] = '--enable-phpdbg';
        $this->variants['zip'] = '--enable-zip';
        $this->variants['bcmath'] = '--enable-bcmath';
        $this->variants['fileinfo'] = '--enable-fileinfo';
        $this->variants['ctype'] = '--enable-ctype';
        $this->variants['cgi'] = '--enable-cgi';
        $this->variants['soap'] = '--enable-soap';
        $this->variants['gcov'] = '--enable-gcov';
        $this->variants['pcntl'] = '--enable-pcntl';
        $this->variants['phar'] = '--enable-phar';
        $this->variants['session'] = '--enable-session';
        $this->variants['tokenizer'] = '--enable-tokenizer';
        // opcache was added since 5.6
        $this->variants['opcache'] = '--enable-opcache';
        $this->variants['imap'] = '--with-imap-ssl';
        $this->variants['tidy'] = '--with-tidy';
        $this->variants['kerberos'] = '--with-kerberos';
        $this->variants['xmlrpc'] = '--with-xmlrpc';
        $this->variants['fpm'] = function (Build $build, $prefix = null) {
            $opts = array('--enable-fpm');
            if ($bin = Utils::findBin('systemctl') && Utils::findIncludePrefix('systemd/sd-daemon.h')) {
                $opts[] = '--with-fpm-systemd';
            }
            return $opts;
        };
        $this->variants['dtrace'] = function (Build $build, $prefix = null) {
            // if dtrace is supported
            /*
            if ($prefix = Utils::findIncludePrefix('sys/sdt.h')) {
                return "--enable-dtrace";
            }
            */
            return '--enable-dtrace';
        };
        $this->variants['pcre'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return array('--with-pcre-regex', "--with-pcre-dir={$prefix}");
            }
            if ($prefix = Utils::findIncludePrefix('pcre.h')) {
                return array('--with-pcre-regex', "--with-pcre-dir={$prefix}");
            }
            if ($bin = Utils::findBin('brew')) {
                if ($prefix = exec_line("{$bin} --prefix pcre")) {
                    if (file_exists($prefix)) {
                        return array('--with-pcre-regex', "--with-pcre-dir={$prefix}");
                    }
                    echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                }
            }
            return array('--with-pcre-regex');
        };
        $this->variants['mhash'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return "--with-mhash={$prefix}";
            }
            if ($prefix = Utils::findIncludePrefix('mhash.h')) {
                return "--with-mhash={$prefix}";
            }
            if ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix mhash")) {
                    if (file_exists($output)) {
                        return "--with-mhash={$output}";
                    }
                    echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                }
            }
            return '--with-mhash';
            // let autotool to find it.
        };
        $this->variants['mcrypt'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return "--with-mcrypt={$prefix}";
            }
            if ($prefix = Utils::findIncludePrefix('mcrypt.h')) {
                return "--with-mcrypt={$prefix}";
            }
            if ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix mcrypt")) {
                    if (file_exists($output)) {
                        return "--with-mcrypt={$output}";
                    }
                    echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                }
            }
            return '--with-mcrypt';
            // let autotool to find it.
        };
        $this->variants['zlib'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return "--with-zlib={$prefix}";
            }
            if ($prefix = Utils::findIncludePrefix('zlib.h')) {
                return "--with-zlib={$prefix}";
            }
            return;
        };
        $this->variants['curl'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return "--with-curl={$prefix}";
            }
            if ($prefix = Utils::findIncludePrefix('curl/curl.h')) {
                return "--with-curl={$prefix}";
            }
            if ($prefix = Utils::getPkgConfigPrefix('libcurl')) {
                return "--with-curl={$prefix}";
            }
            if ($bin = Utils::findBin('brew')) {
                if ($prefix = exec_line("{$bin} --prefix curl")) {
                    if (file_exists($prefix)) {
                        return "--with-curl={$prefix}";
                    }
                    echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                }
            }
            if ($bin = Utils::findBin('curl-config')) {
                if ($prefix = exec_line("{$bin} --prefix")) {
                    if (file_exists($prefix)) {
                        return "--with-curl={$prefix}";
                    }
                    echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                }
            }
            return;
        };
        /*
        Users might prefer readline over libedit because only readline supports
        readline_list_history() (http://www.php.net/readline-list-history).
        On the other hand we want libedit to be the default because its license
        is compatible with PHP's which means PHP can be distributable.
        
        related issue https://github.com/phpbrew/phpbrew/issues/497
        
        The default libreadline version that comes with OS X is too old and
        seems to be missing symbols like rl_mark, rl_pending_input,
        rl_history_list, rl_on_new_line. This is not detected by ./configure
        
        So we should prefer macports/homebrew library than the system readline library.
        @see https://bugs.php.net/bug.php?id=48608
        */
        $this->variants['readline'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return "--with-readline={$prefix}";
            }
            if ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix readline")) {
                    if (file_exists($output)) {
                        return '--with-readline=' . $output;
                    }
                    echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                }
            }
            if ($prefix = Utils::findIncludePrefix('readline' . DIRECTORY_SEPARATOR . 'readline.h')) {
                return '--with-readline=' . $prefix;
            }
            return '--with-readline';
        };
        /*
         * editline is conflict with readline
         *
         * one must tap the homebrew/dupes to use this formula
         *
         *      brew tap homebrew/dupes
         */
        $this->variants['editline'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return "--with-libedit={$prefix}";
            } elseif ($prefix = Utils::findIncludePrefix('editline' . DIRECTORY_SEPARATOR . 'readline.h')) {
                return "--with-libedit={$prefix}";
            } elseif ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix libedit")) {
                    if (file_exists($output)) {
                        return '--with-libedit=' . $output;
                    }
                    echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                } else {
                    echo "prefix of libedit not found, please run 'brew tap homebrew/dupes' to get the formula\n";
                }
            }
            return '--with-libedit';
        };
        /*
         * It looks like gd won't be compiled without "shared"
         *
         * Suggested options is +gd=shared,{prefix}
         *
         * Issue: gd.so: undefined symbol: gdImageCreateFromWebp might happend
         *
         * Adding --with-libpath=lib or --with-libpath=lib/x86_64-linux-gnu
         * might solve the gd issue.
         *
         * The configure script in ext/gd detects libraries by something like
         * test -f $PREFIX/$LIBPATH/libxxx.a, where $PREFIX is what you passed
         * in --with-xxxx-dir and $LIBPATH can varies in different OS.
         *
         * By adding --with-libpath, you can set it up properly.
         *
         * @see https://github.com/phpbrew/phpbrew/issues/461
         */
        $this->variants['gd'] = function (Build $build, $prefix = null) {
            $opts = array();
            if ($prefix) {
                $opts[] = "--with-gd={$prefix}";
            } elseif ($prefix = Utils::findIncludePrefix('gd.h')) {
                $opts[] = "--with-gd=shared,{$prefix}";
            } elseif ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix gd")) {
                    if (file_exists($output)) {
                        $opts[] = "--with-gd=shared,{$output}";
                    } else {
                        echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                    }
                }
            }
            $opts[] = '--enable-gd-native-ttf';
            if ($prefix = Utils::findIncludePrefix('jpeglib.h')) {
                $opts[] = "--with-jpeg-dir={$prefix}";
            } elseif ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix libjpeg")) {
                    if (file_exists($output)) {
                        $opts[] = "--with-jpeg-dir={$output}";
                    } else {
                        echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                    }
                }
            }
            if ($prefix = Utils::findIncludePrefix('png.h', 'libpng12/pngconf.h')) {
                $opts[] = "--with-png-dir={$prefix}";
            } elseif ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix libpng")) {
                    if (file_exists($output)) {
                        $opts[] = "--with-png-dir={$output}";
                    } else {
                        echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                    }
                }
            }
            // the freetype-dir option does not take prefix as its value,
            // it takes the freetype.h directory as its value.
            //
            // from configure:
            //   for path in $i/include/freetype2/freetype/freetype.h
            if ($prefix = Utils::findIncludePrefix('freetype2/freetype.h')) {
                $opts[] = "--with-freetype-dir={$prefix}";
            } elseif ($prefix = Utils::findIncludePrefix('freetype2/freetype/freetype.h')) {
                $opts[] = "--with-freetype-dir={$prefix}";
            } elseif ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix freetype", $output, $retval)) {
                    if (file_exists($output)) {
                        $opts[] = "--with-freetype-dir={$output}";
                    } else {
                        echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                    }
                }
            }
            return $opts;
        };
        /*
        --enable-intl
        
         To build the extension you need to install the ยป ICU library, version
         4.0.0 or newer is required.
        
         This extension is bundled with PHP as of PHP version 5.3.0.
         Alternatively, the PECL version of this extension may be used with all
         PHP versions greater than 5.2.0 (5.2.4+ recommended).
        
         This requires --with-icu-dir=/....
        
         Please note prefix must provide {prefix}/bin/icu-config for autoconf
         to find the related icu-config binary, or the configure will fail.
        
         Issue: https://github.com/phpbrew/phpbrew/issues/433
        */
        $this->variants['intl'] = function (Build $build) {
            $opts = array('--enable-intl');
            // If icu variant is not set, and --with-icu-dir could not been found in the extra options
            $icuOption = $build->settings->grepExtraOptionsByPattern('#--with-icu-dir#');
            if (!$build->settings->isEnabledVariant('icu') || empty($icuOption)) {
                if ($bin = Utils::findBin('icu-config')) {
                    /*
                     * let autoconf find it's own icu-config
                     * The build-in acinclude.m4 will find the icu-config from $PATH:/usr/local/bin
                     */
                } elseif ($prefix = Utils::getPkgConfigPrefix('icu-i18n')) {
                    // For macports or linux
                    $opts[] = '--with-icu-dir=' . $prefix;
                } elseif ($bin = Utils::findBin('brew')) {
                    // For homebrew
                    if ($output = exec_line("{$bin} --prefix icu4c")) {
                        if (file_exists($output)) {
                            $opts[] = "--with-icu-dir={$output}";
                        } else {
                            echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                        }
                    }
                }
            }
            return $opts;
        };
        /*
         * icu variant
         *
         * @deprecated this variant is deprecated since icu is a part of intl
         * extension.  however, we kept this variant for user to customize the icu path
         */
        $this->variants['icu'] = function (Build $build, $val = null) {
            if ($val) {
                return '--with-icu-dir=' . $val;
            }
        };
        /*
         * --with-openssl option
         *
         * --with-openssh=shared
         * --with-openssl=[dir]
         *
         * On ubuntu you need to install libssl-dev
         */
        $this->variants['openssl'] = function (Build $build, $val = null) {
            if ($val) {
                return "--with-openssl={$val}";
            }
            if ($prefix = Utils::findIncludePrefix('openssl/opensslv.h')) {
                return "--with-openssl={$prefix}";
            }
            // Special detection and fallback for homebrew openssl
            // @see https://github.com/phpbrew/phpbrew/issues/607
            if ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix openssl")) {
                    if (file_exists($output)) {
                        return "--with-openssl={$output}";
                    }
                    echo "prefix {$output} doesn't exist.";
                }
            }
            if ($prefix = Utils::getPkgConfigPrefix('openssl')) {
                return "--with-openssl={$prefix}";
            }
            $possiblePrefixes = array('/usr/local/opt/openssl');
            $foundPrefixes = array_filter($possiblePrefixes, 'file_exists');
            if (count($foundPrefixes) > 0) {
                return '--with-openssl=' . $foundPrefixes[0];
            }
            // This will create openssl.so file for dynamic loading.
            echo 'Compiling with openssl=shared, please install libssl-dev or openssl header files if you need';
            return '--with-openssl';
        };
        /*
        quote from the manual page:
        
        > MySQL Native Driver is a replacement for the MySQL Client Library
        > (libmysqlclient). MySQL Native Driver is part of the official PHP
        > sources as of PHP 5.3.0.
        
        > The MySQL database extensions MySQL extension, mysqli and PDO MYSQL all
        > communicate with the MySQL server. In the past, this was done by the
        > extension using the services provided by the MySQL Client Library. The
        > extensions were compiled against the MySQL Client Library in order to
        > use its client-server protocol.
        
        > With MySQL Native Driver there is now an alternative, as the MySQL
        > database extensions can be compiled to use MySQL Native Driver instead
        > of the MySQL Client Library.
        
        mysqlnd should be prefered over the native client library.
        
        --with-mysql[=DIR]      Include MySQL support.  DIR is the MySQL base
                                directory.  If mysqlnd is passed as DIR,
                                the MySQL native driver will be used [/usr/local]
        
        --with-mysqli[=FILE]    Include MySQLi support.  FILE is the path
                                to mysql_config.  If mysqlnd is passed as FILE,
                                the MySQL native driver will be used [mysql_config]
        
        --with-pdo-mysql[=DIR]    PDO: MySQL support. DIR is the MySQL base directoy
                                If mysqlnd is passed as DIR, the MySQL native
                                native driver will be used [/usr/local]
        
        --with-mysql            deprecated in 7.0
        
        --enable-mysqlnd        Enable mysqlnd explicitly, will be done implicitly
                                when required by other extensions
        
        mysqlnd was added since php 5.3
        */
        $this->variants['mysql'] = function (Build $build, $prefix = 'mysqlnd') {
            $opts = array();
            if ($build->compareVersion('7.0') < 0) {
                $opts[] = "--with-mysql={$prefix}";
            }
            /*
            if ($build->compareVersion('5.4') > 0) {
                $opts[] = "--enable-mysqlnd";
            }
            */
            $opts[] = "--with-mysqli={$prefix}";
            if ($build->hasVariant('pdo')) {
                $opts[] = "--with-pdo-mysql={$prefix}";
            }
            $foundSock = false;
            if ($bin = Utils::findBin('mysql_config')) {
                if ($output = exec_line("{$bin} --socket")) {
                    $foundSock = true;
                    $opts[] = "--with-mysql-sock={$output}";
                }
            }
            if (!$foundSock) {
                $possiblePaths = array('/opt/local/var/run/mysql57/mysqld.sock', '/opt/local/var/run/mysql56/mysqld.sock', '/opt/local/var/run/mysql55/mysqld.sock', '/opt/local/var/run/mysql54/mysqld.sock', '/tmp/mysql.sock', '/var/run/mysqld/mysqld.sock', '/var/mysql/mysql.sock');
                foreach ($possiblePaths as $path) {
                    if (file_exists($path)) {
                        $opts[] = '--with-mysql-sock=' . $path;
                        break;
                    }
                }
            }
            return $opts;
        };
        $this->variants['sqlite'] = function (Build $build, $prefix = null) {
            $opts = array('--with-sqlite3' . ($prefix ? "={$prefix}" : ''));
            if ($build->hasVariant('pdo')) {
                $opts[] = '--with-pdo-sqlite';
            }
            return $opts;
        };
        /**
         * The --with-pgsql=[DIR] and --with-pdo-pgsql=[DIR] requires [DIR]/bin/pg_config to be found.
         */
        $this->variants['pgsql'] = function (Build $build, $prefix = null) {
            $opts = array();
            // The names are used from macports
            if ($prefix) {
                $opts[] = "--with-pgsql={$prefix}";
                if ($build->hasVariant('pdo')) {
                    $opts[] = "--with-pdo-pgsql={$prefix}";
                }
                return $opts;
            }
            $bin = Utils::findBin('pg_config');
            if (!$bin) {
                $bin = first_existing_executable(array('/opt/local/lib/postgresql95/bin/pg_config', '/opt/local/lib/postgresql94/bin/pg_config', '/opt/local/lib/postgresql93/bin/pg_config', '/opt/local/lib/postgresql92/bin/pg_config', '/Library/PostgreSQL/9.5/bin/pg_config', '/Library/PostgreSQL/9.4/bin/pg_config', '/Library/PostgreSQL/9.3/bin/pg_config', '/Library/PostgreSQL/9.2/bin/pg_config', '/Library/PostgreSQL/9.1/bin/pg_config'));
            }
            if ($bin) {
                $opts[] = "--with-pgsql=" . dirname($bin);
                if ($build->hasVariant('pdo')) {
                    $opts[] = "--with-pdo-pgsql=" . dirname($bin);
                }
                return $opts;
            }
            $opts[] = "--with-pgsql";
            if ($build->hasVariant('pdo')) {
                $opts[] = '--with-pdo-pgsql';
            }
            return $opts;
        };
        $this->variants['xml'] = function (Build $build) {
            $options = array('--enable-dom', '--enable-libxml', '--enable-simplexml', '--enable-xml', '--enable-xmlreader', '--enable-xmlwriter', '--with-xsl');
            do {
                if ($bin = Utils::findBin('brew')) {
                    // for brew, it could be "/usr/local/opt/libxml2"
                    // or "/usr/local/Cellar/libxml2/2.9.3" before install.
                    if ($output = exec_line("{$bin} --prefix libxml2")) {
                        if (file_exists($output)) {
                            $options[] = "--with-libxml-dir={$output}";
                            break;
                        }
                        echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                    }
                }
                if ($prefix = Utils::getPkgConfigPrefix('libxml')) {
                    $options[] = "--with-libxml-dir={$prefix}";
                    break;
                }
                if ($prefix = Utils::findIncludePrefix('libxml2/libxml/globals.h')) {
                    $options[] = "--with-libxml-dir={$prefix}";
                    break;
                }
                if ($prefix = Utils::findLibPrefix('libxml2.a')) {
                    $options[] = "--with-libxml-dir={$prefix}";
                    break;
                }
            } while (0);
            return $options;
        };
        $this->variants['xml_all'] = $this->variants['xml'];
        $this->variants['apxs2'] = function (Build $build, $prefix = null) {
            $a = '--with-apxs2';
            if ($prefix) {
                return '--with-apxs2=' . $prefix;
            }
            if ($bin = Utils::findBinByPrefix('apxs2')) {
                return '--with-apxs2=' . $bin;
            } elseif ($bin = Utils::findBinByPrefix('apxs')) {
                return '--with-apxs2=' . $bin;
            }
            /* Special paths for homebrew */
            $possiblePaths = array('/usr/local/opt/httpd24/bin/apxs', '/usr/local/opt/httpd23/bin/apxs', '/usr/local/opt/httpd22/bin/apxs', '/usr/local/opt/httpd21/bin/apxs', '/usr/local/sbin/apxs', '/usr/local/bin/apxs', '/usr/sbin/apxs', '/usr/bin/apxs');
            if ($path = first_existing_executable($possiblePaths)) {
                $opts[] = "--with-apxs2={$path}";
            }
            return $a;
            // fallback to autoconf finder
        };
        $this->variants['gettext'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return '--with-gettext=' . $prefix;
            }
            if ($prefix = Utils::findIncludePrefix('libintl.h')) {
                return '--with-gettext=' . $prefix;
            }
            if ($bin = Utils::findBin('brew')) {
                if ($output = exec_line("{$bin} --prefix gettext")) {
                    if (file_exists($output)) {
                        return "--with-gettext={$output}";
                    }
                    echo "homebrew prefix '{$output}' doesn't exist. you forgot to install?\n";
                }
            }
            return '--with-gettext';
        };
        $this->variants['iconv'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return "--with-iconv={$prefix}";
            }
            /*
             * php can't be compile with --with-iconv=/usr because it uses giconv
             *
             * https://bugs.php.net/bug.php?id=48451
             *
            // detect include path for iconv.h
            if ( $prefix = Utils::find_include_prefix('giconv.h', 'iconv.h') ) {
                return "--with-iconv=$prefix";
            }
            */
            return '--with-iconv';
        };
        $this->variants['bz2'] = function ($build, $prefix = null) {
            if ($prefix) {
                return "--with-bz2={$prefix}";
            }
            if ($prefix = Utils::findIncludePrefix('bzlib.h')) {
                return "--with-bz2={$prefix}";
            }
            return '--with-bz2';
        };
        $this->variants['ipc'] = function (Build $build) {
            return array('--enable-shmop', '--enable-sysvsem', '--enable-sysvshm', '--enable-sysvmsg');
        };
        $this->variants['gmp'] = function (Build $build, $prefix = null) {
            if ($prefix) {
                return "--with-gmp={$prefix}";
            }
            if ($prefix = Utils::findIncludePrefix('gmp.h')) {
                return "--with-gmp={$prefix}";
            }
            return '--with-gmp';
            // let autotool to find it.
        };
        // merge virtual variants with config file
        $customVirtualVariants = Config::getConfigParam('variants');
        $customVirtualVariantsToAdd = array();
        if (!empty($customVirtualVariants)) {
            foreach ($customVirtualVariants as $key => $extension) {
                // The extension might be null
                if (!empty($extension)) {
                    $customVirtualVariantsToAdd[$key] = array_keys($extension);
                }
            }
        }
        $this->virtualVariants = array_merge($customVirtualVariantsToAdd, $this->virtualVariants);
        // create +everything variant
        $this->virtualVariants['everything'] = array_diff(array_keys($this->variants), array('apxs2', 'all'));
    }