Du kan inte välja fler än 25 ämnen Ämnen måste starta med en bokstav eller siffra, kan innehålla bindestreck ('-') och vara max 35 tecken långa.

238 lines
5.8KB

  1. <?php
  2. namespace App\Kintone\Models;
  3. use App\Kintone\KintoneRecordQuery;
  4. use App\Util\DateUtil;
  5. use Illuminate\Support\Arr;
  6. use Illuminate\Support\Carbon;
  7. use stdClass;
  8. abstract class KintoneModel
  9. {
  10. const FIELD_RECORD_NUMBER = "レコード番号";
  11. const FIELD_CREATED_TIME = "作成日時";
  12. const FIELD_UPDATED_TIME = "更新日時";
  13. protected ?int $recordId = null;
  14. protected ?int $revision = null;
  15. protected ?Carbon $createdAt = null;
  16. protected ?Carbon $updatedAt = null;
  17. protected ?stdClass $dataOrigin = null;
  18. protected stdClass $data;
  19. protected array $fields = [];
  20. private array $changed = [];
  21. public function __construct()
  22. {
  23. $this->data = new stdClass();
  24. }
  25. public function set(string $fieldCode, $value)
  26. {
  27. $field = Arr::get($this->fields, $fieldCode);
  28. if ($field instanceof FieldType) {
  29. $this->setData($fieldCode, $field, $value);
  30. } else if (is_array($field)) {
  31. $this->setTable($fieldCode, $value);
  32. }
  33. data_set($this->changed, $fieldCode, true);
  34. return $this;
  35. }
  36. private function setTable(string $fieldCode, array $table)
  37. {
  38. foreach ($table as $index => $row) {
  39. $row = data_get($row, "value");
  40. $this->setTableRow($fieldCode, $index, $row);
  41. }
  42. }
  43. private function setTableRow(string $fieldCode, int $index, array $row)
  44. {
  45. foreach ($row as $columnFieldCode => $column) {
  46. $value = $column["value"];
  47. $type = $this->fields[$fieldCode][$columnFieldCode];
  48. $insertKey = sprintf("%s.%d.%s", $fieldCode, $index, $columnFieldCode);
  49. $this->setData($insertKey, $type, $value);
  50. }
  51. }
  52. private function setData(string $path, FieldType $type, $value)
  53. {
  54. if (
  55. $type === FieldType::STRING ||
  56. $type === FieldType::ARRAY
  57. ) {
  58. data_set($this->data, $path, $value);
  59. // logger([$path, $value]);
  60. return $this;
  61. }
  62. if ($type === FieldType::DATETIME) {
  63. data_set($this->data, $path, DateUtil::parse($value));
  64. return $this;
  65. }
  66. }
  67. public function setDataFromRecordResponse(array $data): bool
  68. {
  69. $ret = true;
  70. foreach ($data as $fieldCode => $ele) {
  71. $type = data_get($ele, "type");
  72. $value = data_get($ele, "value");
  73. if ($type === "RECORD_NUMBER") {
  74. $this->recordId = $value;
  75. continue;
  76. }
  77. if ($type === "__REVISION__") {
  78. $this->revision = $value;
  79. continue;
  80. }
  81. if ($type === "CREATED_TIME") {
  82. $this->createdAt = DateUtil::parse($value);
  83. continue;
  84. }
  85. if ($type === "UPDATED_TIME") {
  86. $this->updatedAt = DateUtil::parse($value);
  87. continue;
  88. }
  89. $this->set($fieldCode, $value);
  90. }
  91. $ret = $this->setDataCustom($data);
  92. if ($ret) {
  93. $this->clean();
  94. }
  95. return $ret;
  96. }
  97. /**
  98. * 変更前データを現在データで上書きする
  99. *
  100. * @return void
  101. */
  102. public function clean(?int $revision = null)
  103. {
  104. $this->dataOrigin = clone $this->data;
  105. if ($revision !== null) {
  106. $this->revision = $revision;
  107. }
  108. $this->changed = [];
  109. }
  110. public function getApiLayout(): array
  111. {
  112. $ret = [];
  113. foreach ($this->fields as $fieldCode => $type) {
  114. // 変更があった項目のみレイアウトへ出力する
  115. if (!Arr::has($this->changed, $fieldCode)) {
  116. continue;
  117. }
  118. $path = sprintf("%s.value", $fieldCode);
  119. if ($type === FieldType::STRING) {
  120. data_set($ret, $path, data_get($this->data, $fieldCode));
  121. continue;
  122. }
  123. if ($type === FieldType::ARRAY) {
  124. data_set($ret, $path, data_get($this->data, $fieldCode));
  125. continue;
  126. }
  127. if ($type === FieldType::DATETIME) {
  128. data_set($ret, $path, $this->getDate($fieldCode)->toIso8601ZuluString());
  129. continue;
  130. }
  131. }
  132. return array_merge($ret, $this->getApiLayoutCustom());
  133. }
  134. public function get(string $key)
  135. {
  136. return data_get($this->data, $key);
  137. }
  138. public function getStr(string $key): ?string
  139. {
  140. return $this->get($key);
  141. }
  142. public function getNumber(string $key): ?int
  143. {
  144. return $this->get($key);
  145. }
  146. public function getDate(string $key): ?Carbon
  147. {
  148. return $this->get($key);
  149. }
  150. public function getTable(string $key): ?array
  151. {
  152. return $this->get($key);
  153. }
  154. public function getRecordId(): ?int
  155. {
  156. return $this->recordId;
  157. }
  158. public function setRecordId(int $recordId): void
  159. {
  160. $this->recordId = $recordId;
  161. }
  162. public function getRevision(): ?int
  163. {
  164. return $this->revision;
  165. }
  166. public function setRevision(int $revision): void
  167. {
  168. $this->revision = $revision;
  169. }
  170. public function getUpdatedAt(): ?Carbon
  171. {
  172. return $this->updatedAt;
  173. }
  174. public function getCreatedAt(): ?Carbon
  175. {
  176. return $this->createdAt;
  177. }
  178. static public function query()
  179. {
  180. return new KintoneRecordQuery(static::class);
  181. }
  182. /**
  183. * オーバーライドを期待
  184. *
  185. * @param array $data
  186. * @return boolean
  187. */
  188. protected function setDataCustom(array $data): bool
  189. {
  190. return true;
  191. }
  192. /**
  193. * オーバーライドを期待
  194. *
  195. * @return array
  196. */
  197. protected function getApiLayoutCustom(): array
  198. {
  199. return [];
  200. }
  201. }