artistList, $this->idList, $this->roleList); self::$cache->delete_value($this->cacheKey()); return $this; } protected function artistList(): array { if (isset($this->artistList)) { return $this->artistList; } $key = $this->cacheKey(); $artistList = self::$cache->get_value($key); if ($artistList === false) { $artistList = $this->artistListRaw(); self::$cache->cache_value($key, $artistList, 86400 * 7); } $this->artistList = $artistList; return $this->artistList; } /** * Generate the artist name. (Individual artists will be clickable, or VA) */ public function link(): string { return $this->renderRole(self::RENDER_HTML); } /** * Generate the artist name as text. */ public function text(): string { return $this->renderRole(self::RENDER_TEXT); } public function nameList(): array { $list = []; foreach ($this->idList() as $role => $artistList) { $list[$role] = array_map(fn ($a) => $a['name'], $artistList); } return $list; } /** * A readable representation of the artists grouped by their roles in a * release group. All artist roles are present as arrays (no need to see if * the key exists). Like roleList() but some of the key names change. * 'main' becomes 'artists' * 'guest' becomes 'with' * 'remixer' becomes 'remixedBy' * 'composer' becomes 'composers' * A role is an array of three keys: ["id" => 801, "aliasid" => 768, "name" => "The Group"] */ public function roleListByType(): array { $list = $this->idList(); return [ 'artists' => $list[ARTIST_MAIN] ?? [], 'with' => $list[ARTIST_GUEST] ?? [], 'remixedBy' => $list[ARTIST_REMIXER] ?? [], 'composers' => $list[ARTIST_COMPOSER] ?? [], 'conductor' => $list[ARTIST_CONDUCTOR] ?? [], 'dj' => $list[ARTIST_DJ] ?? [], 'producer' => $list[ARTIST_PRODUCER] ?? [], 'arranger' => $list[ARTIST_ARRANGER] ?? [], ]; } /** * Returns the id of the first artist that would be shown in the renderRole * display. If it would be shown as "various ...", then it's the first * artist of that role type. * * @return int|null */ public function primaryId(): int|null { $roleList = $this->roleList(); $composerCount = count($roleList['composer'] ?? []); $conductorCount = count($roleList['conductor'] ?? []); $djCount = count($roleList['dj'] ?? []); $mainCount = count($roleList['main'] ?? []); if ($djCount) { return $roleList['dj'][0]['id']; } elseif ($composerCount) { return $roleList['composer'][0]['id']; } elseif ($mainCount) { return $roleList['main'][0]['id']; } elseif ($conductorCount) { return $roleList['conductor'][0]['id']; } return null; } protected function renderRole(int $mode): string { $roleList = $this->roleList(); $arrangerCount = count($roleList['arranger'] ?? []); $composerCount = count($roleList['composer'] ?? []); $conductorCount = count($roleList['conductor'] ?? []); $djCount = count($roleList['dj'] ?? []); $mainCount = count($roleList['main'] ?? []); if ($composerCount + $mainCount + $conductorCount + $djCount === 0) { return ''; } $and = match ($mode) { self::RENDER_HTML => ' & ', default => ' and ', }; $chunk = []; if ($djCount > 0) { $chunk[] = match ($djCount) { 1 => $this->artistLink($mode, $roleList['dj'][0]), 2 => $this->artistLink($mode, $roleList['dj'][0]) . $and . $this->artistLink($mode, $roleList['dj'][1]), default => $this->various('DJs', $roleList['dj'], $mode), }; } else { if ($composerCount > 0) { $chunk[] = match ($composerCount) { 1 => $this->artistLink($mode, $roleList['composer'][0]), 2 => $this->artistLink($mode, $roleList['composer'][0]) . $and . $this->artistLink($mode, $roleList['composer'][1]), default => $this->various('Composers', $roleList['composer'], $mode), }; if ($arrangerCount > 0) { $chunk[] = 'arranged by'; $chunk[] = match ($arrangerCount) { 1 => $this->artistLink($mode, $roleList['arranger'][0]), 2 => $this->artistLink($mode, $roleList['arranger'][0]) . $and . $this->artistLink($mode, $roleList['arranger'][1]), default => $this->various('Arrangers', $roleList['arranger'], $mode), }; } if ($mainCount == 0 and $conductorCount > 0) { $chunk[] = 'conducted by'; } elseif ($mainCount > 0) { $chunk[] = 'performed by'; } } if ($mainCount > 0) { $chunk[] = match ($mainCount) { 1 => $this->artistLink($mode, $roleList['main'][0]), 2 => $this->artistLink($mode, $roleList['main'][0]) . $and . $this->artistLink($mode, $roleList['main'][1]), default => $this->various('Artists', $roleList['main'], $mode), }; } if ($conductorCount > 0) { if ($mainCount > 0) { $chunk[] = 'under'; } $chunk[] = match ($conductorCount) { 1 => $this->artistLink($mode, $roleList['conductor'][0]), 2 => $this->artistLink($mode, $roleList['conductor'][0]) . $and . $this->artistLink($mode, $roleList['conductor'][1]), default => $this->various('Conductors', $roleList['conductor'], $mode), }; } } return implode(' ', $chunk); } protected function various(string $role, array $artistList, int $mode): string { return match ($mode) { self::RENDER_HTML => 'Various $role", default => "Various $role", }; } /** * Generate an HTML anchor for an artist */ protected function artistLink(int $mode, array $info): string { return match ($mode) { self::RENDER_HTML => '' . html_escape($info['name']) . '', default => $info['name'], }; } }