diff --git a/src/Types.ts b/src/Types.ts index e6e28d6..5ceb9c0 100644 --- a/src/Types.ts +++ b/src/Types.ts @@ -16,6 +16,16 @@ export interface ReplaceCallbackOptions { * `` tags for preloading fonts as a string */ linksAsString: string; + + /** + * `` tags for preloading fonts as an array of strings + */ + linksAsArray: string[]; + + /** + * Link data for building a `` tag + */ + linksAsStructuredData: LinkData[]; } /** @@ -81,6 +91,8 @@ export interface PluginOptions { replaceCallback?: ({ indexSource, linksAsString, + linksAsArray, + linksAsStructuredData, }: ReplaceCallbackOptions) => string; /** @@ -96,3 +108,27 @@ export interface PluginOptions { */ filter?: string | RegExp; } + +/** + * Data to build link. + */ +export interface LinkData { + /** + * Is the font request crossorigin or not. + * + * Defaults to true. + */ + crossorigin: PluginOptions["crossorigin"]; + + /** + * Type of load. It can be either "preload" or "prefetch". + * + * Defaults to "preload". + */ + loadType: PluginOptions["loadType"]; + + /** + * Final value of href attribute of the . + */ + href: string; +} diff --git a/src/index.ts b/src/index.ts index 9f01811..785e01b 100644 --- a/src/index.ts +++ b/src/index.ts @@ -2,7 +2,7 @@ import { JSDOM } from "jsdom"; import fs from "fs"; import path from "path"; import { Compiler, Compilation } from "webpack"; -import { Callback, LoadType, PluginOptions } from "./Types"; +import { Callback, LinkData, LoadType, PluginOptions } from "./Types"; export default class WebpackFontPreloadPlugin { private options: PluginOptions; @@ -67,9 +67,17 @@ export default class WebpackFontPreloadPlugin { const publicPath = (outputOptions && outputOptions.publicPath) || ""; if (indexSource) { let strLink = ""; + const linksAsArray: string[] = []; + const linksAsStructuredData: LinkData[] = []; assets.forEach((asset) => { if (this.isFontAsset(asset.name) && this.isFiltered(asset.name)) { strLink += this.getLinkTag(asset.name, publicPath.toString()); + linksAsArray.push( + this.getLinkTag(asset.name, publicPath.toString()) + ); + linksAsStructuredData.push( + this.getLinkData(asset.name, publicPath.toString()) + ); } }); // If `replaceCallback` is specified then app is responsible to forming the updated @@ -80,6 +88,8 @@ export default class WebpackFontPreloadPlugin { this.options.replaceCallback({ indexSource: indexSource.toString(), linksAsString: strLink, + linksAsArray, + linksAsStructuredData, }) ); } else { @@ -162,6 +172,20 @@ export default class WebpackFontPreloadPlugin { >`; } + /** + * Get all the necesarry data for building of a `` tag for provided name + * and public path. + * + * @param {string} name Name of the font asset + * @param {string} publicPath Public path from webpack configuration + * @returns {LinkData} Structured data of the link + * + */ + private getLinkData(name: string, publicPath: string): LinkData { + const { crossorigin, loadType } = this.options; + return { crossorigin, loadType, href: `${publicPath}${name}` }; + } + /** * Check if the specified asset is a font asset. * diff --git a/test/utils/TestUtil.ts b/test/utils/TestUtil.ts index 3848608..e05500b 100644 --- a/test/utils/TestUtil.ts +++ b/test/utils/TestUtil.ts @@ -161,7 +161,7 @@ export function areValidFonts( validExtensions: string[] ): Promise { const expression = /(?:\.([^.]+))?$/; - const errors = []; + const errors: string[] = []; if (fonts.length === 0) { return Promise.reject(["No font's are preloaded in the output."]); }