1<?php 2/** 3 * This file is part of the FreeDSx Socket package. 4 * 5 * (c) Chad Sikorra <Chad.Sikorra@gmail.com> 6 * 7 * For the full copyright and license information, please view the LICENSE 8 * file that was distributed with this source code. 9 */ 10 11namespace FreeDSx\Socket; 12 13use FreeDSx\Socket\Exception\ConnectionException; 14 15/** 16 * Given a selection of hosts, connect to one and return the Socket. 17 * 18 * @author Chad Sikorra <Chad.Sikorra@gmail.com> 19 */ 20class SocketPool 21{ 22 /** 23 * @var array 24 */ 25 protected $options = [ 26 'servers' => [], 27 'port' => 389, 28 'timeout_connect' => 1, 29 ]; 30 31 /** 32 * @var array 33 */ 34 protected $socketOpts = [ 35 'use_ssl', 36 'ssl_validate_cert', 37 'ssl_allow_self_signed', 38 'ssl_ca_cert', 39 'ssl_cert', 40 'ssl_peer_name', 41 'timeout_connect', 42 'timeout_read', 43 'port', 44 'transport', 45 ]; 46 47 /** 48 * @param array $options 49 */ 50 public function __construct(array $options) 51 { 52 $this->options = \array_merge($this->options, $options); 53 } 54 55 /** 56 * @throws ConnectionException 57 */ 58 public function connect(string $hostname = '') : Socket 59 { 60 $hosts = ($hostname !== '') ? [$hostname] : (array) $this->options['servers']; 61 62 $lastEx = null; 63 $socket = null; 64 foreach ($hosts as $host) { 65 try { 66 $socket = Socket::create( 67 $host, 68 $this->getSocketOptions() 69 ); 70 break; 71 } catch (\Exception $e) { 72 $lastEx = $e; 73 } 74 } 75 76 if ($socket === null) { 77 throw new ConnectionException(sprintf( 78 'Unable to connect to server(s): %s', 79 implode(',', $hosts) 80 ), 0, $lastEx); 81 } 82 83 return $socket; 84 } 85 86 /** 87 * @return array 88 */ 89 protected function getSocketOptions() : array 90 { 91 $opts = []; 92 93 foreach ($this->socketOpts as $name) { 94 if (isset($this->options[$name])) { 95 $opts[$name] = $this->options[$name]; 96 } 97 } 98 99 return $opts; 100 } 101} 102