mirror of
https://github.com/Karaka-Management/phpOMS.git
synced 2026-01-11 17:58:41 +00:00
fix billing process
This commit is contained in:
parent
4d0a6e5c2d
commit
b9cc466bed
|
|
@ -46,10 +46,10 @@ class PermissionAbstract implements \JsonSerializable
|
||||||
/**
|
/**
|
||||||
* App name.
|
* App name.
|
||||||
*
|
*
|
||||||
* @var null|string
|
* @var null|int
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
protected ?string $app = null;
|
protected ?int $app = null;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Module id.
|
* Module id.
|
||||||
|
|
@ -135,7 +135,7 @@ class PermissionAbstract implements \JsonSerializable
|
||||||
* Constructor.
|
* Constructor.
|
||||||
*
|
*
|
||||||
* @param null|int $unit Unit to check (null if all are acceptable)
|
* @param null|int $unit Unit to check (null if all are acceptable)
|
||||||
* @param null|string $app App to check (null if all are acceptable)
|
* @param null|int $app App to check (null if all are acceptable)
|
||||||
* @param null|string $module Module Module to check (null if all are acceptable)
|
* @param null|string $module Module Module to check (null if all are acceptable)
|
||||||
* @param null|string $from Provided by which module
|
* @param null|string $from Provided by which module
|
||||||
* @param null|int $category Category (e.g. customer) (null if all are acceptable)
|
* @param null|int $category Category (e.g. customer) (null if all are acceptable)
|
||||||
|
|
@ -147,7 +147,7 @@ class PermissionAbstract implements \JsonSerializable
|
||||||
*/
|
*/
|
||||||
public function __construct(
|
public function __construct(
|
||||||
int $unit = null,
|
int $unit = null,
|
||||||
string $app = null,
|
int $app = null,
|
||||||
string $module = null,
|
string $module = null,
|
||||||
string $from = null,
|
string $from = null,
|
||||||
int $category = null,
|
int $category = null,
|
||||||
|
|
@ -211,11 +211,11 @@ class PermissionAbstract implements \JsonSerializable
|
||||||
/**
|
/**
|
||||||
* Get app name.
|
* Get app name.
|
||||||
*
|
*
|
||||||
* @return null|string
|
* @return null|int
|
||||||
*
|
*
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
public function getApp() : ?string
|
public function getApp() : ?int
|
||||||
{
|
{
|
||||||
return $this->app;
|
return $this->app;
|
||||||
}
|
}
|
||||||
|
|
@ -223,13 +223,13 @@ class PermissionAbstract implements \JsonSerializable
|
||||||
/**
|
/**
|
||||||
* Set app name.
|
* Set app name.
|
||||||
*
|
*
|
||||||
* @param string $app App name
|
* @param int $app App name
|
||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*
|
*
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
public function setApp(string $app = null) : void
|
public function setApp(int $app = null) : void
|
||||||
{
|
{
|
||||||
$this->app = $app;
|
$this->app = $app;
|
||||||
}
|
}
|
||||||
|
|
@ -467,7 +467,7 @@ class PermissionAbstract implements \JsonSerializable
|
||||||
*
|
*
|
||||||
* @param int $permission Permission to check
|
* @param int $permission Permission to check
|
||||||
* @param null|int $unit Unit Unit to check (null if all are acceptable)
|
* @param null|int $unit Unit Unit to check (null if all are acceptable)
|
||||||
* @param null|string $app App App to check (null if all are acceptable)
|
* @param null|int $app App App to check (null if all are acceptable)
|
||||||
* @param null|string $module Module Module to check (null if all are acceptable)
|
* @param null|string $module Module Module to check (null if all are acceptable)
|
||||||
* @param null|int $category Category (e.g. customer) (null if all are acceptable)
|
* @param null|int $category Category (e.g. customer) (null if all are acceptable)
|
||||||
* @param null|int $element (e.g. customer id) (null if all are acceptable)
|
* @param null|int $element (e.g. customer id) (null if all are acceptable)
|
||||||
|
|
@ -480,7 +480,7 @@ class PermissionAbstract implements \JsonSerializable
|
||||||
public function hasPermission(
|
public function hasPermission(
|
||||||
int $permission,
|
int $permission,
|
||||||
int $unit = null,
|
int $unit = null,
|
||||||
string $app = null,
|
int $app = null,
|
||||||
string $module = null,
|
string $module = null,
|
||||||
int $category = null,
|
int $category = null,
|
||||||
int $element = null,
|
int $element = null,
|
||||||
|
|
|
||||||
|
|
@ -123,7 +123,7 @@ trait PermissionHandlingTrait
|
||||||
*
|
*
|
||||||
* @param int $permission Permission to check
|
* @param int $permission Permission to check
|
||||||
* @param null|int $unit Unit Unit to check (null if all are acceptable)
|
* @param null|int $unit Unit Unit to check (null if all are acceptable)
|
||||||
* @param null|string $app App App to check (null if all are acceptable)
|
* @param null|int $app App App to check (null if all are acceptable)
|
||||||
* @param null|string $module Module Module to check (null if all are acceptable)
|
* @param null|string $module Module Module to check (null if all are acceptable)
|
||||||
* @param null|int $category Type (e.g. customer) (null if all are acceptable)
|
* @param null|int $category Type (e.g. customer) (null if all are acceptable)
|
||||||
* @param null|int $element (e.g. customer id) (null if all are acceptable)
|
* @param null|int $element (e.g. customer id) (null if all are acceptable)
|
||||||
|
|
@ -136,15 +136,13 @@ trait PermissionHandlingTrait
|
||||||
public function hasPermission(
|
public function hasPermission(
|
||||||
int $permission,
|
int $permission,
|
||||||
int $unit = null,
|
int $unit = null,
|
||||||
string $app = null,
|
int $app = null,
|
||||||
string $module = null,
|
string $module = null,
|
||||||
int $category = null,
|
int $category = null,
|
||||||
int $element = null,
|
int $element = null,
|
||||||
int $component = null
|
int $component = null
|
||||||
) : bool
|
) : bool
|
||||||
{
|
{
|
||||||
$app = $app !== null ? \strtolower($app) : $app;
|
|
||||||
|
|
||||||
foreach ($this->permissions as $p) {
|
foreach ($this->permissions as $p) {
|
||||||
if ($p->hasPermission($permission, $unit, $app, $module, $category, $element, $component)) {
|
if ($p->hasPermission($permission, $unit, $app, $module, $category, $element, $component)) {
|
||||||
return true;
|
return true;
|
||||||
|
|
|
||||||
|
|
@ -70,7 +70,7 @@ final class BasicOcr
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reat image from path
|
* Read image from path
|
||||||
*
|
*
|
||||||
* @param string $path Image to read
|
* @param string $path Image to read
|
||||||
* @param int $limit Limit
|
* @param int $limit Limit
|
||||||
|
|
@ -93,7 +93,8 @@ final class BasicOcr
|
||||||
if (($read = \fread($fp, 4)) === false || ($unpack = \unpack('N', $read)) === false) {
|
if (($read = \fread($fp, 4)) === false || ($unpack = \unpack('N', $read)) === false) {
|
||||||
return []; // @codeCoverageIgnore
|
return []; // @codeCoverageIgnore
|
||||||
}
|
}
|
||||||
$magicNumber = $unpack[1];
|
|
||||||
|
// $magicNumber = $unpack[1];
|
||||||
|
|
||||||
if (($read = \fread($fp, 4)) === false || ($unpack = \unpack('N', $read)) === false) {
|
if (($read = \fread($fp, 4)) === false || ($unpack = \unpack('N', $read)) === false) {
|
||||||
return []; // @codeCoverageIgnore
|
return []; // @codeCoverageIgnore
|
||||||
|
|
@ -125,6 +126,7 @@ final class BasicOcr
|
||||||
) {
|
) {
|
||||||
return []; // @codeCoverageIgnore
|
return []; // @codeCoverageIgnore
|
||||||
}
|
}
|
||||||
|
|
||||||
$images[] = \array_values($unpack);
|
$images[] = \array_values($unpack);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -237,6 +239,53 @@ final class BasicOcr
|
||||||
return $dist;
|
return $dist;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static function imagesToMNIST(array $images, string $out, int $resolution) : void
|
||||||
|
{
|
||||||
|
$out = \fopen($out, 'wb');
|
||||||
|
|
||||||
|
\fwrite($out, \pack('N', 2051));
|
||||||
|
\fwrite($out, \pack('N', 1));
|
||||||
|
\fwrite($out, \pack('N', $resolution));
|
||||||
|
\fwrite($out, \pack('N', $resolution));
|
||||||
|
|
||||||
|
foreach ($images as $in) {
|
||||||
|
$im = \imagecreatefromstring(\file_get_contents($in));
|
||||||
|
$new = \imagescale($im, $resolution, $resolution);
|
||||||
|
|
||||||
|
// Convert the image to grayscale and normalize the pixel values
|
||||||
|
$mnist = [];
|
||||||
|
for ($i = 0; $i < $resolution; ++$i) {
|
||||||
|
for ($j = 0; $j < $resolution; ++$j) {
|
||||||
|
$pixel = \imagecolorat($new, $j, $i);
|
||||||
|
$gray = \round((0.299 * (($pixel >> 16) & 0xFF) + 0.587 * (($pixel >> 8) & 0xFF) + 0.114 * ($pixel & 0xFF)) / 255, 3);
|
||||||
|
|
||||||
|
\array_push($mnist, $gray);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for ($i = 0; $i < \count($mnist); $i++) {
|
||||||
|
\fwrite($out, \pack('C', \round($mnist[$i] * 255)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
\fclose($out);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static function labelsToMNIST(array $data, string $out) : void
|
||||||
|
{
|
||||||
|
// Only allows single char labels
|
||||||
|
$out = \fopen($out, 'wb');
|
||||||
|
|
||||||
|
\fwrite($out, \pack('N', 2049));
|
||||||
|
\fwrite($out, \pack('N', 1));
|
||||||
|
|
||||||
|
foreach ($data as $e) {
|
||||||
|
\fwrite($out, \pack('C', $e));
|
||||||
|
}
|
||||||
|
|
||||||
|
\fclose($out);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Categorize an unknown image
|
* Categorize an unknown image
|
||||||
*
|
*
|
||||||
|
|
@ -250,7 +299,6 @@ final class BasicOcr
|
||||||
*/
|
*/
|
||||||
public function matchImage(string $path, int $comparison = 3, int $limit = 0) : array
|
public function matchImage(string $path, int $comparison = 3, int $limit = 0) : array
|
||||||
{
|
{
|
||||||
// @todo: implement image reading if it isn't an mnist file
|
|
||||||
$Xtest = $this->readImages($path, $limit);
|
$Xtest = $this->readImages($path, $limit);
|
||||||
|
|
||||||
return $this->kNearest($this->Xtrain, $this->ytrain, $Xtest, $comparison);
|
return $this->kNearest($this->Xtrain, $this->ytrain, $Xtest, $comparison);
|
||||||
|
|
|
||||||
|
|
@ -115,8 +115,6 @@ final class TesseractOcr
|
||||||
return '';
|
return '';
|
||||||
}
|
}
|
||||||
|
|
||||||
// @todo: auto flip image if x% of text are garbage words?
|
|
||||||
|
|
||||||
\unlink($filepath);
|
\unlink($filepath);
|
||||||
|
|
||||||
return \trim($parsed);
|
return \trim($parsed);
|
||||||
|
|
|
||||||
|
|
@ -37,7 +37,7 @@ final class DependencyResolver
|
||||||
{
|
{
|
||||||
$resolved = [];
|
$resolved = [];
|
||||||
$unresolved = [];
|
$unresolved = [];
|
||||||
foreach ($graph as $table => $dependency) {
|
foreach ($graph as $table => $_) {
|
||||||
self::dependencyResolve($table, $graph, $resolved, $unresolved);
|
self::dependencyResolve($table, $graph, $resolved, $unresolved);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -48,18 +48,18 @@ final class EUVATBffOnline implements EUVATInterface
|
||||||
$request->setMethod(RequestMethod::GET);
|
$request->setMethod(RequestMethod::GET);
|
||||||
|
|
||||||
$result = [
|
$result = [
|
||||||
'status' => -1,
|
'status' => -1,
|
||||||
'vat' => 'C',
|
'vat' => 'C',
|
||||||
'name' => '',
|
'name' => '',
|
||||||
'city' => '',
|
'city' => '',
|
||||||
'postal' => '',
|
'postal' => '',
|
||||||
'address' => '',
|
'address' => '',
|
||||||
'body' => '',
|
'body' => '',
|
||||||
];
|
];
|
||||||
|
|
||||||
$matches = [];
|
$matches = [];
|
||||||
try {
|
try {
|
||||||
$body = Rest::request($request)->getBody();
|
$body = Rest::request($request)->getBody();
|
||||||
$result['body'] = $body;
|
$result['body'] = $body;
|
||||||
|
|
||||||
\preg_match('/ErrorCode.*?(\d+)/s', $body, $matches);
|
\preg_match('/ErrorCode.*?(\d+)/s', $body, $matches);
|
||||||
|
|
@ -93,13 +93,13 @@ final class EUVATBffOnline implements EUVATInterface
|
||||||
) : array
|
) : array
|
||||||
{
|
{
|
||||||
$result = [
|
$result = [
|
||||||
'status' => -1,
|
'status' => -1,
|
||||||
'vat' => 'C',
|
'vat' => 'C',
|
||||||
'name' => 'C',
|
'name' => 'C',
|
||||||
'city' => 'C',
|
'city' => 'C',
|
||||||
'postal' => 'C',
|
'postal' => 'C',
|
||||||
'address' => 'C',
|
'address' => 'C',
|
||||||
'body' => '',
|
'body' => '',
|
||||||
];
|
];
|
||||||
|
|
||||||
if (empty($ownVAT)) {
|
if (empty($ownVAT)) {
|
||||||
|
|
@ -112,7 +112,7 @@ final class EUVATBffOnline implements EUVATInterface
|
||||||
$request->setMethod(RequestMethod::GET);
|
$request->setMethod(RequestMethod::GET);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
$body = Rest::request($request)->getBody();
|
$body = Rest::request($request)->getBody();
|
||||||
$result['body'] = $body;
|
$result['body'] = $body;
|
||||||
|
|
||||||
$matches = [];
|
$matches = [];
|
||||||
|
|
|
||||||
|
|
@ -68,6 +68,11 @@ final class EUVATVies implements EUVATInterface
|
||||||
$result['body'] = $body;
|
$result['body'] = $body;
|
||||||
|
|
||||||
$json = \json_decode($body, true);
|
$json = \json_decode($body, true);
|
||||||
|
|
||||||
|
if ($json === false) {
|
||||||
|
return $result;
|
||||||
|
}
|
||||||
|
|
||||||
$result = \array_merge($result, self::parseResponse($json));
|
$result = \array_merge($result, self::parseResponse($json));
|
||||||
|
|
||||||
$result['status'] = $json['userError'] === 'VALID' ? 0 : -1;
|
$result['status'] = $json['userError'] === 'VALID' ? 0 : -1;
|
||||||
|
|
@ -91,13 +96,13 @@ final class EUVATVies implements EUVATInterface
|
||||||
) : array
|
) : array
|
||||||
{
|
{
|
||||||
$result = [
|
$result = [
|
||||||
'status' => -1,
|
'status' => -1,
|
||||||
'vat' => 'C',
|
'vat' => 'C',
|
||||||
'name' => 'C',
|
'name' => 'C',
|
||||||
'city' => 'C',
|
'city' => 'C',
|
||||||
'postal' => 'C',
|
'postal' => 'C',
|
||||||
'address' => 'C',
|
'address' => 'C',
|
||||||
'body' => '',
|
'body' => '',
|
||||||
];
|
];
|
||||||
|
|
||||||
$request = new HttpRequest(
|
$request = new HttpRequest(
|
||||||
|
|
@ -110,10 +115,15 @@ final class EUVATVies implements EUVATInterface
|
||||||
$request->setMethod(RequestMethod::GET);
|
$request->setMethod(RequestMethod::GET);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
$body = Rest::request($request)->getBody();
|
$body = Rest::request($request)->getBody();
|
||||||
$result['body'] = $body;
|
$result['body'] = $body;
|
||||||
|
|
||||||
$json = \json_decode($body, true);
|
$json = \json_decode($body, true);
|
||||||
|
|
||||||
|
if ($json === false) {
|
||||||
|
return $result;
|
||||||
|
}
|
||||||
|
|
||||||
$result = \array_merge($result, self::parseResponse($json));
|
$result = \array_merge($result, self::parseResponse($json));
|
||||||
|
|
||||||
if ($otherName === '') {
|
if ($otherName === '') {
|
||||||
|
|
@ -167,14 +177,14 @@ final class EUVATVies implements EUVATInterface
|
||||||
private static function parseResponse(array $json) : array
|
private static function parseResponse(array $json) : array
|
||||||
{
|
{
|
||||||
$result = [
|
$result = [
|
||||||
'vat' => '',
|
'vat' => '',
|
||||||
'name' => '',
|
'name' => '',
|
||||||
'city' => '',
|
'city' => '',
|
||||||
'postal' => '',
|
'postal' => '',
|
||||||
'address' => '',
|
'address' => '',
|
||||||
];
|
];
|
||||||
|
|
||||||
$result['vat'] = $json['isValid'] ? 'A' : 'B';
|
$result['vat'] = $json['isValid'] ? 'A' : 'B';
|
||||||
$result['name'] = $json['isValid'];
|
$result['name'] = $json['isValid'];
|
||||||
|
|
||||||
$result['city'] = \stripos($json['address'], "\n") !== false
|
$result['city'] = \stripos($json['address'], "\n") !== false
|
||||||
|
|
@ -194,9 +204,9 @@ final class EUVATVies implements EUVATInterface
|
||||||
: $json['address'];
|
: $json['address'];
|
||||||
|
|
||||||
|
|
||||||
$result['name'] = $result['name'] === '---' ? '' : $result['name'];
|
$result['name'] = $result['name'] === '---' ? '' : $result['name'];
|
||||||
$result['city'] = $result['city'] === '---' ? '' : $result['city'];
|
$result['city'] = $result['city'] === '---' ? '' : $result['city'];
|
||||||
$result['postal'] = $result['postal'] === '---' ? '' : $result['postal'];
|
$result['postal'] = $result['postal'] === '---' ? '' : $result['postal'];
|
||||||
$result['address'] = $result['address'] === '---' ? '' : $result['address'];
|
$result['address'] = $result['address'] === '---' ? '' : $result['address'];
|
||||||
|
|
||||||
return $result;
|
return $result;
|
||||||
|
|
|
||||||
|
|
@ -34,7 +34,16 @@ final class Forensics
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
public static function benfordAnalysis(array $data)
|
/**
|
||||||
|
* Perform the Benford analysis
|
||||||
|
*
|
||||||
|
* @param array $data Data to analyze
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
|
public static function benfordAnalysis(array $data) : array
|
||||||
{
|
{
|
||||||
$digits = \array_fill(1, 9, 0);
|
$digits = \array_fill(1, 9, 0);
|
||||||
$size = \count($data);
|
$size = \count($data);
|
||||||
|
|
@ -52,6 +61,13 @@ final class Forensics
|
||||||
return $results;
|
return $results;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Calculate the general Benford distribution
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
public static function expectedBenfordDistribution() : array
|
public static function expectedBenfordDistribution() : array
|
||||||
{
|
{
|
||||||
$expected = [];
|
$expected = [];
|
||||||
|
|
|
||||||
|
|
@ -96,6 +96,8 @@ final class HttpSession implements SessionInterface
|
||||||
]);
|
]);
|
||||||
\session_start();
|
\session_start();
|
||||||
// @codeCoverageIgnoreEnd
|
// @codeCoverageIgnoreEnd
|
||||||
|
} else {
|
||||||
|
throw new \Exception('Bad application workflow');
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($this->inactivityInterval > 0
|
if ($this->inactivityInterval > 0
|
||||||
|
|
|
||||||
|
|
@ -93,28 +93,42 @@ final class Kernel
|
||||||
if (\count($kernel) === 3) {
|
if (\count($kernel) === 3) {
|
||||||
\imageconvolution($im, $kernel, 1, 0);
|
\imageconvolution($im, $kernel, 1, 0);
|
||||||
} else {
|
} else {
|
||||||
// @todo: implement @see https://rosettacode.org/wiki/Image_convolution
|
|
||||||
// @todo: not working yet
|
|
||||||
$dim = [\imagesx($im), \imagesy($im)];
|
$dim = [\imagesx($im), \imagesy($im)];
|
||||||
$kDim = [\count($kernel[1]), \count($kernel)]; // @todo: is the order correct? mhh...
|
$kDim = [\count($kernel[1]), \count($kernel)];
|
||||||
|
|
||||||
$kWidthRadius = NumericUtils::uRightShift($kDim[0], 1);
|
$kWidthRadius = NumericUtils::uRightShift($kDim[0], 1);
|
||||||
$kHeightRadius = NumericUtils::uRightShift($kDim[1], 1);
|
$kHeightRadius = NumericUtils::uRightShift($kDim[1], 1);
|
||||||
|
|
||||||
for ($i = $dim[0] - 1; $i >= 0; --$i) {
|
for ($y = 0; $y < $dim[1]; ++$y) {
|
||||||
for ($j = $dim[1] - 1; $j >= 0; --$j) {
|
for ($x = 0; $x < $dim[0]; ++$x) {
|
||||||
$newPixel = 0;
|
$newR = 0;
|
||||||
|
$newG = 0;
|
||||||
|
$newB = 0;
|
||||||
|
|
||||||
for ($ki = $kDim[0] - 1; $ki >= 0; --$ki) {
|
for ($ky = 0; $ky < $kDim[0]; ++$ky) {
|
||||||
for ($kj = $kDim[1] - 1; $kj >= 0; --$kj) {
|
for ($kx = 0; $kx < $kDim[1]; ++$kx) {
|
||||||
$newPixel += $kernel[$ki][$kj] * \imagecolorat($im,
|
$pixel = \imagecolorat($im,
|
||||||
\min(\max($i + $ki - $kWidthRadius, 0), $dim[0] - 1),
|
\min(\max($x + $kx - $kWidthRadius, 0), $dim[0] - 1),
|
||||||
\min(\max($j + $kj - $kHeightRadius, 0), $dim[1] - 1)
|
\min(\max($y + $ky - $kHeightRadius, 0), $dim[1] - 1)
|
||||||
);
|
);
|
||||||
|
|
||||||
|
// old
|
||||||
|
$r = ($pixel >> 16) & 0xFF;
|
||||||
|
$g = ($pixel >> 8) & 0xFF;
|
||||||
|
$b = $pixel & 0xFF;
|
||||||
|
|
||||||
|
// new
|
||||||
|
$newR += $r * $kernel[$ky][$kx];
|
||||||
|
$newG += $g * $kernel[$ky][$kx];
|
||||||
|
$newB += $b * $kernel[$ky][$kx];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
\imagesetpixel($im, $i, $j, (int) $newPixel);
|
$newR = \max(0, \min(255, $newR));
|
||||||
|
$newG = \max(0, \min(255, $newG));
|
||||||
|
$newB = \max(0, \min(255, $newB));
|
||||||
|
|
||||||
|
\imagesetpixel($im, $x, $y, (int) (($newR << 16) + ($newG << 8) | $newB));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
542
Localization/ISO639CountryTrait.php
Normal file
542
Localization/ISO639CountryTrait.php
Normal file
|
|
@ -0,0 +1,542 @@
|
||||||
|
<?php
|
||||||
|
/**
|
||||||
|
* Karaka
|
||||||
|
*
|
||||||
|
* PHP Version 8.1
|
||||||
|
*
|
||||||
|
* @package phpOMS\Localization
|
||||||
|
* @copyright Dennis Eichhorn
|
||||||
|
* @license OMS License 2.0
|
||||||
|
* @version 1.0.0
|
||||||
|
* @link https://jingga.app
|
||||||
|
*/
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
namespace phpOMS\Localization;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ISO 639 country -> language trait.
|
||||||
|
*
|
||||||
|
* @package phpOMS\Localization
|
||||||
|
* @license OMS License 2.0
|
||||||
|
* @link https://jingga.app
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
|
trait ISO639CountryTrait
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Get language from country.
|
||||||
|
*
|
||||||
|
* @param string $country Country
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
|
public static function languageFromCountry(string $country) : array
|
||||||
|
{
|
||||||
|
switch (\strtoupper($country)) {
|
||||||
|
case ISO3166TwoEnum::_AFG:
|
||||||
|
return [self::_PS, self::_UZ, self::_TK];
|
||||||
|
case ISO3166TwoEnum::_ALA:
|
||||||
|
return [self::_SV];
|
||||||
|
case ISO3166TwoEnum::_ALB:
|
||||||
|
return [self::_SQ];
|
||||||
|
case ISO3166TwoEnum::_DZA:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_ASM:
|
||||||
|
return [self::_EN, self::_SM];
|
||||||
|
case ISO3166TwoEnum::_AND:
|
||||||
|
return [self::_CA];
|
||||||
|
case ISO3166TwoEnum::_AGO:
|
||||||
|
return [self::_PT];
|
||||||
|
case ISO3166TwoEnum::_AIA:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_ATG:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_ARG:
|
||||||
|
return [self::_ES, self::_GN];
|
||||||
|
case ISO3166TwoEnum::_ARM:
|
||||||
|
return [self::_HY, self::_RU];
|
||||||
|
case ISO3166TwoEnum::_ABW:
|
||||||
|
return [self::_NL];
|
||||||
|
case ISO3166TwoEnum::_AUS:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_AUT:
|
||||||
|
return [self::_DE];
|
||||||
|
case ISO3166TwoEnum::_AZE:
|
||||||
|
return [self::_AZ, self::_RU, self::_HY];
|
||||||
|
case ISO3166TwoEnum::_BHS:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_BHR:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_BGD:
|
||||||
|
return [self::_BN];
|
||||||
|
case ISO3166TwoEnum::_BRB:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_BLR:
|
||||||
|
return [self::_BE, self::_RU];
|
||||||
|
case ISO3166TwoEnum::_BEL:
|
||||||
|
return [self::_NL, self::_FR, self::_DE];
|
||||||
|
case ISO3166TwoEnum::_BLZ:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_BEN:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_BMU:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_BTN:
|
||||||
|
return [self::_DZ];
|
||||||
|
case ISO3166TwoEnum::_BOL:
|
||||||
|
return [self::_ES, self::_QU, self::_AY];
|
||||||
|
case ISO3166TwoEnum::_BES:
|
||||||
|
return [self::_NL, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_BIH:
|
||||||
|
return [self::_BS, self::_HR, self::_SR];
|
||||||
|
case ISO3166TwoEnum::_BWA:
|
||||||
|
return [self::_EN, self::_TN];
|
||||||
|
case ISO3166TwoEnum::_BVT:
|
||||||
|
return [];
|
||||||
|
case ISO3166TwoEnum::_BRA:
|
||||||
|
return [self::_PT];
|
||||||
|
case ISO3166TwoEnum::_IOT:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_BRN:
|
||||||
|
return [self::_MS];
|
||||||
|
case ISO3166TwoEnum::_BGR:
|
||||||
|
return [self::_BG];
|
||||||
|
case ISO3166TwoEnum::_BFA:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_BDI:
|
||||||
|
return [self::_RN, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_CPV:
|
||||||
|
return [self::_PT];
|
||||||
|
case ISO3166TwoEnum::_KHM:
|
||||||
|
return [self::_KM];
|
||||||
|
case ISO3166TwoEnum::_CMR:
|
||||||
|
return [self::_FR, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_CAN:
|
||||||
|
return [self::_EN, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_CYM:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_CAF:
|
||||||
|
return [self::_FR, self::_SG];
|
||||||
|
case ISO3166TwoEnum::_TCD:
|
||||||
|
return [self::_FR, self::_AR];
|
||||||
|
case ISO3166TwoEnum::_CHL:
|
||||||
|
return [self::_ES];
|
||||||
|
break;
|
||||||
|
case ISO3166TwoEnum::_CHN:
|
||||||
|
return [self::_ZH];
|
||||||
|
break;
|
||||||
|
case ISO3166TwoEnum::_CXR:
|
||||||
|
return [self::_EN];
|
||||||
|
break;
|
||||||
|
case ISO3166TwoEnum::_CCK:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_COL:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_COM:
|
||||||
|
return [self::_AR, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_COG:
|
||||||
|
return [self::_FR, self::_LN, self::_KG, self::_SW];
|
||||||
|
case ISO3166TwoEnum::_COD:
|
||||||
|
return [self::_FR, self::_LN, self::_KG, self::_SW];
|
||||||
|
case ISO3166TwoEnum::_COK:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_CRI:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_CIV:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_HRV:
|
||||||
|
return [self::_HR];
|
||||||
|
case ISO3166TwoEnum::_CUB:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_CUW:
|
||||||
|
return [self::_NL, self::_PA, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_CYP:
|
||||||
|
return [self::_EL, self::_TR];
|
||||||
|
case ISO3166TwoEnum::_CZE:
|
||||||
|
return [self::_CS, self::_SK];
|
||||||
|
case ISO3166TwoEnum::_DNK:
|
||||||
|
return [self::_DA];
|
||||||
|
case ISO3166TwoEnum::_DJI:
|
||||||
|
return [self::_FR, self::_AR, self::_SO];
|
||||||
|
case ISO3166TwoEnum::_DMA:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_DOM:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_ECU:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_EGY:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_SLV:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_GNQ:
|
||||||
|
return [self::_ES, self::_FR, self::_PT];
|
||||||
|
case ISO3166TwoEnum::_ERI:
|
||||||
|
return [self::_TI, self::_AR, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_EST:
|
||||||
|
return [self::_ET];
|
||||||
|
case ISO3166TwoEnum::_ETH:
|
||||||
|
return [self::_AM, self::_OM, self::_TI, self::_SO, self::_AR];
|
||||||
|
case ISO3166TwoEnum::_FLK:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_FRO:
|
||||||
|
return [self::_FO];
|
||||||
|
case ISO3166TwoEnum::_FJI:
|
||||||
|
return [self::_EN, self::_FJ, self::_HI, self::_UR];
|
||||||
|
case ISO3166TwoEnum::_FIN:
|
||||||
|
return [self::_FI, self::_SV];
|
||||||
|
case ISO3166TwoEnum::_FRA:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_GUF:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_PYF:
|
||||||
|
return [self::_FR, self::_TY];
|
||||||
|
case ISO3166TwoEnum::_ATF:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_GAB:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_GMB:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_GEO:
|
||||||
|
return [self::_KA];
|
||||||
|
case ISO3166TwoEnum::_DEU:
|
||||||
|
return [self::_DE];
|
||||||
|
case ISO3166TwoEnum::_GHA:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_GIB:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_GRC:
|
||||||
|
return [self::_EL];
|
||||||
|
case ISO3166TwoEnum::_GRL:
|
||||||
|
return [self::_KL];
|
||||||
|
case ISO3166TwoEnum::_GRD:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_GLP:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_GUM:
|
||||||
|
return [self::_EN, self::_CH, self::_ES];
|
||||||
|
case ISO3166TwoEnum::_GTM:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_GGY:
|
||||||
|
return [self::_EN, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_GIN:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_GNB:
|
||||||
|
return [self::_PT];
|
||||||
|
case ISO3166TwoEnum::_GUY:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_HTI:
|
||||||
|
return [self::_FR, self::_HT];
|
||||||
|
case ISO3166TwoEnum::_HMD:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_VAT:
|
||||||
|
return [self::_IT, self::_LA];
|
||||||
|
case ISO3166TwoEnum::_HND:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_HKG:
|
||||||
|
return [self::_ZH, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_HUN:
|
||||||
|
return [self::_HU];
|
||||||
|
case ISO3166TwoEnum::_ISL:
|
||||||
|
return [self::_IS];
|
||||||
|
case ISO3166TwoEnum::_IND:
|
||||||
|
return [self::_HI, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_IDN:
|
||||||
|
return [self::_ID];
|
||||||
|
case ISO3166TwoEnum::_IRN:
|
||||||
|
return [self::_FA];
|
||||||
|
case ISO3166TwoEnum::_IRQ:
|
||||||
|
return [self::_AR, self::_KU];
|
||||||
|
case ISO3166TwoEnum::_IRL:
|
||||||
|
return [self::_GA, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_IMN:
|
||||||
|
return [self::_EN, self::_GV];
|
||||||
|
case ISO3166TwoEnum::_ISR:
|
||||||
|
return [self::_HE, self::_AR];
|
||||||
|
case ISO3166TwoEnum::_ITA:
|
||||||
|
return [self::_IT];
|
||||||
|
case ISO3166TwoEnum::_JAM:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_JPN:
|
||||||
|
return [self::_JA];
|
||||||
|
case ISO3166TwoEnum::_JEY:
|
||||||
|
return [self::_EN, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_JOR:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_KAZ:
|
||||||
|
return [self::_KK, self::_RU];
|
||||||
|
case ISO3166TwoEnum::_KEN:
|
||||||
|
return [self::_SW, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_KIR:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_PRK:
|
||||||
|
return [self::_KO];
|
||||||
|
case ISO3166TwoEnum::_KOR:
|
||||||
|
return [self::_KO];
|
||||||
|
case ISO3166TwoEnum::_KWT:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_KGZ:
|
||||||
|
return [self::_KY, self::_RU];
|
||||||
|
case ISO3166TwoEnum::_LAO:
|
||||||
|
return [self::_LO];
|
||||||
|
case ISO3166TwoEnum::_LVA:
|
||||||
|
return [self::_LV];
|
||||||
|
case ISO3166TwoEnum::_LBN:
|
||||||
|
return [self::_AR, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_LSO:
|
||||||
|
return [self::_EN, self::_ST];
|
||||||
|
case ISO3166TwoEnum::_LBR:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_LBY:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_LIE:
|
||||||
|
return [self::_DE];
|
||||||
|
case ISO3166TwoEnum::_LTU:
|
||||||
|
return [self::_LT];
|
||||||
|
case ISO3166TwoEnum::_LUX:
|
||||||
|
return [self::_LB, self::_FR, self::_DE];
|
||||||
|
case ISO3166TwoEnum::_MAC:
|
||||||
|
return [self::_ZH, self::_PT];
|
||||||
|
case ISO3166TwoEnum::_MDG:
|
||||||
|
return [self::_MG, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_MWI:
|
||||||
|
return [self::_NY, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_MYS:
|
||||||
|
return [self::_MS];
|
||||||
|
case ISO3166TwoEnum::_MDV:
|
||||||
|
return [self::_DV];
|
||||||
|
case ISO3166TwoEnum::_MLI:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_MLT:
|
||||||
|
return [self::_MT, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_MHL:
|
||||||
|
return [self::_MH, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_MTQ:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_MRT:
|
||||||
|
return [self::_AR, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_MUS:
|
||||||
|
return [self::_EN, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_MYT:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_MEX:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_FSM:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_MDA:
|
||||||
|
return [self::_RO];
|
||||||
|
case ISO3166TwoEnum::_MCO:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_MNG:
|
||||||
|
return [self::_MN];
|
||||||
|
case ISO3166TwoEnum::_MNE:
|
||||||
|
return [self::_SR, self::_BS, self::_SQ, self::_HR];
|
||||||
|
case ISO3166TwoEnum::_MSR:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_MAR:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_MOZ:
|
||||||
|
return [self::_PT];
|
||||||
|
case ISO3166TwoEnum::_MMR:
|
||||||
|
return [self::_MY];
|
||||||
|
case ISO3166TwoEnum::_NAM:
|
||||||
|
return [self::_EN, self::_AF];
|
||||||
|
case ISO3166TwoEnum::_NRU:
|
||||||
|
return [self::_NA, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_NPL:
|
||||||
|
return [self::_NE];
|
||||||
|
case ISO3166TwoEnum::_NLD:
|
||||||
|
return [self::_NL];
|
||||||
|
case ISO3166TwoEnum::_NCL:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_NZL:
|
||||||
|
return [self::_EN, self::_MI];
|
||||||
|
case ISO3166TwoEnum::_NIC:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_NER:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_NGA:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_NIU:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_NFK:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_MNP:
|
||||||
|
return [self::_EN, self::_CH];
|
||||||
|
case ISO3166TwoEnum::_NOR:
|
||||||
|
return [self::_NO, self::_NB, self::_NN];
|
||||||
|
case ISO3166TwoEnum::_OMN:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_PAK:
|
||||||
|
return [self::_UR, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_PLW:
|
||||||
|
return [self::_EN, self::_JA, self::_ZH];
|
||||||
|
case ISO3166TwoEnum::_PSE:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_PAN:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_PNG:
|
||||||
|
return [self::_EN, self::_HO];
|
||||||
|
case ISO3166TwoEnum::_PRY:
|
||||||
|
return [self::_ES, self::_GN];
|
||||||
|
case ISO3166TwoEnum::_PER:
|
||||||
|
return [self::_ES, self::_QU, self::_AY];
|
||||||
|
case ISO3166TwoEnum::_PHL:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_PCN:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_POL:
|
||||||
|
return [self::_PL];
|
||||||
|
case ISO3166TwoEnum::_PRT:
|
||||||
|
return [self::_PT];
|
||||||
|
case ISO3166TwoEnum::_PRI:
|
||||||
|
return [self::_ES, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_QAT:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_REU:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_ROU:
|
||||||
|
return [self::_RO];
|
||||||
|
case ISO3166TwoEnum::_RUS:
|
||||||
|
return [self::_RU];
|
||||||
|
case ISO3166TwoEnum::_RWA:
|
||||||
|
return [self::_RW, self::_EN, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_BLM:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_SHN:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_KNA:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_LCA:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_MAF:
|
||||||
|
return [self::_FR, self::_EN, self::_NL];
|
||||||
|
case ISO3166TwoEnum::_SPM:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_VCT:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_WSM:
|
||||||
|
return [self::_SM, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_SMR:
|
||||||
|
return [self::_IT];
|
||||||
|
case ISO3166TwoEnum::_STP:
|
||||||
|
return [self::_PT];
|
||||||
|
case ISO3166TwoEnum::_SAU:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_SEN:
|
||||||
|
return [self::_FR, self::_WO];
|
||||||
|
case ISO3166TwoEnum::_SRB:
|
||||||
|
return [self::_SR];
|
||||||
|
case ISO3166TwoEnum::_SYC:
|
||||||
|
return [self::_FR, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_SLE:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_SGP:
|
||||||
|
return [self::_EN, self::_MS, self::_TA, self::_ZH];
|
||||||
|
case ISO3166TwoEnum::_SXM:
|
||||||
|
return [self::_NL, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_SVK:
|
||||||
|
return [self::_SK];
|
||||||
|
case ISO3166TwoEnum::_SVN:
|
||||||
|
return [self::_SL];
|
||||||
|
case ISO3166TwoEnum::_SLB:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_SOM:
|
||||||
|
return [self::_SO, self::_AR, self::_IT, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_ZAF:
|
||||||
|
return [self::_ZU, self::_XH, self::_AF, self::_EN, self::_TN, self::_ST, self::_TS, self::_SS, self::_VE];
|
||||||
|
case ISO3166TwoEnum::_SGS:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_KOR:
|
||||||
|
return [self::_KO];
|
||||||
|
case ISO3166TwoEnum::_SSD:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_ESP:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_LKA:
|
||||||
|
return [self::_SI, self::_TA, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_SDN:
|
||||||
|
return [self::_AR, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_SUR:
|
||||||
|
return [self::_NL];
|
||||||
|
case ISO3166TwoEnum::_SJM:
|
||||||
|
return [self::_NO];
|
||||||
|
case ISO3166TwoEnum::_SWZ:
|
||||||
|
return [self::_EN, self::_SS];
|
||||||
|
case ISO3166TwoEnum::_SWE:
|
||||||
|
return [self::_SV];
|
||||||
|
case ISO3166TwoEnum::_CHE:
|
||||||
|
return [self::_DE, self::_FR, self::_IT];
|
||||||
|
case ISO3166TwoEnum::_SYR:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_TWN:
|
||||||
|
return [self::_ZH];
|
||||||
|
case ISO3166TwoEnum::_TJK:
|
||||||
|
return [self::_TG, self::_RU];
|
||||||
|
case ISO3166TwoEnum::_TZA:
|
||||||
|
return [self::_SW, self::_EN];
|
||||||
|
case ISO3166TwoEnum::_THA:
|
||||||
|
return [self::_TH];
|
||||||
|
case ISO3166TwoEnum::_TLS:
|
||||||
|
return [self::_PT];
|
||||||
|
case ISO3166TwoEnum::_TGO:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_TKL:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_TON:
|
||||||
|
return [self::_EN, self::_TO];
|
||||||
|
case ISO3166TwoEnum::_TTO:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_TUN:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_TUR:
|
||||||
|
return [self::_TR];
|
||||||
|
case ISO3166TwoEnum::_TKM:
|
||||||
|
return [self::_TK, self::_RU];
|
||||||
|
case ISO3166TwoEnum::_TCA:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_TUV:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_UGA:
|
||||||
|
return [self::_EN, self::_SW];
|
||||||
|
case ISO3166TwoEnum::_UKR:
|
||||||
|
return [self::_UK];
|
||||||
|
case ISO3166TwoEnum::_ARE:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_GBR:
|
||||||
|
return [self::_EN, self::_CY, self::_GD, self::_GA];
|
||||||
|
case ISO3166TwoEnum::_USA:
|
||||||
|
return [self::_EN, self::_ES];
|
||||||
|
case ISO3166TwoEnum::_UMI:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_URY:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_UZB:
|
||||||
|
return [self::_UZ, self::_RU];
|
||||||
|
case ISO3166TwoEnum::_VUT:
|
||||||
|
return [self::_BI, self::_EN, self::_FR];
|
||||||
|
case ISO3166TwoEnum::_VEN:
|
||||||
|
return [self::_ES];
|
||||||
|
case ISO3166TwoEnum::_VNM:
|
||||||
|
return [self::_VI];
|
||||||
|
case ISO3166TwoEnum::_VGB:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_VIR:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_WLF:
|
||||||
|
return [self::_FR];
|
||||||
|
case ISO3166TwoEnum::_ESH:
|
||||||
|
return [self::_AR, self::_ES];
|
||||||
|
case ISO3166TwoEnum::_YEM:
|
||||||
|
return [self::_AR];
|
||||||
|
case ISO3166TwoEnum::_ZMB:
|
||||||
|
return [self::_EN];
|
||||||
|
case ISO3166TwoEnum::_ZWE:
|
||||||
|
return [self::_EN, self::_SN, self::_ND];
|
||||||
|
default:
|
||||||
|
return [];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -118,6 +118,8 @@ class ISO639Enum extends Enum
|
||||||
|
|
||||||
public const _FJ = 'Fijian';
|
public const _FJ = 'Fijian';
|
||||||
|
|
||||||
|
public const _FIL = 'Filipino';
|
||||||
|
|
||||||
public const _FO = 'Faroese';
|
public const _FO = 'Faroese';
|
||||||
|
|
||||||
public const _FR = 'French';
|
public const _FR = 'French';
|
||||||
|
|
@ -393,4 +395,6 @@ class ISO639Enum extends Enum
|
||||||
public const _ZH = 'Chinese';
|
public const _ZH = 'Chinese';
|
||||||
|
|
||||||
public const _ZU = 'Zulu';
|
public const _ZU = 'Zulu';
|
||||||
|
|
||||||
|
use ISO639CountryTrait;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -74,6 +74,8 @@ class ISO639x1Enum extends Enum
|
||||||
|
|
||||||
public const _BG = 'bg';
|
public const _BG = 'bg';
|
||||||
|
|
||||||
|
public const _MS = 'ms';
|
||||||
|
|
||||||
public const _MY = 'my';
|
public const _MY = 'my';
|
||||||
|
|
||||||
public const _CA = 'ca';
|
public const _CA = 'ca';
|
||||||
|
|
@ -86,6 +88,8 @@ class ISO639x1Enum extends Enum
|
||||||
|
|
||||||
public const _CV = 'cv';
|
public const _CV = 'cv';
|
||||||
|
|
||||||
|
public const _KU = 'ku';
|
||||||
|
|
||||||
public const _KW = 'kw';
|
public const _KW = 'kw';
|
||||||
|
|
||||||
public const _KO = 'ko';
|
public const _KO = 'ko';
|
||||||
|
|
@ -120,6 +124,8 @@ class ISO639x1Enum extends Enum
|
||||||
|
|
||||||
public const _FI = 'fi';
|
public const _FI = 'fi';
|
||||||
|
|
||||||
|
public const _FIL = 'fil';
|
||||||
|
|
||||||
public const _FR = 'fr';
|
public const _FR = 'fr';
|
||||||
|
|
||||||
public const _FF = 'ff';
|
public const _FF = 'ff';
|
||||||
|
|
@ -262,6 +268,8 @@ class ISO639x1Enum extends Enum
|
||||||
|
|
||||||
public const _OS = 'os';
|
public const _OS = 'os';
|
||||||
|
|
||||||
|
public const _PA = 'pa';
|
||||||
|
|
||||||
public const _PI = 'pi';
|
public const _PI = 'pi';
|
||||||
|
|
||||||
public const _FA = 'fa';
|
public const _FA = 'fa';
|
||||||
|
|
@ -322,6 +330,8 @@ class ISO639x1Enum extends Enum
|
||||||
|
|
||||||
public const _TE = 'te';
|
public const _TE = 'te';
|
||||||
|
|
||||||
|
public const _TG = 'tg';
|
||||||
|
|
||||||
public const _TH = 'th';
|
public const _TH = 'th';
|
||||||
|
|
||||||
public const _TI = 'ti';
|
public const _TI = 'ti';
|
||||||
|
|
@ -348,6 +358,8 @@ class ISO639x1Enum extends Enum
|
||||||
|
|
||||||
public const _UR = 'ur';
|
public const _UR = 'ur';
|
||||||
|
|
||||||
|
public const _UZ = 'uz';
|
||||||
|
|
||||||
public const _VE = 've';
|
public const _VE = 've';
|
||||||
|
|
||||||
public const _VI = 'vi';
|
public const _VI = 'vi';
|
||||||
|
|
@ -373,4 +385,6 @@ class ISO639x1Enum extends Enum
|
||||||
public const _ZU = 'zu';
|
public const _ZU = 'zu';
|
||||||
|
|
||||||
public const _ZH = 'zh';
|
public const _ZH = 'zh';
|
||||||
|
|
||||||
|
use ISO639CountryTrait;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -120,6 +120,8 @@ class ISO639x2Enum extends Enum
|
||||||
|
|
||||||
public const _FI = 'fin';
|
public const _FI = 'fin';
|
||||||
|
|
||||||
|
public const _FIL = 'fil';
|
||||||
|
|
||||||
public const _FR = 'fra';
|
public const _FR = 'fra';
|
||||||
|
|
||||||
public const _FF = 'ful';
|
public const _FF = 'ful';
|
||||||
|
|
@ -393,4 +395,6 @@ class ISO639x2Enum extends Enum
|
||||||
public const _ZA = 'zha';
|
public const _ZA = 'zha';
|
||||||
|
|
||||||
public const _ZU = 'zul';
|
public const _ZU = 'zul';
|
||||||
|
|
||||||
|
use ISO639CountryTrait;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,7 @@ namespace phpOMS\Localization;
|
||||||
use phpOMS\Autoloader;
|
use phpOMS\Autoloader;
|
||||||
use phpOMS\Log\FileLogger;
|
use phpOMS\Log\FileLogger;
|
||||||
use phpOMS\Module\ModuleAbstract;
|
use phpOMS\Module\ModuleAbstract;
|
||||||
|
use phpOMS\Stdlib\Base\FloatInt;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Localization class.
|
* Localization class.
|
||||||
|
|
@ -206,22 +207,31 @@ final class L11nManager
|
||||||
/**
|
/**
|
||||||
* Print a numeric value
|
* Print a numeric value
|
||||||
*
|
*
|
||||||
* @param Localization $l11n Localization
|
* @param Localization $l11n Localization
|
||||||
* @param int|float $numeric Numeric value to print
|
* @param int|float|FloatInt $numeric Numeric value to print
|
||||||
* @param null|string $format Format type to use
|
* @param null|string $format Format type to use
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*
|
*
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
public function getNumeric(Localization $l11n, int | float $numeric, string $format = null) : string
|
public function getNumeric(Localization $l11n, int | float | FloatInt $numeric, string $format = null) : string
|
||||||
{
|
{
|
||||||
return \number_format(
|
if (!($numeric instanceof FloatInt)) {
|
||||||
$numeric,
|
return \number_format(
|
||||||
$l11n->getPrecision()[$format ?? 'medium'],
|
$numeric,
|
||||||
$l11n->getDecimal(),
|
$l11n->getPrecision()[$format ?? 'medium'],
|
||||||
$l11n->getThousands()
|
$l11n->getDecimal(),
|
||||||
|
$l11n->getThousands()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
$numeric->setLocalization(
|
||||||
|
$l11n->getThousands(),
|
||||||
|
$l11n->getDecimal()
|
||||||
);
|
);
|
||||||
|
|
||||||
|
return $numeric->getAmount($l11n->getPrecision()[$format ?? 'medium']);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -247,17 +257,23 @@ final class L11nManager
|
||||||
/**
|
/**
|
||||||
* Print a currency
|
* Print a currency
|
||||||
*
|
*
|
||||||
* @param Localization $l11n Localization
|
* @param Localization $l11n Localization
|
||||||
* @param int|float $currency Currency value to print
|
* @param int|float|Money $currency Currency value to print
|
||||||
* @param null|string $format Format type to use
|
* @param null|string $symbol Currency name/symbol
|
||||||
* @param null|string $symbol Currency name/symbol
|
* @param null|string $format Format type to use
|
||||||
* @param int $divide Divide currency by divisor
|
* @param int $divide Divide currency by divisor
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*
|
*
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
public function getCurrency(Localization $l11n, int | float $currency, string $format = null, string $symbol = null, int $divide = 1) : string
|
public function getCurrency(
|
||||||
|
Localization $l11n,
|
||||||
|
int | float | Money $currency,
|
||||||
|
string $symbol = null,
|
||||||
|
string $format = null,
|
||||||
|
int $divide = 1
|
||||||
|
) : string
|
||||||
{
|
{
|
||||||
$language = $l11n->getLanguage();
|
$language = $l11n->getLanguage();
|
||||||
$symbol ??= $l11n->getCurrency();
|
$symbol ??= $l11n->getCurrency();
|
||||||
|
|
@ -266,7 +282,7 @@ final class L11nManager
|
||||||
$currency = (int) ($currency * \pow(10, Money::MAX_DECIMALS));
|
$currency = (int) ($currency * \pow(10, Money::MAX_DECIMALS));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!empty($symbol)) {
|
if ($divide > 1 && !empty($symbol)) {
|
||||||
if ($divide === 1000) {
|
if ($divide === 1000) {
|
||||||
$symbol = $this->getHtml($language, '0', '0', 'CurrencyK') . $symbol;
|
$symbol = $this->getHtml($language, '0', '0', 'CurrencyK') . $symbol;
|
||||||
} elseif ($divide === 1000000) {
|
} elseif ($divide === 1000000) {
|
||||||
|
|
@ -276,7 +292,10 @@ final class L11nManager
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
$money = new Money((int) ($currency / $divide));
|
$money = !($currency instanceof Money)
|
||||||
|
? new Money((int) ($currency / $divide))
|
||||||
|
: $currency;
|
||||||
|
|
||||||
$money->setLocalization(
|
$money->setLocalization(
|
||||||
$l11n->getThousands(),
|
$l11n->getThousands(),
|
||||||
$l11n->getDecimal(),
|
$l11n->getDecimal(),
|
||||||
|
|
|
||||||
|
|
@ -108,14 +108,14 @@ abstract class NgramParser
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!\count($tokens)) {
|
if (empty($tokens)) {
|
||||||
return [];
|
return [];
|
||||||
}
|
}
|
||||||
|
|
||||||
$tokens = \array_merge(...$tokens);
|
$tokens = \array_merge(...$tokens);
|
||||||
unset($tokens['_']);
|
unset($tokens['_']);
|
||||||
|
|
||||||
\arsort($tokens, SORT_NUMERIC);
|
\arsort($tokens, \SORT_NUMERIC);
|
||||||
|
|
||||||
return \array_slice(
|
return \array_slice(
|
||||||
\array_keys($tokens),
|
\array_keys($tokens),
|
||||||
|
|
|
||||||
|
|
@ -39,7 +39,7 @@ class WhitespaceTokenizer
|
||||||
function ($word) {
|
function ($word) {
|
||||||
return "_{$word}_";
|
return "_{$word}_";
|
||||||
},
|
},
|
||||||
\preg_split('/[^\pL]+(?<![\x27\x60\x{2019}])/u', $str, -1, PREG_SPLIT_NO_EMPTY)
|
\preg_split('/[^\pL]+(?<![\x27\x60\x{2019}])/u', $str, -1, \PREG_SPLIT_NO_EMPTY)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -42,7 +42,7 @@ class Localization implements \JsonSerializable
|
||||||
* @var string
|
* @var string
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
protected string $country = ISO3166TwoEnum::_USA;
|
protected string $country = ISO3166TwoEnum::_XXX;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Timezone.
|
* Timezone.
|
||||||
|
|
@ -338,14 +338,12 @@ class Localization implements \JsonSerializable
|
||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*
|
*
|
||||||
* @throws InvalidEnumValue This exception is thrown if the country is invalid
|
|
||||||
*
|
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
public function setCountry(string $country) : void
|
public function setCountry(string $country) : void
|
||||||
{
|
{
|
||||||
if (!ISO3166TwoEnum::isValidValue($country)) {
|
if (!ISO3166TwoEnum::isValidValue($country)) {
|
||||||
throw new InvalidEnumValue($country);
|
$this->country = '';
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->country = $country;
|
$this->country = $country;
|
||||||
|
|
|
||||||
|
|
@ -201,7 +201,7 @@ final class NaiveBayesClassifier
|
||||||
$this->probabilities['attr'][$attr] = ['data' => []];
|
$this->probabilities['attr'][$attr] = ['data' => []];
|
||||||
}
|
}
|
||||||
|
|
||||||
foreach ($valueArray['data'] as $word => $count) {
|
foreach ($valueArray['data'] as $word => $_) {
|
||||||
if (!isset($this->dict[$criteria][$attr]['data'][$word])) {
|
if (!isset($this->dict[$criteria][$attr]['data'][$word])) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,7 @@ namespace phpOMS\Message\Http;
|
||||||
use phpOMS\Localization\Localization;
|
use phpOMS\Localization\Localization;
|
||||||
use phpOMS\Message\RequestAbstract;
|
use phpOMS\Message\RequestAbstract;
|
||||||
use phpOMS\Router\RouteVerb;
|
use phpOMS\Router\RouteVerb;
|
||||||
|
use phpOMS\Security\Guard;
|
||||||
use phpOMS\Uri\HttpUri;
|
use phpOMS\Uri\HttpUri;
|
||||||
use phpOMS\Uri\UriInterface;
|
use phpOMS\Uri\UriInterface;
|
||||||
|
|
||||||
|
|
@ -94,6 +95,7 @@ final class HttpRequest extends RequestAbstract
|
||||||
self::cleanupGlobals();
|
self::cleanupGlobals();
|
||||||
|
|
||||||
$this->data = \array_change_key_case($this->data, \CASE_LOWER);
|
$this->data = \array_change_key_case($this->data, \CASE_LOWER);
|
||||||
|
$this->data = Guard::unslash($this->data);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -106,9 +108,10 @@ final class HttpRequest extends RequestAbstract
|
||||||
private function initCurrentRequest() : void
|
private function initCurrentRequest() : void
|
||||||
{
|
{
|
||||||
$this->uri = HttpUri::fromCurrent();
|
$this->uri = HttpUri::fromCurrent();
|
||||||
$this->data = $_GET + $_POST;
|
$this->data = $_POST + $_GET;
|
||||||
$this->files = $_FILES;
|
$this->files = $_FILES;
|
||||||
$this->header->l11n->setLanguage($this->getRequestLanguage());
|
$this->header->l11n->setLanguage($this->getRequestLanguage());
|
||||||
|
$this->header->l11n->setCountry($this->getRequestCountry());
|
||||||
|
|
||||||
$this->initNonGetData();
|
$this->initNonGetData();
|
||||||
}
|
}
|
||||||
|
|
@ -381,6 +384,31 @@ final class HttpRequest extends RequestAbstract
|
||||||
return \strtolower($firstLocalComponents[0]); // @codeCoverageIgnore
|
return \strtolower($firstLocalComponents[0]); // @codeCoverageIgnore
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get request language
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
|
public function getRequestCountry() : string
|
||||||
|
{
|
||||||
|
if (!isset($_SERVER['HTTP_ACCEPT_LANGUAGE'])) {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
|
||||||
|
// @codeCoverageIgnoreStart
|
||||||
|
$components = \explode(';', $_SERVER['HTTP_ACCEPT_LANGUAGE']);
|
||||||
|
$locals = \stripos($components[0], ',') !== false
|
||||||
|
? $locals = \explode(',', $components[0])
|
||||||
|
: $components;
|
||||||
|
|
||||||
|
$firstLocalComponents = \explode('-', $locals[0]);
|
||||||
|
// @codeCoverageIgnoreEnd
|
||||||
|
|
||||||
|
return \strtoupper($firstLocalComponents[1] ?? ''); // @codeCoverageIgnore
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get request locale
|
* Get request locale
|
||||||
*
|
*
|
||||||
|
|
@ -396,7 +424,9 @@ final class HttpRequest extends RequestAbstract
|
||||||
|
|
||||||
// @codeCoverageIgnoreStart
|
// @codeCoverageIgnoreStart
|
||||||
$components = \explode(';', $_SERVER['HTTP_ACCEPT_LANGUAGE']);
|
$components = \explode(';', $_SERVER['HTTP_ACCEPT_LANGUAGE']);
|
||||||
$locals = \stripos($components[0], ',') !== false ? $locals = \explode(',', $components[0]) : $components;
|
$locals = \stripos($components[0], ',') !== false
|
||||||
|
? $locals = \explode(',', $components[0])
|
||||||
|
: $components;
|
||||||
// @codeCoverageIgnoreEnd
|
// @codeCoverageIgnoreEnd
|
||||||
|
|
||||||
return \str_replace('-', '_', $locals[0]); // @codeCoverageIgnore
|
return \str_replace('-', '_', $locals[0]); // @codeCoverageIgnore
|
||||||
|
|
|
||||||
|
|
@ -92,7 +92,7 @@ final class Rest
|
||||||
/* @phpstan-ignore-next-line */
|
/* @phpstan-ignore-next-line */
|
||||||
$data = self::createMultipartData($boundary, $request->getData());
|
$data = self::createMultipartData($boundary, $request->getData());
|
||||||
|
|
||||||
// @todo: replace boundary/ with the correct boundary= in the future.
|
// @todo: Replace boundary/ with the correct boundary= in the future.
|
||||||
// Currently this cannot be done due to a bug. If we do it now the server cannot correclty populate php://input
|
// Currently this cannot be done due to a bug. If we do it now the server cannot correclty populate php://input
|
||||||
$headers['content-type'] = 'Content-Type: multipart/form-data; boundary/' . $boundary;
|
$headers['content-type'] = 'Content-Type: multipart/form-data; boundary/' . $boundary;
|
||||||
$headers['content-length'] = 'Content-Length: ' . \strlen($data);
|
$headers['content-length'] = 'Content-Length: ' . \strlen($data);
|
||||||
|
|
|
||||||
|
|
@ -336,6 +336,18 @@ abstract class RequestAbstract implements MessageInterface
|
||||||
return $this->header->l11n->getLanguage();
|
return $this->header->l11n->getLanguage();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get request language.
|
||||||
|
*
|
||||||
|
* @return string
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
|
public function getCountry() : string
|
||||||
|
{
|
||||||
|
return $this->header->l11n->getCountry();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get request hash.
|
* Get request hash.
|
||||||
*
|
*
|
||||||
|
|
|
||||||
|
|
@ -101,8 +101,9 @@ final class Head implements RenderableInterface
|
||||||
/**
|
/**
|
||||||
* Add asset.
|
* Add asset.
|
||||||
*
|
*
|
||||||
* @param int $type Asset type
|
* @param int $type Asset type
|
||||||
* @param string $uri Asset uri
|
* @param string $uri Asset uri
|
||||||
|
* @param array $attributes Asset attributes
|
||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*
|
*
|
||||||
|
|
@ -116,8 +117,9 @@ final class Head implements RenderableInterface
|
||||||
/**
|
/**
|
||||||
* Add tag.
|
* Add tag.
|
||||||
*
|
*
|
||||||
* @param int $type Asset type
|
* @param int $type Asset type
|
||||||
* @param string $uri Asset uri
|
* @param string $content Asset content
|
||||||
|
* @param array $attributes Asset attributes
|
||||||
*
|
*
|
||||||
* @return void
|
* @return void
|
||||||
*
|
*
|
||||||
|
|
|
||||||
|
|
@ -74,7 +74,7 @@ interface RouterInterface
|
||||||
* @param string $uri Route
|
* @param string $uri Route
|
||||||
* @param string $csrf CSRF token
|
* @param string $csrf CSRF token
|
||||||
* @param int $verb Route verb
|
* @param int $verb Route verb
|
||||||
* @param string $app Application name
|
* @param int $app Application name
|
||||||
* @param int $unitId Organization id
|
* @param int $unitId Organization id
|
||||||
* @param Account $account Account
|
* @param Account $account Account
|
||||||
* @param array $data Data
|
* @param array $data Data
|
||||||
|
|
@ -87,7 +87,7 @@ interface RouterInterface
|
||||||
string $uri,
|
string $uri,
|
||||||
string $csrf = null,
|
string $csrf = null,
|
||||||
int $verb = RouteVerb::GET,
|
int $verb = RouteVerb::GET,
|
||||||
string $app = null,
|
int $app = null,
|
||||||
int $unitId = null,
|
int $unitId = null,
|
||||||
Account $account = null,
|
Account $account = null,
|
||||||
array $data = null
|
array $data = null
|
||||||
|
|
|
||||||
|
|
@ -113,7 +113,7 @@ final class SocketRouter implements RouterInterface
|
||||||
string $uri,
|
string $uri,
|
||||||
string $csrf = null,
|
string $csrf = null,
|
||||||
int $verb = RouteVerb::GET,
|
int $verb = RouteVerb::GET,
|
||||||
string $app = null,
|
int $app = null,
|
||||||
int $unitId = null,
|
int $unitId = null,
|
||||||
Account $account = null,
|
Account $account = null,
|
||||||
array $data = null
|
array $data = null
|
||||||
|
|
|
||||||
|
|
@ -115,7 +115,7 @@ final class WebRouter implements RouterInterface
|
||||||
string $uri,
|
string $uri,
|
||||||
string $csrf = null,
|
string $csrf = null,
|
||||||
int $verb = RouteVerb::GET,
|
int $verb = RouteVerb::GET,
|
||||||
string $app = null,
|
int $app = null,
|
||||||
int $unitId = null,
|
int $unitId = null,
|
||||||
Account $account = null,
|
Account $account = null,
|
||||||
array $data = null
|
array $data = null
|
||||||
|
|
|
||||||
|
|
@ -52,4 +52,29 @@ final class Guard
|
||||||
{
|
{
|
||||||
return \stripos(FileUtils::absolute($path), FileUtils::absolute(empty($base) ? self::$BASE_PATH : $base)) === 0;
|
return \stripos(FileUtils::absolute($path), FileUtils::absolute(empty($base) ? self::$BASE_PATH : $base)) === 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Remove slashes from a string or array
|
||||||
|
*
|
||||||
|
* @param string|array $data Data to unslash
|
||||||
|
*
|
||||||
|
* @return string|array
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
|
public static function unslash(string | array $data) : string|array
|
||||||
|
{
|
||||||
|
if (\is_array($data)) {
|
||||||
|
$result = [];
|
||||||
|
foreach ($data as $key => $value) {
|
||||||
|
$result[$key] = self::unslash($value);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $result;
|
||||||
|
} elseif (\is_string($data)) {
|
||||||
|
return \stripslashes($data);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $data;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -633,6 +633,18 @@ class Graph
|
||||||
return $longestPath;
|
return $longestPath;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Perform depth first traversal
|
||||||
|
*
|
||||||
|
* @param Node $node Graph node
|
||||||
|
* @param array $visited Is the node already visited
|
||||||
|
* @param array $path Array of nodes (a path through the graph = connected nodes)
|
||||||
|
* @param array $longestPath Array of nodes (longest path through the graph = connected nodes)
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
private function longestPathDfs(Node $node, &$visited, &$path, &$longestPath)
|
private function longestPathDfs(Node $node, &$visited, &$path, &$longestPath)
|
||||||
{
|
{
|
||||||
$visited[$node->getId()] = true;
|
$visited[$node->getId()] = true;
|
||||||
|
|
|
||||||
|
|
@ -172,6 +172,15 @@ class Node
|
||||||
return $this->edges[$key] ?? null;
|
return $this->edges[$key] ?? null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Check if the node has a certain neighbor
|
||||||
|
*
|
||||||
|
* @param Node $node Neighbor node
|
||||||
|
*
|
||||||
|
* @return bool
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
public function hasNeighbor(self $node) : bool
|
public function hasNeighbor(self $node) : bool
|
||||||
{
|
{
|
||||||
foreach ($this->edges as $edge) {
|
foreach ($this->edges as $edge) {
|
||||||
|
|
|
||||||
|
|
@ -166,7 +166,7 @@ final class MultiMap implements \Countable
|
||||||
*/
|
*/
|
||||||
private function garbageCollectValues() : void
|
private function garbageCollectValues() : void
|
||||||
{
|
{
|
||||||
foreach ($this->values as $valueKey => $value) {
|
foreach ($this->values as $valueKey => $_) {
|
||||||
if (!\in_array($valueKey, $this->keys)) {
|
if (!\in_array($valueKey, $this->keys)) {
|
||||||
unset($this->values[$valueKey]);
|
unset($this->values[$valueKey]);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -391,6 +391,8 @@ class Directory extends FileAbstract implements DirectoryInterface
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$e = [];
|
||||||
|
|
||||||
list(
|
list(
|
||||||
$e['permission'],
|
$e['permission'],
|
||||||
$e['number'],
|
$e['number'],
|
||||||
|
|
|
||||||
|
|
@ -86,7 +86,7 @@ final class UriFactory
|
||||||
if ($identifier === '*') {
|
if ($identifier === '*') {
|
||||||
self::$uri = [];
|
self::$uri = [];
|
||||||
} else {
|
} else {
|
||||||
foreach (self::$uri as $key => $value) {
|
foreach (self::$uri as $key => $_) {
|
||||||
if (\stripos($key, $identifier) === 0) {
|
if (\stripos($key, $identifier) === 0) {
|
||||||
unset(self::$uri[$key]);
|
unset(self::$uri[$key]);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -794,7 +794,7 @@ class QR extends TwoDAbstract
|
||||||
{
|
{
|
||||||
$b = 0;
|
$b = 0;
|
||||||
$bitMask = [];
|
$bitMask = [];
|
||||||
$bitMask = $this->generateMaskNo($maskNo, $width, $s, $d);
|
$bitMask = $this->generateMaskNo($maskNo, $width, $s);
|
||||||
|
|
||||||
if ($maskGenOnly) {
|
if ($maskGenOnly) {
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
||||||
|
|
@ -114,7 +114,7 @@ final class Currency
|
||||||
$node = $xml->Cube->Cube->Cube;
|
$node = $xml->Cube->Cube->Cube;
|
||||||
self::$ecbCurrencies = [];
|
self::$ecbCurrencies = [];
|
||||||
|
|
||||||
foreach ($node as $key => $value) {
|
foreach ($node as $value) {
|
||||||
/** @var null|array<string, string|int|float> $attributes */
|
/** @var null|array<string, string|int|float> $attributes */
|
||||||
if (($attributes = $value->attributes()) === null) {
|
if (($attributes = $value->attributes()) === null) {
|
||||||
continue;
|
continue;
|
||||||
|
|
|
||||||
|
|
@ -12,9 +12,27 @@
|
||||||
*/
|
*/
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* iCal parser.
|
||||||
|
*
|
||||||
|
* @package phpOMS\Utils\Parser\Calendar
|
||||||
|
* @license OMS License 2.0
|
||||||
|
* @link https://jingga.app
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
class ICalParser
|
class ICalParser
|
||||||
{
|
{
|
||||||
public static function parse(string $data) {
|
/**
|
||||||
|
* Parse iCal data
|
||||||
|
*
|
||||||
|
* @param string $data iCal data
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
|
public static function parse(string $data) : array
|
||||||
|
{
|
||||||
\preg_match_all('/BEGIN:VEVENT(.*?)END:VEVENT/s', $data, $matches, PREG_SET_ORDER);
|
\preg_match_all('/BEGIN:VEVENT(.*?)END:VEVENT/s', $data, $matches, PREG_SET_ORDER);
|
||||||
|
|
||||||
$eventList = [];
|
$eventList = [];
|
||||||
|
|
@ -54,8 +72,19 @@ class ICalParser
|
||||||
|
|
||||||
$eventList[] = $event;
|
$eventList[] = $event;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return $eventList;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse rrule
|
||||||
|
*
|
||||||
|
* @param string $rruleString rrule string
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*
|
||||||
|
* @since 1.0.0
|
||||||
|
*/
|
||||||
private static function parseRRule($rruleString) : array
|
private static function parseRRule($rruleString) : array
|
||||||
{
|
{
|
||||||
$rrule = [];
|
$rrule = [];
|
||||||
|
|
|
||||||
|
|
@ -28,16 +28,6 @@ use PhpOffice\PhpSpreadsheet\Writer\Pdf;
|
||||||
*/
|
*/
|
||||||
class SpreadsheetWriter extends Pdf
|
class SpreadsheetWriter extends Pdf
|
||||||
{
|
{
|
||||||
/**
|
|
||||||
* Render Pdf
|
|
||||||
*
|
|
||||||
* @todo: can be removed?
|
|
||||||
*
|
|
||||||
* @var bool
|
|
||||||
* @since 1.0.0
|
|
||||||
*/
|
|
||||||
protected bool $isMPdf = true;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Save Spreadsheet to file.
|
* Save Spreadsheet to file.
|
||||||
*
|
*
|
||||||
|
|
@ -47,6 +37,8 @@ class SpreadsheetWriter extends Pdf
|
||||||
*/
|
*/
|
||||||
public function toPdfString(): string
|
public function toPdfString(): string
|
||||||
{
|
{
|
||||||
|
$this->isMPdf = true;
|
||||||
|
|
||||||
$pdf = new \Mpdf\Mpdf();
|
$pdf = new \Mpdf\Mpdf();
|
||||||
|
|
||||||
// Check for paper size and page orientation
|
// Check for paper size and page orientation
|
||||||
|
|
|
||||||
|
|
@ -290,7 +290,7 @@ final class StringUtils
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
// @todo: this should not be necessary
|
// @todo: This should not be necessary but the algorithm above allows for weird combinations.
|
||||||
return \str_replace(
|
return \str_replace(
|
||||||
['</del></del>', '</ins></ins>', '<ins></ins>', '<del></del>', '</ins><ins>', '</del><del>', '</ins> <del>', '</del> <ins>'],
|
['</del></del>', '</ins></ins>', '<ins></ins>', '<del></del>', '</ins><ins>', '</del><del>', '</ins> <del>', '</del> <ins>'],
|
||||||
['</del>', '</ins>', '', '', '', '', '</ins><del>', '</del><ins>'],
|
['</del>', '</ins>', '', '', '', '', '</ins><del>', '</del><ins>'],
|
||||||
|
|
|
||||||
|
|
@ -16,10 +16,12 @@ namespace phpOMS\Views;
|
||||||
|
|
||||||
use phpOMS\Localization\L11nManager;
|
use phpOMS\Localization\L11nManager;
|
||||||
use phpOMS\Localization\Localization;
|
use phpOMS\Localization\Localization;
|
||||||
|
use phpOMS\Localization\Money;
|
||||||
use phpOMS\Message\RequestAbstract;
|
use phpOMS\Message\RequestAbstract;
|
||||||
use phpOMS\Message\ResponseAbstract;
|
use phpOMS\Message\ResponseAbstract;
|
||||||
use phpOMS\Module\Exception\InvalidModuleException;
|
use phpOMS\Module\Exception\InvalidModuleException;
|
||||||
use phpOMS\Module\Exception\InvalidThemeException;
|
use phpOMS\Module\Exception\InvalidThemeException;
|
||||||
|
use phpOMS\Stdlib\Base\FloatInt;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Basic view which can be used as basis for specific implementations.
|
* Basic view which can be used as basis for specific implementations.
|
||||||
|
|
@ -308,14 +310,14 @@ class View extends ViewAbstract
|
||||||
/**
|
/**
|
||||||
* Print a numeric value
|
* Print a numeric value
|
||||||
*
|
*
|
||||||
* @param int|float $numeric Numeric value to print
|
* @param int|float|FloatInt $numeric Numeric value to print
|
||||||
* @param null|string $format Format type to use
|
* @param null|string $format Format type to use
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*
|
*
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
public function getNumeric(int | float $numeric, string $format = null) : string
|
public function getNumeric(int | float | FloatInt $numeric, string $format = null) : string
|
||||||
{
|
{
|
||||||
return $this->l11nManager->getNumeric($this->l11n, $numeric, $format);
|
return $this->l11nManager->getNumeric($this->l11n, $numeric, $format);
|
||||||
}
|
}
|
||||||
|
|
@ -338,18 +340,24 @@ class View extends ViewAbstract
|
||||||
/**
|
/**
|
||||||
* Print a currency
|
* Print a currency
|
||||||
*
|
*
|
||||||
* @param int|float $currency Currency value to print
|
* @param int|float|Money $currency Currency value to print
|
||||||
* @param null|string $format Format type to use
|
* @param int $precision Precision
|
||||||
* @param null|string $symbol Currency name/symbol
|
* @param null|string $symbol Currency name/symbol
|
||||||
* @param int $divide Divide currency by divisor
|
* @param null|string $format Format type to use
|
||||||
|
* @param int $divide Divide currency by divisor
|
||||||
*
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*
|
*
|
||||||
* @since 1.0.0
|
* @since 1.0.0
|
||||||
*/
|
*/
|
||||||
public function getCurrency(int | float $currency, string $format = null, string $symbol = null, int $divide = 1) : string
|
public function getCurrency(
|
||||||
|
int | float | Money $currency,
|
||||||
|
string $symbol = null,
|
||||||
|
string $format = null,
|
||||||
|
int $divide = 1
|
||||||
|
) : string
|
||||||
{
|
{
|
||||||
return $this->l11nManager->getCurrency($this->l11n, $currency, $format, $symbol, $divide);
|
return $this->l11nManager->getCurrency($this->l11n, $currency, $symbol, $format, $divide);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
39
tests/Api/EUVAT/EUVATBffOnlineTest.php
Normal file
39
tests/Api/EUVAT/EUVATBffOnlineTest.php
Normal file
|
|
@ -0,0 +1,39 @@
|
||||||
|
<?php
|
||||||
|
/**
|
||||||
|
* Karaka
|
||||||
|
*
|
||||||
|
* PHP Version 8.1
|
||||||
|
*
|
||||||
|
* @package tests
|
||||||
|
* @copyright Dennis Eichhorn
|
||||||
|
* @license OMS License 2.0
|
||||||
|
* @version 1.0.0
|
||||||
|
* @link https://jingga.app
|
||||||
|
*/
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
namespace phpOMS\tests\Api\EUVAT;
|
||||||
|
|
||||||
|
use phpOMS\Api\EUVAT\EUVATBffOnline;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @testdox phpOMS\tests\Api\EUVAT\EUVATBffOnlineTest: EU VAT German BFF Online validation
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*/
|
||||||
|
final class EUVATBffOnlineTest extends \PHPUnit\Framework\TestCase
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* @testdox The BFF Online service can validate a valid VAT ID
|
||||||
|
* @covers phpOMS\Api\EUVAT\EUVATBffOnline
|
||||||
|
* @group framework
|
||||||
|
*/
|
||||||
|
public function testValidateInvalidId() : void
|
||||||
|
{
|
||||||
|
$bff = new EUVATBffOnline();
|
||||||
|
$status = $bff->validate('DE123456789', 'DE123456789');
|
||||||
|
|
||||||
|
self::assertEquals(0, $status['status']);
|
||||||
|
self::assertEquals('C', $status['vat']);
|
||||||
|
}
|
||||||
|
}
|
||||||
39
tests/Api/EUVAT/EUVATViesTest.php
Normal file
39
tests/Api/EUVAT/EUVATViesTest.php
Normal file
|
|
@ -0,0 +1,39 @@
|
||||||
|
<?php
|
||||||
|
/**
|
||||||
|
* Karaka
|
||||||
|
*
|
||||||
|
* PHP Version 8.1
|
||||||
|
*
|
||||||
|
* @package tests
|
||||||
|
* @copyright Dennis Eichhorn
|
||||||
|
* @license OMS License 2.0
|
||||||
|
* @version 1.0.0
|
||||||
|
* @link https://jingga.app
|
||||||
|
*/
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
namespace phpOMS\tests\Api\EUVAT;
|
||||||
|
|
||||||
|
use phpOMS\Api\EUVAT\EUVATVies;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @testdox phpOMS\tests\Api\EUVAT\EUVATViesTest: EU VAT Vies validation
|
||||||
|
*
|
||||||
|
* @internal
|
||||||
|
*/
|
||||||
|
final class EUVATViesTest extends \PHPUnit\Framework\TestCase
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* @testdox The VIES service can validate a valid VAT ID
|
||||||
|
* @covers phpOMS\Api\EUVAT\EUVATVies
|
||||||
|
* @group framework
|
||||||
|
*/
|
||||||
|
public function testValidateInvalidId() : void
|
||||||
|
{
|
||||||
|
$vies = new EUVATVies();
|
||||||
|
$status = $vies->validate('DE123456789');
|
||||||
|
|
||||||
|
self::assertEquals(0, $status['status']);
|
||||||
|
self::assertEquals('C', $status['vat']);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -7,4 +7,4 @@ use phpOMS\Message\Http\HttpRequest;
|
||||||
|
|
||||||
$request = HttpRequest::createFromSuperglobals();
|
$request = HttpRequest::createFromSuperglobals();
|
||||||
|
|
||||||
echo $request->getRequestLanguage();
|
echo $request->getCountry();
|
||||||
|
|
|
||||||
|
|
@ -59,7 +59,7 @@ final class HttpRequestTest extends \PHPUnit\Framework\TestCase
|
||||||
self::assertEquals('', $request->__toString());
|
self::assertEquals('', $request->__toString());
|
||||||
self::assertFalse($request->hasData('key'));
|
self::assertFalse($request->hasData('key'));
|
||||||
self::assertNull($request->getData('key'));
|
self::assertNull($request->getData('key'));
|
||||||
self::assertEquals('en', $request->getRequestLanguage());
|
self::assertEquals('en', $request->getCountry());
|
||||||
self::assertEquals('en_US', $request->getLocale());
|
self::assertEquals('en_US', $request->getLocale());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -135,7 +135,7 @@ final class NodeTest extends \PHPUnit\Framework\TestCase
|
||||||
|
|
||||||
self::assertInstanceOf(Edge::class, $edge = $node1->setNodeRelative($node2, null, false));
|
self::assertInstanceOf(Edge::class, $edge = $node1->setNodeRelative($node2, null, false));
|
||||||
self::assertCount(1, $node2->getEdges());
|
self::assertCount(1, $node2->getEdges());
|
||||||
self::assertFalse($edge->isDirected());
|
self::assertFalse($edge->isDirected);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -173,7 +173,7 @@ final class NodeTest extends \PHPUnit\Framework\TestCase
|
||||||
$node1->setNodeRelative($node2);
|
$node1->setNodeRelative($node2);
|
||||||
$node1->setNodeRelative($node3);
|
$node1->setNodeRelative($node3);
|
||||||
|
|
||||||
self::assertEquals('C', $node1->getEdgeByNeighbor($node3)->getNode2()->getId());
|
self::assertEquals('C', $node1->getEdgeByNeighbor($node3)->node2->getId());
|
||||||
self::assertNull($node1->getEdgeByNeighbor($node4));
|
self::assertNull($node1->getEdgeByNeighbor($node4));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user