Skip to content

Commit 6e48526

Browse files
committed
chore: update version to 2.1.6 and enhance logging configuration
- Incremented project version to `2.1.6` in `composer.json`. - Updated `composer.lock` with new content hash. - Enhanced `ConfigLoader` to support logging configuration from environment variables. - Updated `Logger` class to handle console and file logging based on configuration. - Modified `TestOpsReporter` to utilize centralized logging. - Added unit tests for logging functionality in `TestOpsReporterTest`.
1 parent d3f2763 commit 6e48526

File tree

9 files changed

+113
-31
lines changed

9 files changed

+113
-31
lines changed

composer.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@
4040
"scripts": {
4141
"test": "phpunit"
4242
},
43-
"version": "2.1.5",
43+
"version": "2.1.6",
4444
"config": {
4545
"platform": {
4646
"php": "8.0"

composer.lock

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/Config/BaseConfig.php

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,6 @@ public function __construct(string $reporterName, LoggerInterface $logger)
2424
}
2525
}
2626
$this->logger = $logger;
27-
2827
}
2928

3029
public function getReporterName(): string

src/Config/ConfigLoader.php

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,7 @@ private function loadFromJsonFile(): QaseConfig
6060
if (isset($data['environment'])) $config->setEnvironment($data['environment']);
6161
if (isset($data['rootSuite'])) $config->setRootSuite($data['rootSuite']);
6262
if (isset($data['debug'])) $config->setDebug($data['debug']);
63+
if (isset($data['logging'])) $config->setLogging($data['logging']);
6364

6465
if (isset($data['statusMapping'])) {
6566
$statusMapping = new StatusMapping(new \Qase\PhpCommons\Loggers\Logger(false));
@@ -131,6 +132,12 @@ private function overrideWithEnvVariables(): void
131132
case "qase_debug":
132133
$this->config->setDebug($value);
133134
break;
135+
case "qase_logging_console":
136+
$this->parseLoggingConsole($value);
137+
break;
138+
case "qase_logging_file":
139+
$this->parseLoggingFile($value);
140+
break;
134141
case "qase_status_mapping":
135142
$this->parseStatusMapping($value);
136143
break;
@@ -294,6 +301,30 @@ private function parseExternalLinkUrl(string $value): void
294301
}
295302
}
296303

304+
/**
305+
* Parse logging console setting from environment variable
306+
*
307+
* @param string $value Console logging setting (true/false)
308+
*/
309+
private function parseLoggingConsole(string $value): void
310+
{
311+
$logging = $this->config->getLogging() ?? [];
312+
$logging['console'] = filter_var($value, FILTER_VALIDATE_BOOLEAN);
313+
$this->config->setLogging($logging);
314+
}
315+
316+
/**
317+
* Parse logging file setting from environment variable
318+
*
319+
* @param string $value File logging setting (true/false)
320+
*/
321+
private function parseLoggingFile(string $value): void
322+
{
323+
$logging = $this->config->getLogging() ?? [];
324+
$logging['file'] = filter_var($value, FILTER_VALIDATE_BOOLEAN);
325+
$this->config->setLogging($logging);
326+
}
327+
297328
/**
298329
* Parse status mapping from environment variable
299330
* Format: "invalid=failed,skipped=passed"

src/Loggers/Logger.php

Lines changed: 36 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -16,21 +16,38 @@ class Logger implements LoggerInterface
1616
'RESET' => "\033[0m", // Reset color
1717
];
1818
private bool $debug;
19+
private bool $consoleEnabled;
20+
private bool $fileEnabled;
1921
private string $logFilePath;
2022

21-
public function __construct(bool $debug = false)
23+
public function __construct(bool $debug = false, ?array $loggingConfig = null)
2224
{
2325
$this->debug = $debug;
2426
$this->logFilePath = getcwd() . '/logs/log_' . date('Y-m-d') . '.log';
2527

26-
if (!is_dir(getcwd() . '/logs')) {
28+
// Set default logging configuration
29+
$this->consoleEnabled = true;
30+
$this->fileEnabled = true;
31+
32+
// Override with config if provided
33+
if ($loggingConfig !== null) {
34+
if (isset($loggingConfig['console'])) {
35+
$this->consoleEnabled = (bool)$loggingConfig['console'];
36+
}
37+
if (isset($loggingConfig['file'])) {
38+
$this->fileEnabled = (bool)$loggingConfig['file'];
39+
}
40+
}
41+
42+
// Create logs directory if file logging is enabled
43+
if ($this->fileEnabled && !is_dir(getcwd() . '/logs')) {
2744
mkdir(getcwd() . '/logs', 0777, true);
2845
}
2946
}
3047

3148
public function info(string $message): void
3249
{
33-
$this->log($message, 'INFO');
50+
$this->writeLog($message, 'INFO');
3451
}
3552

3653
public function debug(string $message): void
@@ -39,24 +56,31 @@ public function debug(string $message): void
3956
return;
4057
}
4158

42-
$this->log($message, 'DEBUG');
59+
$this->writeLog($message, 'DEBUG');
4360
}
4461

4562
public function error(string $message): void
4663
{
47-
$this->log($message, 'ERROR');
64+
$this->writeLog($message, 'ERROR');
4865
}
4966

50-
private function log(string $message, string $level): void
51-
{
52-
$color = self::LEVEL_COLORS[$level] ?? self::LEVEL_COLORS['RESET'];
53-
$reset = self::LEVEL_COLORS['RESET'];
5467

68+
private function writeLog(string $message, string $level): void
69+
{
5570
$timestamp = date('Y-m-d H:i:s');
56-
$formattedMessage = sprintf("%s %s%s %s %s%s\n", $color, self::PREFIX, $timestamp, $level, $message, $reset);
71+
$logEntry = $timestamp . ' ' . $level . ' ' . $message . PHP_EOL;
5772

58-
echo $formattedMessage;
73+
// Console output
74+
if ($this->consoleEnabled) {
75+
$color = self::LEVEL_COLORS[$level] ?? self::LEVEL_COLORS['RESET'];
76+
$reset = self::LEVEL_COLORS['RESET'];
77+
$formattedMessage = sprintf("%s %s%s %s %s%s\n", $color, self::PREFIX, $timestamp, $level, $message, $reset);
78+
echo $formattedMessage;
79+
}
5980

60-
file_put_contents($this->logFilePath, $timestamp . ' ' . $level . ' ' . $message . PHP_EOL, FILE_APPEND);
81+
// File output
82+
if ($this->fileEnabled) {
83+
file_put_contents($this->logFilePath, $logEntry, FILE_APPEND);
84+
}
6185
}
6286
}

src/Models/Config/QaseConfig.php

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ class QaseConfig
1313
public ?string $rootSuite = null;
1414
public bool $debug;
1515
public array $statusMapping = [];
16+
public ?array $logging = null;
1617
public TestopsConfig $testops;
1718
public ReportConfig $report;
1819

@@ -21,6 +22,7 @@ public function __construct()
2122
$this->mode = Mode::OFF;
2223
$this->fallback = Mode::OFF;
2324
$this->debug = false;
25+
$this->logging = null;
2426
$this->testops = new TestopsConfig();
2527
$this->report = new ReportConfig();
2628
}
@@ -98,4 +100,24 @@ public function setStatusMapping(array $statusMapping): void
98100
{
99101
$this->statusMapping = $statusMapping;
100102
}
103+
104+
/**
105+
* Get logging configuration
106+
*
107+
* @return array|null
108+
*/
109+
public function getLogging(): ?array
110+
{
111+
return $this->logging;
112+
}
113+
114+
/**
115+
* Set logging configuration
116+
*
117+
* @param array|null $logging
118+
*/
119+
public function setLogging(?array $logging): void
120+
{
121+
$this->logging = $logging;
122+
}
101123
}

src/Reporters/ReporterFactory.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ public static function create(String $framework = "", String $reporterName = "")
2222
{
2323
$configLoader = new ConfigLoader(new Logger(true));
2424
$config = $configLoader->getConfig();
25-
$logger = new Logger($config->getDebug());
25+
$logger = new Logger($config->getDebug(), $config->getLogging());
2626
$hostInfo = new HostInfo();
2727
$hostData = $hostInfo->getHostInfo($framework, $reporterName);
2828
$logger->debug("Host data: " . json_encode($hostData));
@@ -55,6 +55,6 @@ private static function createInternalReporter(LoggerInterface $logger, QaseConf
5555
private static function prepareTestopsReporter(LoggerInterface $logger, QaseConfig $config, StateInterface $state): InternalReporterInterface
5656
{
5757
$client = new ApiClientV2($logger, $config->testops);
58-
return new TestOpsReporter($client, $config, $state);
58+
return new TestOpsReporter($client, $config, $state, $logger);
5959
}
6060
}

src/Reporters/TestOpsReporter.php

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
use Exception;
88
use Qase\PhpCommons\Interfaces\ClientInterface;
99
use Qase\PhpCommons\Interfaces\InternalReporterInterface;
10+
use Qase\PhpCommons\Interfaces\LoggerInterface;
1011
use Qase\PhpCommons\Interfaces\StateInterface;
1112
use Qase\PhpCommons\Models\Config\QaseConfig;
1213

@@ -16,14 +17,16 @@ class TestOpsReporter implements InternalReporterInterface
1617
private ClientInterface $client;
1718
private QaseConfig $config;
1819
private StateInterface $state;
20+
private LoggerInterface $logger;
1921
private ?int $runId = null;
2022
private ?array $cachedConfigurationGroups = null;
2123

22-
public function __construct(ClientInterface $client, QaseConfig $config, StateInterface $state)
24+
public function __construct(ClientInterface $client, QaseConfig $config, StateInterface $state, LoggerInterface $logger)
2325
{
2426
$this->client = $client;
2527
$this->config = $config;
2628
$this->state = $state;
29+
$this->logger = $logger;
2730
}
2831

2932
/**
@@ -293,8 +296,8 @@ private function updateExternalIssue(int $runId): void
293296
]
294297
);
295298
} catch (Exception $e) {
296-
// Log error through the client's logger
297-
error_log('Failed to update external issue: ' . $e->getMessage());
299+
// Log error through the centralized logger
300+
$this->logger->error('Failed to update external issue: ' . $e->getMessage());
298301
}
299302
}
300303
}

tests/TestOpsReporterTest.php

Lines changed: 14 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
use Exception;
66
use PHPUnit\Framework\TestCase;
77
use Qase\PhpCommons\Interfaces\ClientInterface;
8+
use Qase\PhpCommons\Interfaces\LoggerInterface;
89
use Qase\PhpCommons\Interfaces\StateInterface;
910
use Qase\PhpCommons\Models\Config\QaseConfig;
1011
use Qase\PhpCommons\Reporters\TestOpsReporter;
@@ -14,12 +15,14 @@ class TestOpsReporterTest extends TestCase
1415
{
1516
private $clientMock;
1617
private $stateMock;
18+
private $loggerMock;
1719
private QaseConfig $config;
1820

1921
protected function setUp(): void
2022
{
2123
$this->clientMock = $this->createMock(ClientInterface::class);
2224
$this->stateMock = $this->createMock(StateInterface::class);
25+
$this->loggerMock = $this->createMock(LoggerInterface::class);
2326
$this->config = $this->getConfig();
2427
}
2528

@@ -30,7 +33,7 @@ public function testStartRunCreatesNewRunIfRunIdIsNull(): void
3033
$this->stateMock->method('startRun')
3134
->willReturn(123);
3235

33-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
36+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
3437
$reporter->startRun();
3538

3639
$this->assertSame(123, $this->getPrivateProperty($reporter, 'runId'));
@@ -47,7 +50,7 @@ public function testStartRunThrowsExceptionIfRunNotFound(): void
4750
$this->expectException(Exception::class);
4851
$this->expectExceptionMessage('Run with id 123 not found');
4952

50-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
53+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
5154
$reporter->startRun();
5255
}
5356

@@ -59,7 +62,7 @@ public function testStartRunUsesExistingRunId(): void
5962
->with('TEST_PROJECT', 123)
6063
->willReturn(true);
6164

62-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
65+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
6366
$reporter->startRun();
6467

6568
$this->assertSame(123, $this->getPrivateProperty($reporter, 'runId'));
@@ -73,7 +76,7 @@ public function testSendResultsClearsResults(): void
7376
->method('sendResults')
7477
->with('TEST_PROJECT', 123, ['result1', 'result2']);
7578

76-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
79+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
7780
$reporter->startRun();
7881

7982
$reporter->addResult('result1');
@@ -91,7 +94,7 @@ public function testAddResultSendsResultsWhenBatchSizeIsReached(): void
9194
->method('sendResults')
9295
->with('TEST_PROJECT', 123, ['result1', 'result2']);
9396

94-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
97+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
9598
$reporter->startRun();
9699

97100
$reporter->addResult('result1');
@@ -116,7 +119,7 @@ public function testCompleteRunSendsRemainingResults(): void
116119
return is_callable($callback);
117120
}));
118121

119-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
122+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
120123
$reporter->startRun();
121124

122125
$reporter->addResult('result1');
@@ -141,7 +144,7 @@ public function testCompleteRunWithNoResultsDoesNothing(): void
141144
->method('completeRun')
142145
->with($this->isType('callable'));
143146

144-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
147+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
145148
$reporter->startRun();
146149
$reporter->completeRun();
147150
}
@@ -155,7 +158,7 @@ public function testCompleteRunWithCompleteIsFalseDoesNotCompleteTestRun(): void
155158
$this->clientMock->expects($this->never())
156159
->method('completeTestRun');
157160

158-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
161+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
159162
$reporter->startRun();
160163
$reporter->completeRun();
161164
}
@@ -174,7 +177,7 @@ public function testAddResultFiltersOutExcludedStatuses(): void
174177
$this->createResultWithStatus('failed')
175178
]);
176179

177-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
180+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
178181
$reporter->startRun();
179182

180183
// Add results with different statuses
@@ -206,7 +209,7 @@ public function testAddResultIncludesAllResultsWhenNoFilterConfigured(): void
206209
]]
207210
);
208211

209-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
212+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
210213
$reporter->startRun();
211214

212215
// Add results with different statuses - all should be included
@@ -230,7 +233,7 @@ public function testAddResultHandlesResultsWithoutStatus(): void
230233
$this->createResultWithStatus('passed')
231234
]);
232235

233-
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock);
236+
$reporter = new TestOpsReporter($this->clientMock, $this->config, $this->stateMock, $this->loggerMock);
234237
$reporter->startRun();
235238

236239
// Add results - one without status should be included

0 commit comments

Comments
 (0)