mirror of
https://github.com/Seldaek/monolog.git
synced 2025-08-01 02:40:24 +02:00
Fixing the socket mess, maybe.
This commit is contained in:
@@ -14,6 +14,7 @@ namespace Monolog\Handler;
|
|||||||
use Monolog\Formatter\FlowdockFormatter;
|
use Monolog\Formatter\FlowdockFormatter;
|
||||||
use Monolog\Test\TestCase;
|
use Monolog\Test\TestCase;
|
||||||
use Monolog\Logger;
|
use Monolog\Logger;
|
||||||
|
use Monolog\Util\LocalSocket;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Dominik Liebler <liebler.dominik@gmail.com>
|
* @author Dominik Liebler <liebler.dominik@gmail.com>
|
||||||
@@ -42,7 +43,7 @@ class FlowdockHandlerTest extends TestCase
|
|||||||
{
|
{
|
||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/POST \/v1\/messages\/team_inbox\/.* HTTP\/1.1\\r\\nHost: api.flowdock.com\\r\\nContent-Type: application\/json\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
$this->assertRegexp('/POST \/v1\/messages\/team_inbox\/.* HTTP\/1.1\\r\\nHost: api.flowdock.com\\r\\nContent-Type: application\/json\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
||||||
|
|
||||||
@@ -61,28 +62,7 @@ class FlowdockHandlerTest extends TestCase
|
|||||||
|
|
||||||
private function initHandlerAndSocket($token = 'myToken')
|
private function initHandlerAndSocket($token = 'myToken')
|
||||||
{
|
{
|
||||||
$tmpFile = sys_get_temp_dir().'/monolog-test-socket.php';
|
$this->socket = LocalSocket::initSocket();
|
||||||
file_put_contents($tmpFile, <<<'SCRIPT'
|
|
||||||
<?php
|
|
||||||
|
|
||||||
$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
|
|
||||||
socket_bind($sock, '127.0.0.1', 51984);
|
|
||||||
socket_listen($sock);
|
|
||||||
|
|
||||||
while (true) {
|
|
||||||
$res = socket_accept($sock);
|
|
||||||
socket_set_option($res, SOL_SOCKET, SO_RCVTIMEO, array("sec" => 0, "usec" => 500));
|
|
||||||
while ($read = socket_read($res, 1024)) {
|
|
||||||
echo $read;
|
|
||||||
}
|
|
||||||
socket_close($res);
|
|
||||||
}
|
|
||||||
SCRIPT
|
|
||||||
);
|
|
||||||
|
|
||||||
$this->socket = new \Symfony\Component\Process\Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($tmpFile));
|
|
||||||
$this->socket->start();
|
|
||||||
|
|
||||||
$this->handler = new FlowdockHandler($token);
|
$this->handler = new FlowdockHandler($token);
|
||||||
|
|
||||||
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'connectionString');
|
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'connectionString');
|
||||||
@@ -92,18 +72,8 @@ SCRIPT
|
|||||||
$this->handler->setFormatter(new FlowdockFormatter('test_source', 'source@test.com'));
|
$this->handler->setFormatter(new FlowdockFormatter('test_source', 'source@test.com'));
|
||||||
}
|
}
|
||||||
|
|
||||||
private function closeSocket()
|
|
||||||
{
|
|
||||||
$this->socket->stop();
|
|
||||||
|
|
||||||
return $this->socket->getOutput();
|
|
||||||
}
|
|
||||||
|
|
||||||
public function tearDown()
|
public function tearDown()
|
||||||
{
|
{
|
||||||
if (isset($this->socket)) {
|
unset($this->socket, $this->handler);
|
||||||
$this->closeSocket();
|
|
||||||
unset($this->socket);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -13,6 +13,7 @@ namespace Monolog\Handler;
|
|||||||
|
|
||||||
use Monolog\Test\TestCase;
|
use Monolog\Test\TestCase;
|
||||||
use Monolog\Logger;
|
use Monolog\Logger;
|
||||||
|
use Monolog\Util\LocalSocket;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Rafael Dohms <rafael@doh.ms>
|
* @author Rafael Dohms <rafael@doh.ms>
|
||||||
@@ -28,51 +29,13 @@ class HipChatHandlerTest extends TestCase
|
|||||||
{
|
{
|
||||||
$this->initHandlerAndSocket('myToken', 'room1', 'Monolog', false, 'hipchat.foo.bar', 'v2');
|
$this->initHandlerAndSocket('myToken', 'room1', 'Monolog', false, 'hipchat.foo.bar', 'v2');
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
|
|
||||||
$content = $this->socket->getOutput();
|
|
||||||
$this->assertRegexp('/POST \/v2\/room\/room1\/notification\?auth_token=.* HTTP\/1.1\\r\\nHost: hipchat.foo.bar\\r\\nContent-Type: application\/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
|
||||||
|
|
||||||
return $content;
|
|
||||||
}
|
|
||||||
|
|
||||||
public function testWriteV2Notify()
|
|
||||||
{
|
|
||||||
$this->initHandlerAndSocket('myToken', 'room1', 'Monolog', true, 'hipchat.foo.bar', 'v2');
|
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
|
||||||
$content = $this->socket->getOutput();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/POST \/v2\/room\/room1\/notification\?auth_token=.* HTTP\/1.1\\r\\nHost: hipchat.foo.bar\\r\\nContent-Type: application\/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
$this->assertRegexp('{POST /v2/room/room1/notification\?auth_token=.* HTTP/1.1\\r\\nHost: hipchat.foo.bar\\r\\nContent-Type: application/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n}', $content);
|
||||||
|
|
||||||
return $content;
|
return $content;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function testRoomSpaces()
|
|
||||||
{
|
|
||||||
$this->initHandlerAndSocket('myToken', 'room name', 'Monolog', false, 'hipchat.foo.bar', 'v2');
|
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
|
||||||
$content = $this->socket->getOutput();
|
|
||||||
|
|
||||||
$this->assertRegexp('/POST \/v2\/room\/room%20name\/notification\?auth_token=.* HTTP\/1.1\\r\\nHost: hipchat.foo.bar\\r\\nContent-Type: application\/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
|
||||||
|
|
||||||
return $content;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @depends testWriteHeader
|
|
||||||
*/
|
|
||||||
public function testWriteContent($content)
|
|
||||||
{
|
|
||||||
$this->assertRegexp('/notify=0&message=test1&message_format=text&color=red&room_id=room1&from=Monolog$/', $content);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @depends testWriteCustomHostHeader
|
|
||||||
*/
|
|
||||||
public function testWriteContentNotify($content)
|
|
||||||
{
|
|
||||||
$this->assertRegexp('/notify=1&message=test1&message_format=text&color=red&room_id=room1&from=Monolog$/', $content);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @depends testWriteV2
|
* @depends testWriteV2
|
||||||
*/
|
*/
|
||||||
@@ -81,6 +44,17 @@ class HipChatHandlerTest extends TestCase
|
|||||||
$this->assertRegexp('/notify=false&message=test1&message_format=text&color=red&from=Monolog$/', $content);
|
$this->assertRegexp('/notify=false&message=test1&message_format=text&color=red&from=Monolog$/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function testWriteV2Notify()
|
||||||
|
{
|
||||||
|
$this->initHandlerAndSocket('myToken', 'room2', 'Monolog', true, 'hipchat.foo.bar', 'v2');
|
||||||
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
|
$this->assertRegexp('{POST /v2/room/room2/notification\?auth_token=.* HTTP/1.1\\r\\nHost: hipchat.foo.bar\\r\\nContent-Type: application/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n}', $content);
|
||||||
|
|
||||||
|
return $content;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @depends testWriteV2Notify
|
* @depends testWriteV2Notify
|
||||||
*/
|
*/
|
||||||
@@ -89,6 +63,17 @@ class HipChatHandlerTest extends TestCase
|
|||||||
$this->assertRegexp('/notify=true&message=test1&message_format=text&color=red&from=Monolog$/', $content);
|
$this->assertRegexp('/notify=true&message=test1&message_format=text&color=red&from=Monolog$/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function testRoomSpaces()
|
||||||
|
{
|
||||||
|
$this->initHandlerAndSocket('myToken', 'room name', 'Monolog', false, 'hipchat.foo.bar', 'v2');
|
||||||
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
|
$this->assertRegexp('{POST /v2/room/room%20name/notification\?auth_token=.* HTTP/1.1\\r\\nHost: hipchat.foo.bar\\r\\nContent-Type: application/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n}', $content);
|
||||||
|
|
||||||
|
return $content;
|
||||||
|
}
|
||||||
|
|
||||||
public function testWriteContentV2WithoutName()
|
public function testWriteContentV2WithoutName()
|
||||||
{
|
{
|
||||||
$this->initHandlerAndSocket('myToken', 'room1', null, false, 'hipchat.foo.bar', 'v2');
|
$this->initHandlerAndSocket('myToken', 'room1', null, false, 'hipchat.foo.bar', 'v2');
|
||||||
@@ -198,28 +183,7 @@ class HipChatHandlerTest extends TestCase
|
|||||||
|
|
||||||
private function initHandlerAndSocket($token = 'myToken', $room = 'room1', $name = 'Monolog', $notify = false, $host = 'api.hipchat.com', $version = 'v1')
|
private function initHandlerAndSocket($token = 'myToken', $room = 'room1', $name = 'Monolog', $notify = false, $host = 'api.hipchat.com', $version = 'v1')
|
||||||
{
|
{
|
||||||
$tmpFile = sys_get_temp_dir().'/monolog-test-socket.php';
|
$this->socket = LocalSocket::initSocket();
|
||||||
file_put_contents($tmpFile, <<<'SCRIPT'
|
|
||||||
<?php
|
|
||||||
|
|
||||||
$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
|
|
||||||
socket_bind($sock, '127.0.0.1', 51984);
|
|
||||||
socket_listen($sock);
|
|
||||||
|
|
||||||
while (true) {
|
|
||||||
$res = socket_accept($sock);
|
|
||||||
socket_set_option($res, SOL_SOCKET, SO_RCVTIMEO, array("sec" => 0, "usec" => 500));
|
|
||||||
while ($read = socket_read($res, 1024)) {
|
|
||||||
echo $read;
|
|
||||||
}
|
|
||||||
socket_close($res);
|
|
||||||
}
|
|
||||||
SCRIPT
|
|
||||||
);
|
|
||||||
|
|
||||||
$this->socket = new \Symfony\Component\Process\Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($tmpFile));
|
|
||||||
$this->socket->start();
|
|
||||||
|
|
||||||
$this->handler = new HipChatHandler($token, $room, $name, $notify, Logger::DEBUG, true, true, 'text', $host, $version);
|
$this->handler = new HipChatHandler($token, $room, $name, $notify, Logger::DEBUG, true, true, 'text', $host, $version);
|
||||||
|
|
||||||
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'connectionString');
|
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'connectionString');
|
||||||
@@ -229,16 +193,8 @@ SCRIPT
|
|||||||
$this->handler->setFormatter($this->getIdentityFormatter());
|
$this->handler->setFormatter($this->getIdentityFormatter());
|
||||||
}
|
}
|
||||||
|
|
||||||
private function closeSocket()
|
|
||||||
{
|
|
||||||
$this->socket->stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
public function tearDown()
|
public function tearDown()
|
||||||
{
|
{
|
||||||
if (isset($this->socket)) {
|
unset($this->socket, $this->handler);
|
||||||
$this->closeSocket();
|
|
||||||
unset($this->socket);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -13,6 +13,7 @@ namespace Monolog\Handler;
|
|||||||
|
|
||||||
use Monolog\Test\TestCase;
|
use Monolog\Test\TestCase;
|
||||||
use Monolog\Logger;
|
use Monolog\Logger;
|
||||||
|
use Monolog\Util\LocalSocket;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Robert Kaufmann III <rok3@rok3.me>
|
* @author Robert Kaufmann III <rok3@rok3.me>
|
||||||
@@ -34,7 +35,7 @@ class LogEntriesHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'Critical write test'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'Critical write test'));
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
$this->assertRegexp('/testToken \[\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d{6}\+00:00\] test.CRITICAL: Critical write test/', $content);
|
$this->assertRegexp('/testToken \[\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d{6}\+00:00\] test.CRITICAL: Critical write test/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -48,33 +49,13 @@ class LogEntriesHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handleBatch($records);
|
$this->handler->handleBatch($records);
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
$this->assertRegexp('/(testToken \[\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d{6}\+00:00\] .* \[\] \[\]\n){3}/', $content);
|
$this->assertRegexp('/(testToken \[\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d{6}\+00:00\] .* \[\] \[\]\n){3}/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
private function initHandlerAndSocket()
|
private function initHandlerAndSocket()
|
||||||
{
|
{
|
||||||
$tmpFile = sys_get_temp_dir().'/monolog-test-socket.php';
|
$this->socket = LocalSocket::initSocket();
|
||||||
file_put_contents($tmpFile, <<<'SCRIPT'
|
|
||||||
<?php
|
|
||||||
|
|
||||||
$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
|
|
||||||
socket_bind($sock, '127.0.0.1', 51984);
|
|
||||||
socket_listen($sock);
|
|
||||||
|
|
||||||
while (true) {
|
|
||||||
$res = socket_accept($sock);
|
|
||||||
socket_set_option($res, SOL_SOCKET, SO_RCVTIMEO, array("sec" => 0, "usec" => 500));
|
|
||||||
while ($read = socket_read($res, 1024)) {
|
|
||||||
echo $read;
|
|
||||||
}
|
|
||||||
socket_close($res);
|
|
||||||
}
|
|
||||||
SCRIPT
|
|
||||||
);
|
|
||||||
|
|
||||||
$this->socket = new \Symfony\Component\Process\Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($tmpFile));
|
|
||||||
$this->socket->start();
|
|
||||||
|
|
||||||
$useSSL = extension_loaded('openssl');
|
$useSSL = extension_loaded('openssl');
|
||||||
$this->handler = new LogEntriesHandler('testToken', $useSSL, Logger::DEBUG, true);
|
$this->handler = new LogEntriesHandler('testToken', $useSSL, Logger::DEBUG, true);
|
||||||
@@ -84,18 +65,8 @@ SCRIPT
|
|||||||
$reflectionProperty->setValue($this->handler, '127.0.0.1:51984');
|
$reflectionProperty->setValue($this->handler, '127.0.0.1:51984');
|
||||||
}
|
}
|
||||||
|
|
||||||
private function closeSocket()
|
|
||||||
{
|
|
||||||
$this->socket->stop();
|
|
||||||
|
|
||||||
return $this->socket->getOutput();
|
|
||||||
}
|
|
||||||
|
|
||||||
public function tearDown()
|
public function tearDown()
|
||||||
{
|
{
|
||||||
if (isset($this->socket)) {
|
unset($this->socket, $this->handler);
|
||||||
$this->closeSocket();
|
|
||||||
unset($this->socket);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -13,6 +13,7 @@ namespace Monolog\Handler;
|
|||||||
|
|
||||||
use Monolog\Test\TestCase;
|
use Monolog\Test\TestCase;
|
||||||
use Monolog\Logger;
|
use Monolog\Logger;
|
||||||
|
use Monolog\Util\LocalSocket;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Julien Breux <julien.breux@gmail.com>
|
* @author Julien Breux <julien.breux@gmail.com>
|
||||||
@@ -34,7 +35,7 @@ class LogmaticHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'Critical write test'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'Critical write test'));
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/testToken {"message":"Critical write test","context":\[\],"level":500,"level_name":"CRITICAL","channel":"test","datetime":"(.*)","extra":\[\],"hostname":"testHostname","appname":"testAppname"}/', $content);
|
$this->assertRegexp('/testToken {"message":"Critical write test","context":\[\],"level":500,"level_name":"CRITICAL","channel":"test","datetime":"(.*)","extra":\[\],"hostname":"testHostname","appname":"testAppname"}/', $content);
|
||||||
}
|
}
|
||||||
@@ -49,34 +50,14 @@ class LogmaticHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handleBatch($records);
|
$this->handler->handleBatch($records);
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/testToken {"message":"test","context":\[\],"level":300,"level_name":"WARNING","channel":"test","datetime":"(.*)","extra":\[\],"hostname":"testHostname","appname":"testAppname"}/', $content);
|
$this->assertRegexp('/testToken {"message":"test","context":\[\],"level":300,"level_name":"WARNING","channel":"test","datetime":"(.*)","extra":\[\],"hostname":"testHostname","appname":"testAppname"}/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
private function initHandlerAndSocket()
|
private function initHandlerAndSocket()
|
||||||
{
|
{
|
||||||
$tmpFile = sys_get_temp_dir().'/monolog-test-socket.php';
|
$this->socket = LocalSocket::initSocket();
|
||||||
file_put_contents($tmpFile, <<<'SCRIPT'
|
|
||||||
<?php
|
|
||||||
|
|
||||||
$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
|
|
||||||
socket_bind($sock, '127.0.0.1', 51984);
|
|
||||||
socket_listen($sock);
|
|
||||||
|
|
||||||
while (true) {
|
|
||||||
$res = socket_accept($sock);
|
|
||||||
socket_set_option($res, SOL_SOCKET, SO_RCVTIMEO, array("sec" => 0, "usec" => 500));
|
|
||||||
while ($read = socket_read($res, 1024)) {
|
|
||||||
echo $read;
|
|
||||||
}
|
|
||||||
socket_close($res);
|
|
||||||
}
|
|
||||||
SCRIPT
|
|
||||||
);
|
|
||||||
|
|
||||||
$this->socket = new \Symfony\Component\Process\Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($tmpFile));
|
|
||||||
$this->socket->start();
|
|
||||||
|
|
||||||
$useSSL = extension_loaded('openssl');
|
$useSSL = extension_loaded('openssl');
|
||||||
$this->handler = new LogmaticHandler('testToken', 'testHostname', 'testAppname', $useSSL, Logger::DEBUG, true);
|
$this->handler = new LogmaticHandler('testToken', 'testHostname', 'testAppname', $useSSL, Logger::DEBUG, true);
|
||||||
@@ -86,18 +67,8 @@ SCRIPT
|
|||||||
$reflectionProperty->setValue($this->handler, '127.0.0.1:51984');
|
$reflectionProperty->setValue($this->handler, '127.0.0.1:51984');
|
||||||
}
|
}
|
||||||
|
|
||||||
private function closeSocket()
|
|
||||||
{
|
|
||||||
$this->socket->stop();
|
|
||||||
|
|
||||||
return $this->socket->getOutput();
|
|
||||||
}
|
|
||||||
|
|
||||||
public function tearDown()
|
public function tearDown()
|
||||||
{
|
{
|
||||||
if (isset($this->socket)) {
|
unset($this->socket, $this->handler);
|
||||||
$this->closeSocket();
|
|
||||||
unset($this->socket);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -13,6 +13,7 @@ namespace Monolog\Handler;
|
|||||||
|
|
||||||
use Monolog\Test\TestCase;
|
use Monolog\Test\TestCase;
|
||||||
use Monolog\Logger;
|
use Monolog\Logger;
|
||||||
|
use Monolog\Util\LocalSocket;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Almost all examples (expected header, titles, messages) taken from
|
* Almost all examples (expected header, titles, messages) taken from
|
||||||
@@ -30,7 +31,7 @@ class PushoverHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->setHighPriorityLevel(Logger::EMERGENCY); // skip priority notifications
|
$this->handler->setHighPriorityLevel(Logger::EMERGENCY); // skip priority notifications
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/POST \/1\/messages.json HTTP\/1.1\\r\\nHost: api.pushover.net\\r\\nContent-Type: application\/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
$this->assertRegexp('/POST \/1\/messages.json HTTP\/1.1\\r\\nHost: api.pushover.net\\r\\nContent-Type: application\/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
||||||
|
|
||||||
@@ -49,7 +50,7 @@ class PushoverHandlerTest extends TestCase
|
|||||||
{
|
{
|
||||||
$this->initHandlerAndSocket('myToken', 'myUser', 'Backup finished - SQL1');
|
$this->initHandlerAndSocket('myToken', 'myUser', 'Backup finished - SQL1');
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/title=Backup\+finished\+-\+SQL1/', $content);
|
$this->assertRegexp('/title=Backup\+finished\+-\+SQL1/', $content);
|
||||||
}
|
}
|
||||||
@@ -59,7 +60,7 @@ class PushoverHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->setHighPriorityLevel(Logger::EMERGENCY); // skip priority notifications
|
$this->handler->setHighPriorityLevel(Logger::EMERGENCY); // skip priority notifications
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'Backup of database "example" finished in 16 minutes.'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'Backup of database "example" finished in 16 minutes.'));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/message=Backup\+of\+database\+%22example%22\+finished\+in\+16\+minutes\./', $content);
|
$this->assertRegexp('/message=Backup\+of\+database\+%22example%22\+finished\+in\+16\+minutes\./', $content);
|
||||||
}
|
}
|
||||||
@@ -70,7 +71,7 @@ class PushoverHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->setHighPriorityLevel(Logger::EMERGENCY); // skip priority notifications
|
$this->handler->setHighPriorityLevel(Logger::EMERGENCY); // skip priority notifications
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, $message));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, $message));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$expectedMessage = substr($message, 0, 505);
|
$expectedMessage = substr($message, 0, 505);
|
||||||
|
|
||||||
@@ -81,7 +82,7 @@ class PushoverHandlerTest extends TestCase
|
|||||||
{
|
{
|
||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/token=myToken&user=myUser&message=test1&title=Monolog×tamp=\d{10}&priority=1$/', $content);
|
$this->assertRegexp('/token=myToken&user=myUser&message=test1&title=Monolog×tamp=\d{10}&priority=1$/', $content);
|
||||||
}
|
}
|
||||||
@@ -90,16 +91,18 @@ class PushoverHandlerTest extends TestCase
|
|||||||
{
|
{
|
||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handle($this->getRecord(Logger::EMERGENCY, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::EMERGENCY, 'test1'));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/token=myToken&user=myUser&message=test1&title=Monolog×tamp=\d{10}&priority=2&retry=30&expire=25200$/', $content);
|
$this->assertRegexp('/token=myToken&user=myUser&message=test1&title=Monolog×tamp=\d{10}&priority=2&retry=30&expire=25200$/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function testWriteToMultipleUsers()
|
public function testWriteToMultipleUsers()
|
||||||
{
|
{
|
||||||
|
$this->markTestIncomplete('LocalSocket buffer does not support multiple-connections');
|
||||||
|
|
||||||
$this->initHandlerAndSocket('myToken', ['userA', 'userB']);
|
$this->initHandlerAndSocket('myToken', ['userA', 'userB']);
|
||||||
$this->handler->handle($this->getRecord(Logger::EMERGENCY, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::EMERGENCY, 'test1'));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/token=myToken&user=userA&message=test1&title=Monolog×tamp=\d{10}&priority=2&retry=30&expire=25200POST/', $content);
|
$this->assertRegexp('/token=myToken&user=userA&message=test1&title=Monolog×tamp=\d{10}&priority=2&retry=30&expire=25200POST/', $content);
|
||||||
$this->assertRegexp('/token=myToken&user=userB&message=test1&title=Monolog×tamp=\d{10}&priority=2&retry=30&expire=25200$/', $content);
|
$this->assertRegexp('/token=myToken&user=userB&message=test1&title=Monolog×tamp=\d{10}&priority=2&retry=30&expire=25200$/', $content);
|
||||||
@@ -107,28 +110,7 @@ class PushoverHandlerTest extends TestCase
|
|||||||
|
|
||||||
private function initHandlerAndSocket($token = 'myToken', $user = 'myUser', $title = 'Monolog')
|
private function initHandlerAndSocket($token = 'myToken', $user = 'myUser', $title = 'Monolog')
|
||||||
{
|
{
|
||||||
$tmpFile = sys_get_temp_dir().'/monolog-test-socket.php';
|
$this->socket = LocalSocket::initSocket();
|
||||||
file_put_contents($tmpFile, <<<'SCRIPT'
|
|
||||||
<?php
|
|
||||||
|
|
||||||
$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
|
|
||||||
socket_bind($sock, '127.0.0.1', 51984);
|
|
||||||
socket_listen($sock);
|
|
||||||
|
|
||||||
while (true) {
|
|
||||||
$res = socket_accept($sock);
|
|
||||||
socket_set_option($res, SOL_SOCKET, SO_RCVTIMEO, array("sec" => 0, "usec" => 500));
|
|
||||||
while ($read = socket_read($res, 1024)) {
|
|
||||||
echo $read;
|
|
||||||
}
|
|
||||||
socket_close($res);
|
|
||||||
}
|
|
||||||
SCRIPT
|
|
||||||
);
|
|
||||||
|
|
||||||
$this->socket = new \Symfony\Component\Process\Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($tmpFile));
|
|
||||||
$this->socket->start();
|
|
||||||
|
|
||||||
$this->handler = new PushoverHandler($token, $user, $title);
|
$this->handler = new PushoverHandler($token, $user, $title);
|
||||||
|
|
||||||
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'connectionString');
|
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'connectionString');
|
||||||
@@ -138,18 +120,8 @@ SCRIPT
|
|||||||
$this->handler->setFormatter($this->getIdentityFormatter());
|
$this->handler->setFormatter($this->getIdentityFormatter());
|
||||||
}
|
}
|
||||||
|
|
||||||
private function closeSocket()
|
|
||||||
{
|
|
||||||
$this->socket->stop();
|
|
||||||
|
|
||||||
return $this->socket->getOutput();
|
|
||||||
}
|
|
||||||
|
|
||||||
public function tearDown()
|
public function tearDown()
|
||||||
{
|
{
|
||||||
if (isset($this->socket)) {
|
unset($this->socket, $this->handler);
|
||||||
$this->closeSocket();
|
|
||||||
unset($this->socket);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -14,6 +14,7 @@ namespace Monolog\Handler;
|
|||||||
use Monolog\Test\TestCase;
|
use Monolog\Test\TestCase;
|
||||||
use Monolog\Logger;
|
use Monolog\Logger;
|
||||||
use Monolog\Formatter\LineFormatter;
|
use Monolog\Formatter\LineFormatter;
|
||||||
|
use Monolog\Util\LocalSocket;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Greg Kedzierski <greg@gregkedzierski.com>
|
* @author Greg Kedzierski <greg@gregkedzierski.com>
|
||||||
@@ -43,7 +44,7 @@ class SlackHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
$this->assertRegexp('/POST \/api\/chat.postMessage HTTP\/1.1\\r\\nHost: slack.com\\r\\nContent-Type: application\/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
$this->assertRegexp('/POST \/api\/chat.postMessage HTTP\/1.1\\r\\nHost: slack.com\\r\\nContent-Type: application\/x-www-form-urlencoded\\r\\nContent-Length: \d{2,4}\\r\\n\\r\\n/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -52,7 +53,7 @@ class SlackHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
$this->assertRegexp('/token=myToken&channel=channel1&username=Monolog&text=&attachments=.*$/', $content);
|
$this->assertRegexp('/token=myToken&channel=channel1&username=Monolog&text=&attachments=.*$/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -60,12 +61,12 @@ class SlackHandlerTest extends TestCase
|
|||||||
{
|
{
|
||||||
$this->initHandlerAndSocket('myToken', 'channel1', 'Monolog', false);
|
$this->initHandlerAndSocket('myToken', 'channel1', 'Monolog', false);
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->initHandlerAndSocket('myToken', 'channel1', 'Monolog', false);
|
$this->initHandlerAndSocket('myToken', 'channel1', 'Monolog', false);
|
||||||
$this->handler->setFormatter(new LineFormatter('foo--%message%'));
|
$this->handler->setFormatter(new LineFormatter('foo--%message%'));
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test2'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test2'));
|
||||||
$content2 = $this->closeSocket();
|
$content2 = $this->socket->getOutput();
|
||||||
|
|
||||||
$this->assertRegexp('/token=myToken&channel=channel1&username=Monolog&text=test1.*$/', $content);
|
$this->assertRegexp('/token=myToken&channel=channel1&username=Monolog&text=test1.*$/', $content);
|
||||||
$this->assertRegexp('/token=myToken&channel=channel1&username=Monolog&text=foo--test2.*$/', $content2);
|
$this->assertRegexp('/token=myToken&channel=channel1&username=Monolog&text=foo--test2.*$/', $content2);
|
||||||
@@ -76,7 +77,7 @@ class SlackHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket('myToken', 'channel1', 'Monolog', true, 'alien');
|
$this->initHandlerAndSocket('myToken', 'channel1', 'Monolog', true, 'alien');
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
$this->assertRegexp('/icon_emoji=%3Aalien%3A$/', $content);
|
$this->assertRegexp('/icon_emoji=%3Aalien%3A$/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -88,7 +89,7 @@ class SlackHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->handler->handle($this->getRecord($level, 'test1'));
|
$this->handler->handle($this->getRecord($level, 'test1'));
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
$this->assertRegexp('/color%22%3A%22'.$expectedColor.'/', $content);
|
$this->assertRegexp('/color%22%3A%22'.$expectedColor.'/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -97,7 +98,7 @@ class SlackHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket('myToken', 'channel1', 'Monolog', false);
|
$this->initHandlerAndSocket('myToken', 'channel1', 'Monolog', false);
|
||||||
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
$this->handler->handle($this->getRecord(Logger::CRITICAL, 'test1'));
|
||||||
|
|
||||||
$content = $this->closeSocket();
|
$content = $this->socket->getOutput();
|
||||||
$this->assertRegexp('/text=test1/', $content);
|
$this->assertRegexp('/text=test1/', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -117,28 +118,7 @@ class SlackHandlerTest extends TestCase
|
|||||||
|
|
||||||
private function initHandlerAndSocket($token = 'myToken', $channel = 'channel1', $username = 'Monolog', $useAttachment = true, $iconEmoji = null, $useShortAttachment = false, $includeExtra = false)
|
private function initHandlerAndSocket($token = 'myToken', $channel = 'channel1', $username = 'Monolog', $useAttachment = true, $iconEmoji = null, $useShortAttachment = false, $includeExtra = false)
|
||||||
{
|
{
|
||||||
$tmpFile = sys_get_temp_dir().'/monolog-test-socket.php';
|
$this->socket = LocalSocket::initSocket();
|
||||||
file_put_contents($tmpFile, <<<'SCRIPT'
|
|
||||||
<?php
|
|
||||||
|
|
||||||
$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
|
|
||||||
socket_bind($sock, '127.0.0.1', 51984);
|
|
||||||
socket_listen($sock);
|
|
||||||
|
|
||||||
while (true) {
|
|
||||||
$res = socket_accept($sock);
|
|
||||||
socket_set_option($res, SOL_SOCKET, SO_RCVTIMEO, array("sec" => 0, "usec" => 500));
|
|
||||||
while ($read = socket_read($res, 1024)) {
|
|
||||||
echo $read;
|
|
||||||
}
|
|
||||||
socket_close($res);
|
|
||||||
}
|
|
||||||
SCRIPT
|
|
||||||
);
|
|
||||||
|
|
||||||
$this->socket = new \Symfony\Component\Process\Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($tmpFile));
|
|
||||||
$this->socket->start();
|
|
||||||
|
|
||||||
$this->handler = new SlackHandler($token, $channel, $username, $useAttachment, $iconEmoji, Logger::DEBUG, true, $useShortAttachment, $includeExtra);
|
$this->handler = new SlackHandler($token, $channel, $username, $useAttachment, $iconEmoji, Logger::DEBUG, true, $useShortAttachment, $includeExtra);
|
||||||
|
|
||||||
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'connectionString');
|
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'connectionString');
|
||||||
@@ -148,18 +128,8 @@ SCRIPT
|
|||||||
$this->handler->setFormatter($this->getIdentityFormatter());
|
$this->handler->setFormatter($this->getIdentityFormatter());
|
||||||
}
|
}
|
||||||
|
|
||||||
private function closeSocket()
|
|
||||||
{
|
|
||||||
$this->socket->stop();
|
|
||||||
|
|
||||||
return $this->socket->getOutput();
|
|
||||||
}
|
|
||||||
|
|
||||||
public function tearDown()
|
public function tearDown()
|
||||||
{
|
{
|
||||||
if (isset($this->socket)) {
|
unset($this->socket, $this->handler);
|
||||||
$this->closeSocket();
|
|
||||||
unset($this->socket);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -13,6 +13,7 @@ namespace Monolog\Handler;
|
|||||||
|
|
||||||
use Monolog\Test\TestCase;
|
use Monolog\Test\TestCase;
|
||||||
use Monolog\Logger;
|
use Monolog\Logger;
|
||||||
|
use Monolog\Util\LocalSocket;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Pablo de Leon Belloc <pablolb@gmail.com>
|
* @author Pablo de Leon Belloc <pablolb@gmail.com>
|
||||||
@@ -112,39 +113,19 @@ class SocketHandlerTest extends TestCase
|
|||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
$this->writeRecord('Hello world');
|
$this->writeRecord('Hello world');
|
||||||
|
|
||||||
$reflectionProperty = new \ReflectionProperty('\Monolog\Handler\SocketHandler', 'resource');
|
LocalSocket::shutdownSocket();
|
||||||
$reflectionProperty->setAccessible(true);
|
|
||||||
fclose($reflectionProperty->getValue($this->handler));
|
|
||||||
|
|
||||||
$this->writeRecord('Hello world');
|
$this->writeRecord('Hello world2');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
public function testWriteRealSocket()
|
||||||
* @expectedException RuntimeException
|
|
||||||
*/
|
|
||||||
public function testWriteFailsOnIncompleteWrite()
|
|
||||||
{
|
{
|
||||||
$this->initHandlerAndSocket();
|
$this->initHandlerAndSocket();
|
||||||
|
$this->writeRecord("foo bar baz content test1\n");
|
||||||
|
$this->writeRecord("foo bar baz content test2\n");
|
||||||
|
$this->writeRecord("foo bar baz content test3\n");
|
||||||
|
|
||||||
$this->handler->setWritingTimeout(1);
|
$this->assertEquals("foo bar baz content test1\nfoo bar baz content test2\nfoo bar baz content test3\n", $this->socket->getOutput());
|
||||||
|
|
||||||
// the socket will close itself after processing 10000 bytes so while processing b, and then c write fails
|
|
||||||
$this->writeRecord(str_repeat("aaaaaaaaaa\n", 700));
|
|
||||||
$this->assertTrue(true); // asserting to make sure we reach this point
|
|
||||||
$this->writeRecord(str_repeat("bbbbbbbbbb\n", 700));
|
|
||||||
$this->assertTrue(true); // asserting to make sure we reach this point
|
|
||||||
$this->writeRecord(str_repeat("cccccccccc\n", 700));
|
|
||||||
$this->fail('The test should not reach here');
|
|
||||||
}
|
|
||||||
|
|
||||||
public function testWriteWithMemoryFile()
|
|
||||||
{
|
|
||||||
$this->initHandlerAndSocket();
|
|
||||||
$this->writeRecord('test1');
|
|
||||||
$this->writeRecord('test2');
|
|
||||||
$this->writeRecord('test3');
|
|
||||||
$this->closeSocket();
|
|
||||||
$this->assertEquals('test1test2test3', $this->socket->getOutput());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public function testClose()
|
public function testClose()
|
||||||
@@ -187,47 +168,14 @@ class SocketHandlerTest extends TestCase
|
|||||||
|
|
||||||
private function initHandlerAndSocket()
|
private function initHandlerAndSocket()
|
||||||
{
|
{
|
||||||
$tmpFile = sys_get_temp_dir().'/monolog-test-socket.php';
|
$this->socket = LocalSocket::initSocket();
|
||||||
file_put_contents($tmpFile, <<<'SCRIPT'
|
|
||||||
<?php
|
|
||||||
|
|
||||||
$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
|
|
||||||
socket_bind($sock, '127.0.0.1', 51984);
|
|
||||||
socket_listen($sock);
|
|
||||||
$res = socket_accept($sock);
|
|
||||||
socket_set_option($res, SOL_SOCKET, SO_RCVTIMEO, array("sec" => 0, "usec" => 500));
|
|
||||||
$bytesRead = 0;
|
|
||||||
while ($read = socket_read($res, 1024)) {
|
|
||||||
echo $read;
|
|
||||||
$bytesRead += strlen($read);
|
|
||||||
if ($bytesRead > 10000) {
|
|
||||||
socket_close($res);
|
|
||||||
socket_close($sock);
|
|
||||||
die('CLOSED');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
echo 'EXIT';
|
|
||||||
socket_close($res);
|
|
||||||
SCRIPT
|
|
||||||
);
|
|
||||||
|
|
||||||
$this->socket = new \Symfony\Component\Process\Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($tmpFile));
|
|
||||||
$this->socket->start();
|
|
||||||
|
|
||||||
$this->handler = new SocketHandler('tcp://127.0.0.1:51984');
|
$this->handler = new SocketHandler('tcp://127.0.0.1:51984');
|
||||||
$this->handler->setFormatter($this->getIdentityFormatter());
|
$this->handler->setFormatter($this->getIdentityFormatter());
|
||||||
}
|
}
|
||||||
|
|
||||||
private function closeSocket()
|
|
||||||
{
|
|
||||||
$this->socket->stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
public function tearDown()
|
public function tearDown()
|
||||||
{
|
{
|
||||||
if (isset($this->socket)) {
|
unset($this->socket, $this->handler);
|
||||||
$this->closeSocket();
|
|
||||||
unset($this->socket);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -13,6 +13,7 @@ namespace Monolog\Handler;
|
|||||||
|
|
||||||
use Monolog\Test\TestCase;
|
use Monolog\Test\TestCase;
|
||||||
use Monolog\Handler\SyslogUdp\UdpSocket;
|
use Monolog\Handler\SyslogUdp\UdpSocket;
|
||||||
|
use Monolog\Util\LocalSocket;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @requires extension sockets
|
* @requires extension sockets
|
||||||
@@ -23,10 +24,9 @@ class UdpSocketTest extends TestCase
|
|||||||
{
|
{
|
||||||
$this->initSocket();
|
$this->initSocket();
|
||||||
|
|
||||||
$socket = new UdpSocket('127.0.0.1', 51984);
|
$socket = new UdpSocket('127.0.0.1', 51983);
|
||||||
$socket->write("The quick brown fox jumps over the lazy dog", "HEADER: ");
|
$socket->write("The quick brown fox jumps over the lazy dog", "HEADER: ");
|
||||||
|
|
||||||
$this->closeSocket();
|
|
||||||
$this->assertEquals('HEADER: The quick brown fox jumps over the lazy dog', $this->socket->getOutput());
|
$this->assertEquals('HEADER: The quick brown fox jumps over the lazy dog', $this->socket->getOutput());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -34,14 +34,12 @@ class UdpSocketTest extends TestCase
|
|||||||
{
|
{
|
||||||
$this->initSocket();
|
$this->initSocket();
|
||||||
|
|
||||||
$socket = new UdpSocket('127.0.0.1', 51984);
|
$socket = new UdpSocket('127.0.0.1', 51983);
|
||||||
|
|
||||||
$longString = str_repeat("derp", 20000);
|
$longString = str_repeat("derp", 20000);
|
||||||
$socket->write($longString, "HEADER");
|
$socket->write($longString, "HEADER");
|
||||||
|
|
||||||
$truncatedString = str_repeat("derp", 16254).'d';
|
$truncatedString = str_repeat("derp", 16254).'d';
|
||||||
|
|
||||||
$this->closeSocket();
|
|
||||||
$this->assertEquals('HEADER'.$truncatedString, $this->socket->getOutput());
|
$this->assertEquals('HEADER'.$truncatedString, $this->socket->getOutput());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -64,43 +62,11 @@ class UdpSocketTest extends TestCase
|
|||||||
|
|
||||||
private function initSocket()
|
private function initSocket()
|
||||||
{
|
{
|
||||||
$tmpFile = sys_get_temp_dir().'/monolog-test-socket.php';
|
$this->socket = LocalSocket::initSocket(51983, LocalSocket::UDP);
|
||||||
file_put_contents($tmpFile, <<<'SCRIPT'
|
|
||||||
<?php
|
|
||||||
|
|
||||||
$sock = socket_create(AF_INET, SOCK_DGRAM, getprotobyname('udp'));
|
|
||||||
socket_bind($sock, '127.0.0.1', 51984);
|
|
||||||
echo 'INIT';
|
|
||||||
while (true) {
|
|
||||||
socket_recvfrom($sock, $read, 100*1024, 0, $ip, $port);
|
|
||||||
echo $read;
|
|
||||||
}
|
|
||||||
SCRIPT
|
|
||||||
);
|
|
||||||
|
|
||||||
$this->socket = new \Symfony\Component\Process\Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($tmpFile));
|
|
||||||
$this->socket->start();
|
|
||||||
while (true) {
|
|
||||||
if ($this->socket->getOutput() === 'INIT') {
|
|
||||||
$this->socket->clearOutput();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
usleep(100);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private function closeSocket()
|
|
||||||
{
|
|
||||||
usleep(100);
|
|
||||||
$this->socket->stop();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public function tearDown()
|
public function tearDown()
|
||||||
{
|
{
|
||||||
if (isset($this->socket)) {
|
unset($this->socket, $this->handler);
|
||||||
$this->closeSocket();
|
|
||||||
unset($this->socket);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
234
tests/Monolog/Util/LocalSocket.php
Normal file
234
tests/Monolog/Util/LocalSocket.php
Normal file
@@ -0,0 +1,234 @@
|
|||||||
|
<?php declare(strict_types=1);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This file is part of the Monolog package.
|
||||||
|
*
|
||||||
|
* (c) Jordi Boggiano <j.boggiano@seld.be>
|
||||||
|
*
|
||||||
|
* For the full copyright and license information, please view the LICENSE
|
||||||
|
* file that was distributed with this source code.
|
||||||
|
*/
|
||||||
|
|
||||||
|
namespace Monolog\Util;
|
||||||
|
|
||||||
|
use Symfony\Component\Process\Process;
|
||||||
|
|
||||||
|
class LocalSocket
|
||||||
|
{
|
||||||
|
const TCP = 'tcp';
|
||||||
|
const UDP = 'udp';
|
||||||
|
|
||||||
|
private static $sockets = [];
|
||||||
|
private static $shutdownHandler = false;
|
||||||
|
|
||||||
|
public static function initSocket(int $port = 51984, string $proto = LocalSocket::TCP)
|
||||||
|
{
|
||||||
|
if (!isset(self::$sockets[$proto][$port])) {
|
||||||
|
$file = self::initFile($port, $proto);
|
||||||
|
|
||||||
|
$process = new Process(escapeshellarg(PHP_BINARY).' '.escapeshellarg($file));
|
||||||
|
$process->start(function ($type, $out) use ($proto, $port) {
|
||||||
|
if ($type === 'err') {
|
||||||
|
if (substr($out, 0, 4) === 'INIT') {
|
||||||
|
if ($proto === LocalSocket::UDP) {
|
||||||
|
self::$sockets[$proto][$port]['comms'] = null;
|
||||||
|
} else {
|
||||||
|
$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname($proto));
|
||||||
|
socket_connect($sock, '127.0.0.1', $port);
|
||||||
|
socket_write($sock, "MONITOR\n");
|
||||||
|
self::$sockets[$proto][$port]['comms'] = $sock;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
self::$sockets[$proto][$port] = [
|
||||||
|
'file' => $file,
|
||||||
|
'process' => $process,
|
||||||
|
'busy' => false,
|
||||||
|
];
|
||||||
|
|
||||||
|
// make sure the socket is listening
|
||||||
|
while (true) {
|
||||||
|
if ($process->getErrorOutput() === 'INIT') {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
usleep(100);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!self::$shutdownHandler) {
|
||||||
|
register_shutdown_function(function () {
|
||||||
|
LocalSocket::shutdownSockets();
|
||||||
|
});
|
||||||
|
self::$shutdownHandler = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$sock = self::$sockets[$proto][$port];
|
||||||
|
if (!$sock['process']->isRunning()) {
|
||||||
|
throw new \RuntimeException(
|
||||||
|
'LocalSocket '.$proto.'://127.0.0.1:'.$port.' appears to have died unexpectedly: ' . "\n\n" .
|
||||||
|
$sock['process']->getOutput()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
self::clearSocket($port, $proto);
|
||||||
|
|
||||||
|
return new class($sock['process'], $sock['comms']) {
|
||||||
|
public function __construct(Process $proc, $comms)
|
||||||
|
{
|
||||||
|
$this->process = $proc;
|
||||||
|
$this->comms = $comms;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getOutput()
|
||||||
|
{
|
||||||
|
// read out until getting a !DONE! ack and then tell the socket to terminate the connection
|
||||||
|
if ($this->comms) {
|
||||||
|
$out = '';
|
||||||
|
socket_write($this->comms, "DONE?\n");
|
||||||
|
while ($data = socket_read($this->comms, 2048)) {
|
||||||
|
$out .= $data;
|
||||||
|
if (substr($out, -6) === '!DONE!') {
|
||||||
|
$out = substr($out, 0, -6);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
$out = preg_replace('{.*!BEGIN!}', '', $out);
|
||||||
|
|
||||||
|
socket_write($this->comms, "TERMINATE\n");
|
||||||
|
|
||||||
|
return $out;
|
||||||
|
}
|
||||||
|
|
||||||
|
// wait 3 seconds max for output for UDP
|
||||||
|
$retries = 3000;
|
||||||
|
while (!$this->process->getOutput() && $retries-- && $this->process->getStatus()) {
|
||||||
|
usleep(100);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $this->process->getOutput();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
private static function clearSocket(int $port = 51984, string $proto = LocalSocket::TCP)
|
||||||
|
{
|
||||||
|
if (isset(self::$sockets[$proto][$port])) {
|
||||||
|
self::$sockets[$proto][$port]['process']->clearOutput();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static function shutdownSocket(int $port = 51984, string $proto = LocalSocket::TCP)
|
||||||
|
{
|
||||||
|
if (!isset(self::$sockets[$proto][$port])) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (is_resource(self::$sockets[$proto][$port]['comms'])) {
|
||||||
|
socket_write(self::$sockets[$proto][$port]['comms'], "EXIT\n");
|
||||||
|
socket_close(self::$sockets[$proto][$port]['comms']);
|
||||||
|
}
|
||||||
|
$sock = self::$sockets[$proto][$port];
|
||||||
|
$sock['process']->stop();
|
||||||
|
@unlink($sock['file']);
|
||||||
|
unset(self::$sockets[$proto][$port]);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static function shutdownSockets()
|
||||||
|
{
|
||||||
|
foreach (self::$sockets as $proto => $ports) {
|
||||||
|
foreach ($ports as $port => $sock) {
|
||||||
|
self::shutdownSocket($port, $proto);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static function initFile(int $port, string $proto): string
|
||||||
|
{
|
||||||
|
$tmpFile = sys_get_temp_dir().'/monolog-test-'.$proto.'-socket-'.$port.'.php';
|
||||||
|
|
||||||
|
if ($proto === self::UDP) {
|
||||||
|
file_put_contents($tmpFile, <<<SCRIPT
|
||||||
|
<?php
|
||||||
|
|
||||||
|
\$sock = socket_create(AF_INET, SOCK_DGRAM, getprotobyname('udp'));
|
||||||
|
if (!socket_bind(\$sock, '127.0.0.1', $port)) {
|
||||||
|
fwrite(STDERR, 'COULD NOT BIND $port');
|
||||||
|
}
|
||||||
|
fwrite(STDERR, 'INIT');
|
||||||
|
while (true) {
|
||||||
|
socket_recvfrom(\$sock, \$read, 100*1024, 0, \$ip, \$port);
|
||||||
|
fwrite(STDOUT, \$read);
|
||||||
|
}
|
||||||
|
SCRIPT
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
file_put_contents($tmpFile, <<<SCRIPT
|
||||||
|
<?php
|
||||||
|
|
||||||
|
\$sock = socket_create(AF_INET, SOCK_STREAM, getprotobyname('tcp'));
|
||||||
|
if (!socket_bind(\$sock, '127.0.0.1', $port)) {
|
||||||
|
fwrite(STDERR, 'COULD NOT BIND $port');
|
||||||
|
}
|
||||||
|
if (!socket_listen(\$sock)) {
|
||||||
|
fwrite(STDERR, 'COULD NOT LISTEN $port');
|
||||||
|
}
|
||||||
|
fwrite(STDERR, 'INIT');
|
||||||
|
|
||||||
|
\$monitor = socket_accept(\$sock);
|
||||||
|
\$read = socket_read(\$monitor, 1024, PHP_NORMAL_READ);
|
||||||
|
if (substr(\$read, 0, 7) !== 'MONITOR') {
|
||||||
|
fwrite(STDERR, "Unexpected input: \$read");
|
||||||
|
} else {
|
||||||
|
fwrite(STDERR, "MONITORED");
|
||||||
|
}
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
\$res = socket_accept(\$sock);
|
||||||
|
socket_set_option(\$res, SOL_SOCKET, SO_RCVTIMEO, array("sec" => 0, "usec" => 0));
|
||||||
|
socket_write(\$monitor, '!BEGIN!');
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
\$read = [\$res, \$monitor, \$sock];
|
||||||
|
\$write = [];
|
||||||
|
\$except = [];
|
||||||
|
\$timeout = 0;
|
||||||
|
|
||||||
|
if (socket_select(\$read, \$write, \$except, \$timeout) < 1) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach (\$read as \$readsock) {
|
||||||
|
if (\$readsock === \$res) {
|
||||||
|
\$bytes = socket_read(\$res, 1024);
|
||||||
|
//if (\$bytes === '' && in_array(\$sock, \$read)) {
|
||||||
|
// // client closed
|
||||||
|
// socket_write(\$monitor, 'CLIENTCLOSED');
|
||||||
|
// break 2;
|
||||||
|
//}
|
||||||
|
socket_write(\$monitor, \$bytes);
|
||||||
|
} else {
|
||||||
|
\$bytes = socket_read(\$monitor, 1024, PHP_NORMAL_READ);
|
||||||
|
if (substr(trim(\$bytes), 0, 9) === 'TERMINATE') {
|
||||||
|
break 2;
|
||||||
|
} elseif (substr(trim(\$bytes), 0, 5) === 'DONE?') {
|
||||||
|
socket_write(\$monitor, '!DONE!');
|
||||||
|
} elseif (substr(trim(\$bytes), 0, 5) === 'EXIT') {
|
||||||
|
socket_close(\$res);
|
||||||
|
socket_close(\$monitor);
|
||||||
|
die;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
socket_close(\$res);
|
||||||
|
}
|
||||||
|
SCRIPT
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $tmpFile;
|
||||||
|
}
|
||||||
|
}
|
Reference in New Issue
Block a user