예제 #1
0
파일: Resolver.php 프로젝트: koolkode/async
 /**
  * {@inheritdoc}
  */
 public function resolve(string $host) : Awaitable
 {
     $host = \strtolower(\trim($host, '[]'));
     if ($host === 'localhost') {
         return new Success(new Address('::1', '127.0.0.1'));
     }
     if (Address::isResolved($host)) {
         return new Success(new Address($host));
     }
     if (isset($this->hosts[$host])) {
         return new Success($this->hosts[$host]);
     }
     if (isset($this->cache[$host]) && \time() < $this->cache[$host]['expires']) {
         return new Success($this->cache[$host]['address']);
     }
     if (!isset($this->pending[$host])) {
         $this->pending[$host] = $resolver = new Coroutine($this->resolveHost($host));
         $resolver->when(function (\Throwable $e = null, array $val = null) use($host) {
             unset($this->pending[$host]);
             if ($val) {
                 $this->cache[$host] = $val;
             }
         });
     }
     return new Task(new Transform($this->pending[$host], function (array $result) {
         return $result['address'];
     }));
 }
예제 #2
0
파일: Resolver.php 프로젝트: koolkode/async
 /**
  * {@inheritdoc}
  */
 public function resolve(string $host) : Awaitable
 {
     $host = \strtolower(\trim($host, '[]'));
     if ($host === 'localhost') {
         return new Success(new Address('::1', '127.0.0.1'));
     }
     if (Address::isResolved($host)) {
         return new Success(new Address($host));
     }
     return $this->loop->handleCallback('uv_getaddrinfo', function ($result, array $ips) use($host) {
         if ($result < 0) {
             throw new \RuntimeException(\sprintf('Could not resolve "%s" into an IP address', $host));
         }
         return new Address(...$ips);
     }, $host, '', []);
 }
예제 #3
0
 /**
  * Set all DNS nameservers to be used.
  * 
  * @param array $servers DNS server addresses including UDP port number
  * 
  * @throws \InvalidArgumentException When a server entry is invalid or cannot be resolved into an IP address.
  */
 public function setNameservers(array $servers)
 {
     $result = [];
     foreach ($servers as $host) {
         if (false === ($index = \strrpos($host, ':'))) {
             throw new \InvalidArgumentException(\sprintf('No DNS server UDP port number specified (default port is 53): "%s"', $host));
         }
         $address = \substr($host, 0, $index);
         $port = \substr($host, $index + 1);
         if (!\preg_match("'[1-9][0-9]*'", $port)) {
             throw new \InvalidArgumentException(\sprintf('Invalid DNS server port number: "%s"', $port));
         }
         if (!Address::isResolved($address)) {
             $ips = \gethostbynamel($address);
             if (empty($ips)) {
                 throw new \InvalidArgumentException(\sprintf('Cannot resolve DNS server into an IP address: "%s"', $address));
             }
             foreach ($ips as $ip) {
                 $result[] = \sprintf('%s:%u', $ip, $port);
             }
         } else {
             $result[] = $host;
         }
     }
     $this->nameservers = $result;
 }
예제 #4
0
 protected function connectSocket(Uri $uri) : Awaitable
 {
     $host = $uri->getHost();
     if (Address::isResolved($host)) {
         $factory = new SocketFactory(new Address($host) . ':' . $uri->getPort(), 'tcp');
     } else {
         $factory = new SocketFactory($uri->getHostWithPort(true), 'tcp');
     }
     $factory->setTcpNoDelay(true);
     if ($this->protocols && Socket::isAlpnSupported()) {
         $factory->setOption('ssl', 'alpn_protocols', \implode(',', $this->protocols));
     }
     return $factory->createSocketStream(5, $uri->getScheme() === 'https');
 }