*/ private array $values; /** * @param array $values */ private function __construct(array $values) { $this->values = $values; } /** * @param array $raw */ public static function from_array(array $raw, int $default_per_page = 20): self { $status = sanitize_key((string) ($raw['status'] ?? self::STATUS_ALL)); if (!in_array($status, self::STATUS_GROUPS, true)) { $status = self::STATUS_ALL; } $product_type = sanitize_key((string) ($raw['type'] ?? $raw['product_type'] ?? '')); $types = DomainModel::order_product_type_labels(); if ($product_type !== '' && !isset($types[$product_type])) { $product_type = ''; } $order_number = strtoupper(preg_replace('/[^A-Za-z0-9_-]/', '', (string) ($raw['order_number'] ?? '')) ?? ''); $order_number = substr($order_number, 0, 32); $page = max(1, absint($raw['page'] ?? 1)); $per_page = max(1, min(50, absint($raw['per_page'] ?? $default_per_page))); return new self([ 'status' => $status, 'product_type' => $product_type, 'order_number' => $order_number, 'page' => $page, 'per_page' => $per_page, ]); } public function status(): string { return (string) $this->values['status']; } public function product_type(): string { return (string) $this->values['product_type']; } public function order_number(): string { return (string) $this->values['order_number']; } public function page(): int { return (int) $this->values['page']; } public function per_page(): int { return (int) $this->values['per_page']; } /** @return string[] */ public function database_statuses(): array { return match ($this->status()) { self::STATUS_PENDING => [Order::STATUS_CREATED, Order::STATUS_PENDING], self::STATUS_COMPLETED => [Order::STATUS_PAID], self::STATUS_CLOSED => [Order::STATUS_CANCELLED, Order::STATUS_EXPIRED], default => [ Order::STATUS_CREATED, Order::STATUS_PENDING, Order::STATUS_PAID, Order::STATUS_CANCELLED, Order::STATUS_EXPIRED, ], }; } /** @return array */ public function url_values(): array { return array_filter([ 'order_status' => $this->status() !== self::STATUS_ALL ? $this->status() : '', 'order_type' => $this->product_type(), 'order_number' => $this->order_number(), 'order_page' => $this->page() > 1 ? $this->page() : '', ], static fn($value): bool => $value !== ''); } /** @return array */ public function repository_args(): array { return [ 'status_in' => $this->database_statuses(), 'product_type' => $this->product_type(), 'order_number_prefix' => $this->order_number(), 'limit' => $this->per_page(), 'offset' => ($this->page() - 1) * $this->per_page(), ]; } }