From 3340d60d91cc9afbe1a2d02b67b3f98f5c1da5a3 Mon Sep 17 00:00:00 2001 From: Shivam Mathur Date: Tue, 16 Feb 2021 11:06:23 +0530 Subject: [PATCH] Improve support for pecl_http on linux and macOS --- __tests__/extensions.test.ts | 12 +++ dist/index.js | 12 +-- src/extensions.ts | 12 +-- src/scripts/ext/http.sh | 166 +++++++++++++++++++++++++++++++++++ 4 files changed, 190 insertions(+), 12 deletions(-) create mode 100644 src/scripts/ext/http.sh diff --git a/__tests__/extensions.test.ts b/__tests__/extensions.test.ts index 664c1469..b15efd0d 100644 --- a/__tests__/extensions.test.ts +++ b/__tests__/extensions.test.ts @@ -123,6 +123,12 @@ describe('Extension tests', () => { linux = await extensions.addExtension('geos', '7.3', 'linux'); expect(linux).toContain('add_geos'); + linux = await extensions.addExtension('pecl_http', '7.3', 'linux'); + expect(linux).toContain('add_http'); + + linux = await extensions.addExtension('http-1.2.3', '7.3', 'linux'); + expect(linux).toContain('add_http http-1.2.3'); + linux = await extensions.addExtension('oci8, pdo_oci', '7.3', 'linux'); expect(linux).toContain('add_oci oci8'); expect(linux).toContain('add_oci pdo_oci'); @@ -190,6 +196,12 @@ describe('Extension tests', () => { darwin = await extensions.addExtension('geos', '7.3', 'darwin'); expect(darwin).toContain('add_geos'); + darwin = await extensions.addExtension('pecl_http', '7.3', 'darwin'); + expect(darwin).toContain('add_http'); + + darwin = await extensions.addExtension('http-1.2.3', '7.3', 'darwin'); + expect(darwin).toContain('add_http http-1.2.3'); + darwin = await extensions.addExtension('oci8, pdo_oci', '7.3', 'darwin'); expect(darwin).toContain('add_oci oci8'); expect(darwin).toContain('add_oci pdo_oci'); diff --git a/dist/index.js b/dist/index.js index bda97ecf..e265c7cd 100644 --- a/dist/index.js +++ b/dist/index.js @@ -2909,12 +2909,12 @@ async function addExtensionDarwin(extension_csv, version) { return; // match 5.3blackfire...8.0blackfire // match 5.3blackfire-(semver)...8.0blackfire-(semver) - // match pdo_oci and oci8 + // match pdo_oci, oci8, http, pecl_http // match 5.3ioncube...7.4ioncube, 5.3geos...7.4geos // match 7.0phalcon3...7.3phalcon3 and 7.2phalcon4...7.4phalcon4 // match 5.6couchbase...7.4couchbase case /^(5\.[3-6]|7\.[0-4]|8\.0)blackfire(-\d+\.\d+\.\d+)?$/.test(version_extension): - case /^pdo_oci$|^oci8$/.test(extension): + case /^pdo_oci$|^oci8$|^http|^pecl_http/.test(extension): case /^(5\.[3-6]|7\.[0-4])(ioncube|geos)$/.test(version_extension): case /^7\.[0-3]phalcon3$|^7\.[2-4]phalcon4$/.test(version_extension): case /^5\.6couchbase$|^7\.[0-4]couchbase$/.test(version_extension): @@ -2938,10 +2938,10 @@ async function addExtensionDarwin(extension_csv, version) { case /(5\.[3-6]|7\.0)pcov/.test(version_extension): add_script += await utils.getUnsupportedLog('pcov', version, 'darwin'); return; - // match 5.6 to 8.9 for amqp, grpc, igbinary, imagick, imap, pecl_http, protobuf, raphf, swoole, xdebug, xdebug2, zmq + // match 5.6 to 8.9 for amqp, grpc, igbinary, imagick, imap, protobuf, raphf, swoole, xdebug, xdebug2, zmq // match 7.1 to 8.9 for pcov // match 5.6 to 7.4 for propro - case /(5\.6|7\.[0-4]|8\.[0-9])(amqp|grpc|http|igbinary|imagick|imap|pecl_http|protobuf|raphf|swoole|xdebug|xdebug2|zmq)/.test(version_extension): + case /(5\.6|7\.[0-4]|8\.[0-9])(amqp|grpc|igbinary|imagick|imap|protobuf|raphf|swoole|xdebug|xdebug2|zmq)/.test(version_extension): case /(5\.6|7\.[0-4])propro/.test(version_extension): case /(7\.[1-4]|8\.[0-9])pcov/.test(version_extension): add_script += await utils.joins('\nadd_brew_extension', ext_name, ext_prefix); @@ -3069,13 +3069,13 @@ async function addExtensionLinux(extension_csv, version) { // match 5.3blackfire...8.0blackfire // match 5.3blackfire-(semver)...8.0blackfire-(semver) // match 5.3pdo_cubrid...7.2php_cubrid, 5.3cubrid...7.4cubrid - // match pdo_oci and oci8 + // match pdo_oci, oci8, http, pecl_http // match 5.3ioncube...7.4ioncube, 5.3geos...7.4geos // match 7.0phalcon3...7.3phalcon3 and 7.2phalcon4...7.4phalcon4 // match 5.6gearman...7.4gearman, 5.6couchbase...7.4couchbase case /^(5\.[3-6]|7\.[0-4]|8\.0)blackfire(-\d+\.\d+\.\d+)?$/.test(version_extension): case /^((5\.[3-6])|(7\.[0-2]))pdo_cubrid$|^((5\.[3-6])|(7\.[0-4]))cubrid$/.test(version_extension): - case /^pdo_oci$|^oci8$/.test(extension): + case /^pdo_oci$|^oci8$|^http|^pecl_http/.test(extension): case /^(5\.6|7\.[0-4]|8\.0)intl-[\d]+\.[\d]+$/.test(version_extension): case /^(5\.[3-6]|7\.[0-4])(ioncube|geos)$/.test(version_extension): case /^7\.[0-3]phalcon3$|^7\.[2-4]phalcon4$/.test(version_extension): diff --git a/src/extensions.ts b/src/extensions.ts index d44ff166..e102f466 100644 --- a/src/extensions.ts +++ b/src/extensions.ts @@ -26,14 +26,14 @@ export async function addExtensionDarwin( return; // match 5.3blackfire...8.0blackfire // match 5.3blackfire-(semver)...8.0blackfire-(semver) - // match pdo_oci and oci8 + // match pdo_oci, oci8, http, pecl_http // match 5.3ioncube...7.4ioncube, 5.3geos...7.4geos // match 7.0phalcon3...7.3phalcon3 and 7.2phalcon4...7.4phalcon4 // match 5.6couchbase...7.4couchbase case /^(5\.[3-6]|7\.[0-4]|8\.0)blackfire(-\d+\.\d+\.\d+)?$/.test( version_extension ): - case /^pdo_oci$|^oci8$/.test(extension): + case /^pdo_oci$|^oci8$|^http|^pecl_http/.test(extension): case /^(5\.[3-6]|7\.[0-4])(ioncube|geos)$/.test(version_extension): case /^7\.[0-3]phalcon3$|^7\.[2-4]phalcon4$/.test(version_extension): case /^5\.6couchbase$|^7\.[0-4]couchbase$/.test(version_extension): @@ -79,10 +79,10 @@ export async function addExtensionDarwin( case /(5\.[3-6]|7\.0)pcov/.test(version_extension): add_script += await utils.getUnsupportedLog('pcov', version, 'darwin'); return; - // match 5.6 to 8.9 for amqp, grpc, igbinary, imagick, imap, pecl_http, protobuf, raphf, swoole, xdebug, xdebug2, zmq + // match 5.6 to 8.9 for amqp, grpc, igbinary, imagick, imap, protobuf, raphf, swoole, xdebug, xdebug2, zmq // match 7.1 to 8.9 for pcov // match 5.6 to 7.4 for propro - case /(5\.6|7\.[0-4]|8\.[0-9])(amqp|grpc|http|igbinary|imagick|imap|pecl_http|protobuf|raphf|swoole|xdebug|xdebug2|zmq)/.test( + case /(5\.6|7\.[0-4]|8\.[0-9])(amqp|grpc|igbinary|imagick|imap|protobuf|raphf|swoole|xdebug|xdebug2|zmq)/.test( version_extension ): case /(5\.6|7\.[0-4])propro/.test(version_extension): @@ -250,7 +250,7 @@ export async function addExtensionLinux( // match 5.3blackfire...8.0blackfire // match 5.3blackfire-(semver)...8.0blackfire-(semver) // match 5.3pdo_cubrid...7.2php_cubrid, 5.3cubrid...7.4cubrid - // match pdo_oci and oci8 + // match pdo_oci, oci8, http, pecl_http // match 5.3ioncube...7.4ioncube, 5.3geos...7.4geos // match 7.0phalcon3...7.3phalcon3 and 7.2phalcon4...7.4phalcon4 // match 5.6gearman...7.4gearman, 5.6couchbase...7.4couchbase @@ -260,7 +260,7 @@ export async function addExtensionLinux( case /^((5\.[3-6])|(7\.[0-2]))pdo_cubrid$|^((5\.[3-6])|(7\.[0-4]))cubrid$/.test( version_extension ): - case /^pdo_oci$|^oci8$/.test(extension): + case /^pdo_oci$|^oci8$|^http|^pecl_http/.test(extension): case /^(5\.6|7\.[0-4]|8\.0)intl-[\d]+\.[\d]+$/.test(version_extension): case /^(5\.[3-6]|7\.[0-4])(ioncube|geos)$/.test(version_extension): case /^7\.[0-3]phalcon3$|^7\.[2-4]phalcon4$/.test(version_extension): diff --git a/src/scripts/ext/http.sh b/src/scripts/ext/http.sh new file mode 100644 index 00000000..49ec3edf --- /dev/null +++ b/src/scripts/ext/http.sh @@ -0,0 +1,166 @@ +# Function to get http version for a PHP version. +get_http_version() { + if [[ ${version:?} =~ 5.[3-6] ]]; then + echo "pecl_http-2.6.0" + elif [[ ${version:?} =~ 7.[0-4] ]]; then + echo "pecl_http-3.2.4" + else + echo "pecl_http-$(get_pecl_version "pecl_http" "stable")" + fi +} + +# Function to enable http extension. +enable_http() { + enable_extension propro extension + enable_extension raphf extension + if (! [[ ${version:?} =~ ${jit_versions:?} ]] && check_extension propro && check_extension raphf) || + ( [[ ${version:?} =~ ${jit_versions:?} ]] && check_extension raphf); then + enable_extension http extension + fi +} + +# Function to install linux dependencies. +add_http_dependencies_linux() { + ! [[ ${version:?} =~ ${nightly_versions:?} ]] && add_devtools phpize + install_packages zlib1g libbrotli-dev libcurl4-openssl-dev libevent-dev libicu-dev libidn2-dev + if [[ ${version:?} =~ ${old_versions:?} ]]; then + add_pecl_extension raphf 1.1.2 extension + add_pecl_extension propro 1.0.2 extension + elif [[ ${version:?} =~ 5.6|7.[0-4] ]]; then + add_extension propro extension + add_extension raphf extension + else + add_extension raphf extension + fi +} + +# Function to install darwin dependencies. +add_http_dependencies_darwin() { + brew install brotli curl icu4c libevent libidn2 + if ! [[ ${version:?} =~ ${old_versions:?} ]]; then + if [[ ${version:?} =~ 5.6|7.[0-4] ]]; then + add_brew_extension propro extension + fi + add_brew_extension raphf extension + else + add_pecl_extension raphf 1.1.2 extension + add_pecl_extension propro 1.0.2 extension + fi +} + +# Function to install the dependencies. +add_http_dependencies() { + os=$1 + if [ "$os" = 'Linux' ]; then + add_http_dependencies_linux + else + add_http_dependencies_darwin + fi +} + +# Function to get configure options for http. +get_http_configure_opts() { + os=$1 + if [ "$os" = 'Linux' ]; then + for lib in zlib libbrotli libcurl libevent libicu libidn2 libidn libidnkit2 libidnkit; do + http_opts+=( "--with-http-$lib-dir=/usr" ) + done + else + http_opts+=( "--with-http-zlib-dir=$(xcrun --show-sdk-path)/usr" ) + http_opts+=( "--with-http-libbrotli-dir=$(brew --prefix brotli)" ) + http_opts+=( "--with-http-libcurl-dir=$(brew --prefix curl)" ) + http_opts+=( "--with-http-libicu-dir=$(brew --prefix icu4c)" ) + http_opts+=( "--with-http-libevent-dir=$(brew --prefix libevent)" ) + http_opts+=( "--with-http-libidn2-dir=$(brew --prefix libidn2)" ) + fi +} + +patch_http_source() { + ext=$1 + os=$2 + if [ "$os" = 'Darwin' ] && ! [[ ${version:?} =~ ${old_versions:?} ]]; then + if [[ ${version:?} =~ 5.6|7.[0-4] ]]; then + sed -i '' -e "s|ext/propro|$(brew --prefix propro@"${version:?}")/include/php/ext/propro@${version:?}|" "/tmp/pecl_http-${ext##*-}/src/php_http_api.h" + fi + sed -i '' -e "s|ext/raphf|$(brew --prefix raphf@"${version:?}")/include/php/ext/raphf@${version:?}|" "/tmp/pecl_http-${ext##*-}/src/php_http_api.h" + if [ "${version:?}" = "5.6" ]; then + sed -i '' -e "s|\$abs_srcdir|\$abs_srcdir ${brew_prefix:?}/include|" -e "s|/ext/propro|/php/ext/propro@5.6|" -e "s|/ext/raphf|/php/ext/raphf@5.6|" "/tmp/pecl_http-${ext##*-}/config9.m4" + fi + fi +} + +# Helper function to compile and install http. +build_http() { + ext=$1 + os=$2 + ( + http_opts=() && get_http_configure_opts "$os" + c_opts="CFLAGS=-Wno-implicit-function-declaration" + cd /tmp/pecl_http-"${ext##*-}" || exit + sudo phpize + sudo "$c_opts" ./configure --with-http --with-php-config="$(command -v php-config)" "${http_opts[@]}" + sudo make -j"$(nproc 2>/dev/null || sysctl -n hw.ncpu)" + sudo make install + ) +} + +# Compile and install http explicitly. +# This is done as pecl compiles raphf and propro as well. +add_http_helper() { + ext=$1 + os=$2 + add_http_dependencies "$os" + get -q -n /tmp/http.tgz https://pecl.php.net/get/pecl_http-"${ext##*-}".tgz + tar -xzf /tmp/http.tgz -C /tmp + patch_http_source "$ext" "$os" + build_http "$ext" "$os" + enable_extension http extension +} + +# Function to setup latest http extension. +add_http_latest() { + os=$1 + enable_http + if ! check_extension http; then + if [ "$os" = "Linux" ]; then + if ! [[ "${version:?}" =~ ${old_versions:?}|${nightly_versions:?} ]]; then + if [[ ${version:?} =~ 5.6|7.[0-4] ]]; then + install_packages "php$version-propro" + fi + install_packages "php$version-raphf" "php$version-http" + else + add_http_helper "$(get_http_version)" "$os" + fi + else + if ! [[ "${version:?}" =~ ${old_versions:?} ]]; then + add_brew_extension pecl_http extension + fi + fi + status="Installed and enabled" + fi +} + +# Function to setup http extension given a version. +add_http_version() { + ext=$1 + os=$2 + enable_http + if [ "x$(php -r "echo phpversion('http');")" != "x${ext##*-}" ]; then + remove_extension http >/dev/null + add_http_helper pecl_http-"${ext##*-}" "$os" + status="Installed and enabled" + fi +} + +# Function to setup http extension +add_http() { + ext=$1 + os="$(uname -s)" + status="Enabled" + if [[ "$ext" =~ ^(pecl_http|http)$ ]]; then + add_http_latest "$os" >/dev/null 2>&1 + else + add_http_version "$ext" "$os" >/dev/null 2>&1 + fi + add_extension_log "http" "$status" +}