138 lines
3.3 KiB
TypeScript
138 lines
3.3 KiB
TypeScript
import {Component, html} from 'htm/preact';
|
|
|
|
import ExternalAnchor from '../components/external-anchor.js';
|
|
import Release from '../utilities/release.js';
|
|
|
|
type Props = {
|
|
mbid: string;
|
|
};
|
|
|
|
type State = {
|
|
loading: 'calling-api' | 'invalid-id' | 'unknown-release' | 'finished';
|
|
release: Release | undefined;
|
|
};
|
|
|
|
export default class ReleasePage extends Component<Props, State> {
|
|
constructor(props: Props) {
|
|
props.mbid = encodeURIComponent(props.mbid);
|
|
|
|
super(props);
|
|
|
|
this.state = {
|
|
loading: 'calling-api',
|
|
release: undefined,
|
|
};
|
|
}
|
|
|
|
validateMbid(mbid: string): boolean {
|
|
return mbid.length === 36 && mbid.split('-').length === 5;
|
|
}
|
|
|
|
async componentDidMount() {
|
|
const {mbid} = this.props;
|
|
|
|
if (!this.validateMbid(mbid)) {
|
|
this.setState({loading: 'invalid-id'});
|
|
return;
|
|
}
|
|
|
|
try {
|
|
this.setState({
|
|
loading: 'finished',
|
|
release: await Release.fromMbid(mbid),
|
|
});
|
|
} catch (error: unknown) {
|
|
console.error(error);
|
|
this.setState({loading: 'unknown-release'});
|
|
}
|
|
}
|
|
|
|
render() {
|
|
const {mbid} = this.props;
|
|
const {loading, release} = this.state;
|
|
|
|
if (loading === 'calling-api') {
|
|
return html`Loading MBID: ${mbid}`;
|
|
}
|
|
|
|
if (loading === 'invalid-id') {
|
|
return html`Invalid MBID: ${mbid}`;
|
|
}
|
|
|
|
if (loading === 'unknown-release') {
|
|
return html`No release found with MBID: ${mbid}`;
|
|
}
|
|
|
|
if (loading === 'finished' && release !== undefined) {
|
|
document.title = release.display();
|
|
|
|
const date =
|
|
release.date === undefined
|
|
? undefined
|
|
: html`<span class="release-date">${release.date}</span>`;
|
|
|
|
const image =
|
|
release.image === undefined
|
|
? undefined
|
|
: html`<img class="cover-art" src="${release.image}" />`;
|
|
|
|
const urls = release.links.map((link) => {
|
|
let linkImage;
|
|
if (link.icon !== undefined) {
|
|
linkImage = html`<img src="/icons/${link.icon}" />`;
|
|
}
|
|
|
|
return html`
|
|
<li class="release-link">
|
|
<a href="${link.original}" rel="noopener noreferrer">
|
|
${linkImage} ${link.text}
|
|
</a>
|
|
</li>
|
|
`;
|
|
});
|
|
|
|
const releaseUrl = `https://musicbrainz.org/release/${mbid}`;
|
|
if (urls.length === 0) {
|
|
const editUrl = `${releaseUrl}/edit`;
|
|
urls.push(
|
|
html`
|
|
<li class="no-links">
|
|
<p>
|
|
There are no links for this release yet, consider${' '}
|
|
<${ExternalAnchor} url="${editUrl}" text="adding some" />?
|
|
</p>
|
|
</li>
|
|
`,
|
|
);
|
|
} else {
|
|
urls.push(
|
|
html`<li class="divider"></li>`,
|
|
html`
|
|
<li class="release-link">
|
|
<a href="${releaseUrl}" rel="noopener noreferrer">
|
|
<img src="/icons/musicbrainz.png" /> MusicBrainz
|
|
</a>
|
|
</li>
|
|
`,
|
|
);
|
|
}
|
|
|
|
return html`
|
|
<div class="release">
|
|
<header class="release-header">
|
|
${image}
|
|
<h1>${release.artist}<br />${release.title}</h1>
|
|
${date}
|
|
</header>
|
|
|
|
<main class="release-main">
|
|
<ul class="release-links">
|
|
${urls}
|
|
</ul>
|
|
</main>
|
|
</div>
|
|
`;
|
|
}
|
|
}
|
|
}
|