Code Coverage |
||||||||||
Lines |
Functions and Methods |
Classes and Traits |
||||||||
Total | |
92.31% |
24 / 26 |
|
66.67% |
2 / 3 |
CRAP | |
0.00% |
0 / 1 |
Configuration | |
92.31% |
24 / 26 |
|
66.67% |
2 / 3 |
11.06 | |
0.00% |
0 / 1 |
__construct | |
100.00% |
1 / 1 |
|
100.00% |
1 / 1 |
1 | |||
load | |
89.47% |
17 / 19 |
|
0.00% |
0 / 1 |
6.04 | |||
replace | |
100.00% |
6 / 6 |
|
100.00% |
1 / 1 |
4 |
1 | <?php |
2 | |
3 | declare(strict_types=1); |
4 | |
5 | namespace PeServer\Core\Serialization; |
6 | |
7 | use PeServer\Core\Collection\Arr; |
8 | use PeServer\Core\Code; |
9 | use PeServer\Core\IO\Directory; |
10 | use PeServer\Core\IO\File; |
11 | use PeServer\Core\IO\Path; |
12 | use PeServer\Core\Text; |
13 | use PeServer\Core\Throws\ArgumentException; |
14 | |
15 | /** |
16 | * 設定ファイルの読み込み加工処理。 |
17 | */ |
18 | class Configuration |
19 | { |
20 | #region define |
21 | |
22 | public const FILE_TYPE_DEFAULT = Text::EMPTY; |
23 | public const FILE_TYPE_JSON = 'json'; |
24 | |
25 | #endregion |
26 | |
27 | #region variable |
28 | |
29 | /** |
30 | * 環境。 |
31 | */ |
32 | private readonly string $environment; |
33 | |
34 | #endregion |
35 | |
36 | /** |
37 | * 生成 |
38 | * |
39 | * @param string $environment 環境。 |
40 | */ |
41 | public function __construct(string $environment) |
42 | { |
43 | $this->environment = $environment; |
44 | } |
45 | |
46 | #region function |
47 | |
48 | /** |
49 | * 設定ファイル読み込み。 |
50 | * |
51 | * @param string $directoryPath 設定ファイル配置ディレクトリ。 |
52 | * @param string $fileName ファイル名。 |
53 | * @param string $fileType ファイル種別。未指定(FILE_TYPE_DEFAULT)の場合はファイル拡張子から判断する |
54 | * @return array<mixed> |
55 | */ |
56 | public function load(string $directoryPath, string $fileName, string $fileType = self::FILE_TYPE_DEFAULT): array |
57 | { |
58 | $baseFileExtension = Path::getFileExtension($fileName, false); |
59 | |
60 | $confType = $fileType; |
61 | if ($fileType === self::FILE_TYPE_DEFAULT) { |
62 | $confType = match (Text::toLower($baseFileExtension)) { |
63 | 'json' => self::FILE_TYPE_JSON, |
64 | default => self::FILE_TYPE_DEFAULT, |
65 | }; |
66 | } |
67 | // とりあえずは JSON だけ相手にする |
68 | if ($confType !== self::FILE_TYPE_JSON) { |
69 | throw new ArgumentException('$fileName'); |
70 | } |
71 | |
72 | $baseFilePath = Path::combine($directoryPath, $fileName); |
73 | $environmentFileName = Path::setEnvironmentName($fileName, $this->environment); |
74 | $environmentFilePath = Path::combine($directoryPath, $environmentFileName); |
75 | |
76 | /** @var array<mixed> */ |
77 | $configuration = []; |
78 | |
79 | /** @var array<mixed> */ |
80 | $baseConfiguration = File::readJsonFile($baseFilePath); |
81 | if (File::exists($environmentFilePath)) { |
82 | /** @var array<mixed> */ |
83 | $environmentConfiguration = File::readJsonFile($environmentFilePath); |
84 | $configuration = Arr::replace($baseConfiguration, $environmentConfiguration); |
85 | } else { |
86 | $configuration = $baseConfiguration; |
87 | } |
88 | |
89 | return $configuration; |
90 | } |
91 | |
92 | /** |
93 | * 設定データの再帰的置き換え。 |
94 | * |
95 | * @param array<mixed> $array 元データ。配列の値のみが置き換え対象となる。 |
96 | * @param array<string,string> $map 置き換え設定 |
97 | * @param non-empty-string $head 置き換え開始文字列 |
98 | * @param non-empty-string $tail 置き換え終了文字列 |
99 | * @return array<mixed> |
100 | */ |
101 | public function replace(array $array, array $map, string $head, string $tail): array |
102 | { |
103 | foreach ($array as $key => $value) { |
104 | if (is_array($value)) { |
105 | $array[$key] = $this->replace($value, $map, $head, $tail); |
106 | } elseif (is_string($value)) { |
107 | $array[$key] = Text::replaceMap(Code::toLiteralString($value), $map, $head, $tail); |
108 | } |
109 | } |
110 | |
111 | return $array; |
112 | } |
113 | |
114 | #endregion |
115 | } |