$data */ public static function fromApiResponse(array $data): self { return new self( currency: $data['currency'] ?? 'USD', initial: ($data['initial'] ?? 0) / 100, final: ($data['final'] ?? 0) / 100, discountPercent: $data['discount_percent'] ?? 0, formattedPrice: $data['final_formatted'] ?? null, ); } public static function free(): self { return new self( currency: 'USD', initial: 0.0, final: 0.0, discountPercent: 0, formattedPrice: 'Free', ); } public function isOnSale(): bool { return $this->discountPercent > 0; } public function isFree(): bool { return $this->final <= 0; } public function getSavings(): float { return max(0, $this->initial - $this->final); } public function getDisplayPrice(): string { if ($this->formattedPrice !== null) { return $this->formattedPrice; } if ($this->isFree()) { return 'Free'; } return sprintf('%s %.2f', $this->currency, $this->final); } }