mlocati / docker-php-extension-installer

Easily install PHP extensions in Docker containers
MIT License
4.18k stars 378 forks source link

Fix installing libssl on old Alpine versions #902

Closed transistive closed 5 months ago

transistive commented 5 months ago

When trying to use the script in PHP 5.6 FPM Alpine, it broke trying to install ^libssl[0-9]+(\.[0-9]+)*$

After closer inspection, it seems that the pattern:

#.....
if test -z "$(apk info 2>/dev/null | grep -E ^libssl)"; then
    buildRequiredPackageLists_libssl='^libssl[0-9]+(\.[0-9]+)*$'
elif
#.......

is not portable. It crashes in older PHP fpm scripts. I assume that older alpine versions don't support regex pattern installations.

This solution leverages apk search and grep -E to achieve the same result.

mlocati commented 5 months ago

Which PHP extension are you trying to install on PHP 5.6 fpm that showcases the problem?

transistive commented 5 months ago

I haven't taken the time to isolate the package as I was under the impressions this was a common installation requirement. Here is the list:

install-php-extensions gd \
  apcu \
  amqp \
  memcache \
  sodium \
  redis \
  xdebug \
  mcrypt \
  gmp \
  exif \
  sockets \
  bcmath \
  zip \
  tidy \
  soap \
  mysqli \
  simplexml \
  intl \
  opcache \
  pdo_mysql \
  mongodb \
  @composer

I can narrow it down if you want later, I'm grabbing lunch now

mlocati commented 5 months ago

Nowaways we don't have a libssl-dev package, but one day we may have it. So, I'd prefer this regex: ^libssl[0-9]+[r0-9.\-]*$

Also, everywhere we simply specify either the complete package name or a regular expression that identifies it: why are you using the grep | cut | uniq approach instead?

transistive commented 5 months ago

The problem is when you run :

docker run -it php:5.6-fpm-alpine apk add ^libssl[0-9]+[r0-9.\-]*$ 

it crashes, which gets called indirectly if you run:

docker run php:5.6-fpm-alpine sh -c "
curl -sSLf \
      -o /usr/local/bin/install-php-extensions \
      https://github.com/mlocati/docker-php-extension-installer/releases/latest/download/install-php-extensions
chmod +x /usr/local/bin/install-php-extensions
install-php-extensions mongodb
"

The reason I'm using the funky grep | cut | uniq approach is because if we just use grep it will output something like this:

docker run -it php:5.6-fpm-alpine sh -c 'apk update && apk search | grep -E "^libssl"'

it outputs something like:

libssl1.0-1.0.2u-r0

Which you cannot directly install:

docker run -it php:5.6-fpm-alpine sh -c 'apk add libssl1.0-1.0.2u-r0'

Hence, the cut to only fetch the first part, libssl1.0, which does install:

docker run php:5.6-fpm-alpine sh -c 'apk add libssl1.0'

The uniq part is just me being a bit of a perfectionist but is not required

mlocati commented 5 months ago

You are right, on Alpine we can't use regular expressions to choose apk libraries (I forgot about that).

So, what about

buildRequiredPackageLists_libssl="$(apk search | grep -E '^libssl[0-9]' | cut -d- -f1)"
transistive commented 5 months ago

If that works I'm entirely okay with that! I'm currently not in a place where I can double-check. Good stuff :+1:

mlocati commented 5 months ago

Even better:

apk search | grep -E '^libssl[0-9]' | head -1 | cut -d- -f1
transistive commented 5 months ago

Perfect! Feel free to change it, otherwise I'll do it tomorrow

mlocati commented 5 months ago

Feel free to change it

Done: 3ce069cd7ca7b43b06d3c7fb9ebfe5d31271f767