_releases. An entry holds for the plugin version that ran the check only. * * Not final so the resolver can be tested with a mock. */ class ReleaseStore { /** @param string $versionKey Row key of the version (Divi: 'divi_version', so stored rows stay as they are). */ public function __construct(private string $profileId, private string $versionKey = 'version') { } public static function forProfile(Profile $profile): self { return new self($profile->id, $profile->reportVersionKey); } /** * @return list> Rows with the keys , plugin_version, user_id, released_at, * report_id. */ public function entries(): array { $raw = get_option($this->option(), []); $entries = []; foreach (is_array($raw) ? $raw : [] as $row) { if ( is_array($row) && is_string($row[$this->versionKey] ?? null) && is_string($row['plugin_version'] ?? null) && is_int($row['user_id'] ?? null) && is_string($row['released_at'] ?? null) && is_string($row['report_id'] ?? null) ) { $entries[] = [ $this->versionKey => $row[$this->versionKey], 'plugin_version' => $row['plugin_version'], 'user_id' => $row['user_id'], 'released_at' => $row['released_at'], 'report_id' => $row['report_id'], ]; } } return $entries; } /** * @return array|null */ public function find(string $version, string $pluginVersion): ?array { foreach ($this->entries() as $entry) { if ($entry[$this->versionKey] === $version && $entry['plugin_version'] === $pluginVersion) { return $entry; } } return null; } public function add(string $version, string $pluginVersion, int $userId, string $reportId): void { $entries = $this->without($version, $pluginVersion); $entries[] = [ $this->versionKey => $version, 'plugin_version' => $pluginVersion, 'user_id' => $userId, 'released_at' => gmdate('c'), 'report_id' => $reportId, ]; update_option($this->option(), $entries, false); } public function withdraw(string $version, string $pluginVersion): bool { if ($this->find($version, $pluginVersion) === null) { return false; } update_option($this->option(), $this->without($version, $pluginVersion), false); return true; } /** * @return list> Rows with the keys , plugin_version, user_id, released_at, * report_id. */ private function without(string $version, string $pluginVersion): array { return array_values(array_filter( $this->entries(), fn (array $entry): bool => $entry[$this->versionKey] !== $version || $entry['plugin_version'] !== $pluginVersion )); } private function option(): string { return 'lit_mcp_' . $this->profileId . '_releases'; } }