UNPKG

@paperbits/common

Version:
120 lines (93 loc) 4.34 kB
import * as MediaUtils from "./mediaUtils"; import { IMediaService } from "./IMediaService"; import { IPermalinkResolver, HyperlinkModel } from "../permalinks"; import { MediaContract } from "./mediaContract"; import { ContentItemContract } from "../contentModel"; import { HyperlinkContract } from "../editing"; export class MediaPermalinkResolver implements IPermalinkResolver { protected mediaPath: string = "uploads/"; constructor(private readonly mediaService: IMediaService) { } public canHandleTarget(targetKey: string): boolean { return targetKey.startsWith("uploads/"); } public async getUrlByTargetKey(mediaKey: string): Promise<string> { if (!mediaKey) { throw new Error(`Parameter "mediaKey" not specified.`); } try { const media = await this.mediaService.getMediaByKey(mediaKey); if (!media) { console.warn(`Could not find permalink by key ${mediaKey}.`); return null; } if (media.variants?.length > 0) { // Currently this case is possible only with CDN and image optimization services. const biggestVariant = MediaUtils.getBiggestMediaVariant(media); return biggestVariant.downloadUrl; } else { return media.permalink; } } catch (error) { console.warn(`Could not fetch permalink by key ${mediaKey}. Error: ${error.message}`); return null; } } private async getHyperlink(mediaContract: MediaContract, hyperlinkContract?: HyperlinkContract): Promise<HyperlinkModel> { const hyperlinkModel = new HyperlinkModel(); hyperlinkModel.targetKey = mediaContract.key; hyperlinkModel.href = mediaContract.permalink; hyperlinkModel.title = mediaContract.fileName || mediaContract.permalink; if (hyperlinkContract) { hyperlinkModel.target = hyperlinkContract.target; hyperlinkModel.anchor = hyperlinkContract.anchor; hyperlinkModel.anchorName = hyperlinkContract.anchorName; } return hyperlinkModel; } public async getHyperlinkByTargetKey(targetKey: string): Promise<HyperlinkModel> { if (!targetKey) { throw new Error("Target key cannot be null or empty."); } if (!targetKey.startsWith(this.mediaPath)) { return null; } const mediaContract = await this.mediaService.getMediaByKey(targetKey); if (!mediaContract) { console.warn(`Could create hyperlink for target with key ${targetKey}.`); return null; } const hyperlink = await this.getHyperlink(mediaContract); return hyperlink; } public async getContentItemByPermalink(permalink: string): Promise<ContentItemContract> { if (!permalink) { throw new Error(`Parameter "permalink" not specified.`); } const mediaContract = await this.mediaService.getMediaByPermalink(permalink); return mediaContract; } public async getHyperlinkFromContract(hyperlinkContract: HyperlinkContract, locale?: string): Promise<HyperlinkModel> { if (!hyperlinkContract.targetKey) { throw new Error("Target key cannot be null or empty."); } if (!hyperlinkContract.targetKey.startsWith(this.mediaPath)) { return null; } let hyperlinkModel: HyperlinkModel; if (hyperlinkContract.targetKey) { const mediaContract = await this.mediaService.getMediaByKey(hyperlinkContract.targetKey); if (mediaContract) { return this.getHyperlink(mediaContract, hyperlinkContract); } } hyperlinkModel = new HyperlinkModel(); hyperlinkModel.title = "Unset link"; hyperlinkModel.target = hyperlinkContract.target; hyperlinkModel.targetKey = hyperlinkContract.targetKey; hyperlinkModel.href = "#"; hyperlinkModel.anchor = hyperlinkContract.anchor; hyperlinkModel.anchorName = hyperlinkContract.anchorName; return hyperlinkModel; } }