zendframework / zend-uri

Uri component from Zend Framework
BSD 3-Clause "New" or "Revised" License
117 stars 24 forks source link

Method strtolower break case sensitive aliases #31

Open bmxmale opened 5 years ago

bmxmale commented 5 years ago

@weierophinney you was right with breakage. Simple case from Magento 2.3. Host is not always domain or IP address. When we using docker we can call host via container names.

Example:

host = MAGENTO2_varnish

When we call strtolower then we getting error:

[2019-03-12 11:10:23] main.CRITICAL: Unable to connect to magento2_varnish:80 . Error #0: stream_socket_client(): unable to connect to magento2_varnish:80 (php_network_getaddresses: getaddrinfo failed: Name or service not known) {"method":"GET","url":"http:/","invalidateInfo":{"server":"[object] (Zend\\Uri\\Uri: http://magento2_varnish:80/)","tagsPattern":".*"}} []

So MAGENTO2_varnish != magento2_varnish.

If anyone ( like me ) using aliases on magento then this patch break eg. Varnish Purge request.

Originally posted by @bmxmale in https://github.com/zendframework/zend-uri/pull/29#issuecomment-471958647

weierophinney commented 5 years ago

@bmxmale What is the context for your usage of zend-uri? Is it with the HTTP client? or an incoming request? Or something else?

bmxmale commented 5 years ago

@weierophinney I'm just community contributor of magento but will try to explain it in simple way.

This case come from PurgeCache event when we are using Varnish Cache as FPC. On magento we need to set http_cache_host config to tell Magento where it should send purge request.

Magento config with Varnish host ( used on docker env )

return [
    'http_cache_hosts' => [
        [
            'host' => 'MAGENTO2_varnish'
        ]
    ]
];

Here you can check this option on magento devdocs.

Docker compose used to:

version: '2'
services:
  magento2_nginx:
    container_name: MAGENTO2_nginx
    image: nginx:stable
    volumes:
      - ../magento/magento-2.3:/srv/magento2.3
      - ./mount/nginx/magento.conf:/etc/nginx/conf.d/default.conf
    network_mode: "DOCKER_network"
  magento2_php:
    container_name: MAGENTO2_php
    image: bmxmale/magento2-php:2.3
    volumes_from:
      - magento2_nginx
    network_mode: "DOCKER_network"
  magento2_varnish:
      container_name: MAGENTO2_varnish
      image: bmxmale/docker-magento-varnish:5.2.1
      volumes:
        - ./mount/varnish/varnish.vcl:/etc/varnish/default.vcl
      environment:
        - DEFAULT_VCL=0
      network_mode: "DOCKER_network"
      labels:
        - "traefik.backend=MAGENTO2_varnish"
        - "traefik.port=80"
        - "traefik.frontend.rule=Host:magento.udviklet.dk"
        - "traefik.docker.network=DOCKER_network"

Step by step

  1. When we Refresh/Flush cache on magento, it will send purge request to varnish server.
    Magento\CacheInvalidate\Model\PurgeCache::sendPurgeRequest

  2. Now sendPurgeRequest method call getUris method from cacheServer class. Magento\PageCache\Model\Cache\Server::getUris

  3. Here getUris method create UriFactory to create array of servers to send purge request. Zend\Uri\UriFactory::factory

  4. Method UriFactory create new Uri object. Zend\Uri\Uri::setHost

  5. Method setHost with param $host = 'MAGENTO2_varnish' execute strtolower. As result $host variable will contain magento2_varnish

I'm open to call with you to answer any other questions.

With best regards, Mateusz

bmxmale commented 5 years ago

@weierophinney any update on this?

In my opinion we have 2 options:

Please select one or suggest better solution and I can prepare PR for this.

weierophinney commented 4 years ago

This repository has been closed and moved to laminas/laminas-uri; a new issue has been opened at https://github.com/laminas/laminas-uri/issues/1.