Skip to content

Commit ee8a19a

Browse files
committed
:octocat: QRMarkup: extract CssColorModuleValueTrait to allow use in other output classes
1 parent 2f2f1c8 commit ee8a19a

File tree

4 files changed

+121
-75
lines changed

4 files changed

+121
-75
lines changed
Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
<?php
2+
/**
3+
* CssColorModuleValueTrait.php
4+
*
5+
* @created 04.05.2024
6+
* @author smiley <[email protected]>
7+
* @copyright 2024 smiley
8+
* @license MIT
9+
*/
10+
11+
namespace chillerlan\QRCode\Output;
12+
13+
use function is_string, preg_match, strip_tags, trim;
14+
15+
/**
16+
* Module value checks for output classes that use CSS colors
17+
*/
18+
trait CssColorModuleValueTrait{
19+
20+
/**
21+
* note: we're not necessarily validating the several values, just checking the general syntax
22+
* note: css4 colors are not included
23+
*
24+
* @todo: XSS proof
25+
*
26+
* @see https://developer.mozilla.org/en-US/docs/Web/CSS/color_value
27+
* @implements \chillerlan\QRCode\Output\QROutputInterface::moduleValueIsValid()
28+
* @inheritDoc
29+
*/
30+
public static function moduleValueIsValid(mixed $value):bool{
31+
32+
if(!is_string($value)){
33+
return false;
34+
}
35+
36+
$value = trim(strip_tags($value), " '\"\r\n\t");
37+
38+
// hex notation
39+
// #rgb(a)
40+
// #rrggbb(aa)
41+
if(preg_match('/^#([\da-f]{3}){1,2}$|^#([\da-f]{4}){1,2}$/i', $value)){
42+
return true;
43+
}
44+
45+
// css: hsla/rgba(...values)
46+
if(preg_match('#^(hsla?|rgba?)\([\d .,%/]+\)$#i', $value)){
47+
return true;
48+
}
49+
50+
// predefined css color
51+
if(preg_match('/^[a-z]+$/i', $value)){
52+
return true;
53+
}
54+
55+
return false;
56+
}
57+
58+
/**
59+
* @implements \chillerlan\QRCode\Output\QROutputAbstract::prepareModuleValue()
60+
* @inheritDoc
61+
*/
62+
protected function prepareModuleValue(mixed $value):string{
63+
return trim(strip_tags($value), " '\"\r\n\t");
64+
}
65+
66+
/**
67+
* @implements \chillerlan\QRCode\Output\QROutputAbstract::getDefaultModuleValue()
68+
* @inheritDoc
69+
*/
70+
protected function getDefaultModuleValue(bool $isDark):string{
71+
return ($isDark) ? '#000' : '#fff';
72+
}
73+
74+
}

src/Output/QRMarkup.php

Lines changed: 1 addition & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -10,63 +10,11 @@
1010

1111
namespace chillerlan\QRCode\Output;
1212

13-
use function is_string, preg_match, strip_tags, trim;
14-
1513
/**
1614
* Abstract for markup types: HTML, SVG, ... XML anyone?
1715
*/
1816
abstract class QRMarkup extends QROutputAbstract{
19-
20-
/**
21-
* note: we're not necessarily validating the several values, just checking the general syntax
22-
* note: css4 colors are not included
23-
*
24-
* @todo: XSS proof
25-
*
26-
* @see https://developer.mozilla.org/en-US/docs/Web/CSS/color_value
27-
* @inheritDoc
28-
*/
29-
public static function moduleValueIsValid(mixed $value):bool{
30-
31-
if(!is_string($value)){
32-
return false;
33-
}
34-
35-
$value = trim(strip_tags($value), " '\"\r\n\t");
36-
37-
// hex notation
38-
// #rgb(a)
39-
// #rrggbb(aa)
40-
if(preg_match('/^#([\da-f]{3}){1,2}$|^#([\da-f]{4}){1,2}$/i', $value)){
41-
return true;
42-
}
43-
44-
// css: hsla/rgba(...values)
45-
if(preg_match('#^(hsla?|rgba?)\([\d .,%/]+\)$#i', $value)){
46-
return true;
47-
}
48-
49-
// predefined css color
50-
if(preg_match('/^[a-z]+$/i', $value)){
51-
return true;
52-
}
53-
54-
return false;
55-
}
56-
57-
/**
58-
* @inheritDoc
59-
*/
60-
protected function prepareModuleValue(mixed $value):string{
61-
return trim(strip_tags($value), " '\"\r\n\t");
62-
}
63-
64-
/**
65-
* @inheritDoc
66-
*/
67-
protected function getDefaultModuleValue(bool $isDark):string{
68-
return ($isDark) ? '#000' : '#fff';
69-
}
17+
use CssColorModuleValueTrait;
7018

7119
/**
7220
* @inheritDoc
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
<?php
2+
/**
3+
* CssColorModuleValueProviderTrait.php
4+
*
5+
* @created 04.05.2024
6+
* @author smiley <[email protected]>
7+
* @copyright 2024 smiley
8+
* @license MIT
9+
*/
10+
11+
namespace chillerlan\QRCodeTest\Output;
12+
13+
/**
14+
* A data provider for use in tests that include CssColorModuleValueTrait
15+
*
16+
* @see \chillerlan\QRCode\Output\CssColorModuleValueTrait
17+
*/
18+
trait CssColorModuleValueProviderTrait{
19+
20+
/**
21+
* @implements \chillerlan\QRCodeTest\Output\QROutputTestAbstract::moduleValueProvider()
22+
*/
23+
public static function moduleValueProvider():array{
24+
return [
25+
'invalid: wrong type' => [[], false],
26+
'valid: hex color (3)' => ['#abc', true],
27+
'valid: hex color (4)' => ['#abcd', true],
28+
'valid: hex color (6)' => ['#aabbcc', true],
29+
'valid: hex color (8)' => ['#aabbccdd', true],
30+
'invalid: hex color (non-hex)' => ['#aabbcxyz', false],
31+
'invalid: hex color (too short)' => ['#aa', false],
32+
'invalid: hex color (5)' => ['#aabbc', false],
33+
'invalid: hex color (7)' => ['#aabbccd', false],
34+
'valid: rgb(...%)' => ['rgb(100.0%, 0.0%, 0.0%)', true],
35+
'valid: rgba(...)' => [' rgba(255, 0, 0, 1.0) ', true],
36+
'valid: hsl(...)' => ['hsl(120, 60%, 50%)', true],
37+
'valid: hsla(...)' => ['hsla(120, 255, 191.25, 1.0)', true],
38+
'invalid: rgba(non-numeric)' => ['rgba(255, 0, whatever, 0, 1.0)', false],
39+
'invalid: rgba(extra-char)' => ['rgba(255, 0, 0, 1.0);', false],
40+
'valid: csscolor' => ['purple', true],
41+
'invalid: c5sc0lor' => ['c5sc0lor', false],
42+
];
43+
}
44+
45+
}

tests/Output/QRMarkupTestAbstract.php

Lines changed: 1 addition & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -16,28 +16,7 @@
1616
* Tests the QRMarkup output module
1717
*/
1818
abstract class QRMarkupTestAbstract extends QROutputTestAbstract{
19-
20-
public static function moduleValueProvider():array{
21-
return [
22-
'invalid: wrong type' => [[], false],
23-
'valid: hex color (3)' => ['#abc', true],
24-
'valid: hex color (4)' => ['#abcd', true],
25-
'valid: hex color (6)' => ['#aabbcc', true],
26-
'valid: hex color (8)' => ['#aabbccdd', true],
27-
'invalid: hex color (non-hex)' => ['#aabbcxyz', false],
28-
'invalid: hex color (too short)' => ['#aa', false],
29-
'invalid: hex color (5)' => ['#aabbc', false],
30-
'invalid: hex color (7)' => ['#aabbccd', false],
31-
'valid: rgb(...%)' => ['rgb(100.0%, 0.0%, 0.0%)', true],
32-
'valid: rgba(...)' => [' rgba(255, 0, 0, 1.0) ', true],
33-
'valid: hsl(...)' => ['hsl(120, 60%, 50%)', true],
34-
'valid: hsla(...)' => ['hsla(120, 255, 191.25, 1.0)', true],
35-
'invalid: rgba(non-numeric)' => ['rgba(255, 0, whatever, 0, 1.0)', false],
36-
'invalid: rgba(extra-char)' => ['rgba(255, 0, 0, 1.0);', false],
37-
'valid: csscolor' => ['purple', true],
38-
'invalid: c5sc0lor' => ['c5sc0lor', false],
39-
];
40-
}
19+
use CssColorModuleValueProviderTrait;
4120

4221
/**
4322
* @inheritDoc

0 commit comments

Comments
 (0)