200 ) { $errors[] = __( 'The API key label must be 200 characters or fewer.', 'releasecart' ); } if ( 1 !== preg_match( self::PUBLIC_KEY_PATTERN, $publicKey ) ) { $errors[] = __( 'The public key is malformed.', 'releasecart' ); } if ( '' === $secretHash ) { $errors[] = __( 'An API key cannot exist without a secret.', 'releasecart' ); } if ( array() !== $errors ) { // phpcs:ignore WordPress.Security.EscapeOutput.ExceptionNotEscaped -- Not HTML output here; escaped where printed. throw ApiKeyValidationException::withErrors( $errors ); } $this->id = $id; $this->userId = $userId; $this->label = $label; $this->publicKey = $publicKey; $this->secretHash = $secretHash; $this->permission = $permission; $this->status = $status; $this->lastUsedAt = $lastUsedAt; $this->createdAt = $createdAt; } /** * The row id, or null before the first persist. * * @since 1.0.0 * * @return int|null The id. */ public function id(): ?int { return $this->id; } /** * The owning WP user id. * * @since 1.0.0 * * @return int The user id. */ public function userId(): int { return $this->userId; } /** * The human label the admin gave the key. * * @since 1.0.0 * * @return string The label. */ public function label(): string { return $this->label; } /** * The public lookup key. * * @since 1.0.0 * * @return string The rck_-prefixed public key. */ public function publicKey(): string { return $this->publicKey; } /** * The hash of the secret (never the plaintext). * * @since 1.0.0 * * @return string The wp_hash_password() hash. */ public function secretHash(): string { return $this->secretHash; } /** * The read/write permission. * * @since 1.0.0 * * @return ApiKeyPermission The permission. */ public function permission(): ApiKeyPermission { return $this->permission; } /** * The lifecycle status. * * @since 1.0.0 * * @return ApiKeyStatus The status. */ public function status(): ApiKeyStatus { return $this->status; } /** * When the key last authenticated a request. * * @since 1.0.0 * * @return DateTimeImmutable|null The last-used instant, or null if never. */ public function lastUsedAt(): ?DateTimeImmutable { return $this->lastUsedAt; } /** * When the key was created. * * @since 1.0.0 * * @return DateTimeImmutable|null The creation instant, or null before persisting. */ public function createdAt(): ?DateTimeImmutable { return $this->createdAt; } /** * Whether the key may authenticate at all. * * @since 1.0.0 * * @return bool True while the key is active. */ public function isActive(): bool { return ApiKeyStatus::Active === $this->status; } /** * Whether the key may perform non-safe HTTP methods. * * @since 1.0.0 * * @return bool True for a write key. */ public function canWrite(): bool { return ApiKeyPermission::Write === $this->permission; } /** * A copy with a different status. * * @since 1.0.0 * * @param ApiKeyStatus $status The new status. * @return self The modified copy. */ public function withStatus( ApiKeyStatus $status ): self { return new self( $this->id, $this->userId, $this->label, $this->publicKey, $this->secretHash, $this->permission, $status, $this->lastUsedAt, $this->createdAt ); } /** * A copy with a fresh last-used stamp. * * @since 1.0.0 * * @param DateTimeImmutable $lastUsedAt The authenticating instant. * @return self The modified copy. */ public function withLastUsedAt( DateTimeImmutable $lastUsedAt ): self { return new self( $this->id, $this->userId, $this->label, $this->publicKey, $this->secretHash, $this->permission, $this->status, $lastUsedAt, $this->createdAt ); } /** * Return a copy with its assigned row ID. * * @since 1.0.0 * * @param int $id The assigned row id. * @return self The modified copy. */ public function withId( int $id ): self { return new self( $id, $this->userId, $this->label, $this->publicKey, $this->secretHash, $this->permission, $this->status, $this->lastUsedAt, $this->createdAt ); } }