@smoothcdn/loader 1.0.1 → 1.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/core/config.js +8 -1
- package/dist/core/html-snippets.d.ts +42 -0
- package/dist/core/html-snippets.d.ts.map +1 -0
- package/dist/core/html-snippets.js +55 -0
- package/dist/core/index.d.ts +2 -0
- package/dist/core/index.d.ts.map +1 -1
- package/dist/core/index.js +1 -0
- package/dist/core/utils.d.ts.map +1 -1
- package/dist/core/utils.js +20 -4
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/next/CDNImage.d.ts +2 -7
- package/dist/next/CDNImage.d.ts.map +1 -1
- package/dist/next/CDNImage.js +1 -6
- package/dist/next/Script.d.ts +2 -2
- package/dist/next/Script.d.ts.map +1 -1
- package/dist/next/Script.js +6 -3
- package/dist/next/Style.d.ts +2 -1
- package/dist/next/Style.d.ts.map +1 -1
- package/dist/next/Style.js +6 -3
- package/dist/next/index.d.ts +1 -1
- package/dist/next/index.d.ts.map +1 -1
- package/dist/next/index.js +1 -1
- package/dist/react/CDNAudio.d.ts +5 -2
- package/dist/react/CDNAudio.d.ts.map +1 -1
- package/dist/react/CDNAudio.js +3 -2
- package/dist/react/CDNImage.d.ts +5 -4
- package/dist/react/CDNImage.d.ts.map +1 -1
- package/dist/react/CDNImage.js +19 -14
- package/dist/react/CDNVideo.d.ts +5 -2
- package/dist/react/CDNVideo.d.ts.map +1 -1
- package/dist/react/CDNVideo.js +3 -2
- package/dist/vue/CDNImage.d.ts +29 -1
- package/dist/vue/CDNImage.d.ts.map +1 -1
- package/dist/vue/CDNImage.js +46 -5
- package/package.json +1 -1
- package/readme.md +15 -8
package/dist/core/config.js
CHANGED
|
@@ -23,7 +23,7 @@ export function normalizeConfig(scdnConfig) {
|
|
|
23
23
|
return {
|
|
24
24
|
...scdnConfig,
|
|
25
25
|
cdnUrl: scdnConfig.cdnUrl || resolveCdnUrl(scdnConfig),
|
|
26
|
-
version: scdnConfig.version
|
|
26
|
+
version: normalizeOptionalString(scdnConfig.version),
|
|
27
27
|
replacePath: scdnConfig.replacePath || scdnConfig.replacePaths,
|
|
28
28
|
variants: scdnConfig.variants || [
|
|
29
29
|
{
|
|
@@ -38,6 +38,13 @@ export function normalizeConfig(scdnConfig) {
|
|
|
38
38
|
]
|
|
39
39
|
};
|
|
40
40
|
}
|
|
41
|
+
const normalizeOptionalString = (value) => {
|
|
42
|
+
if (typeof value !== "string") {
|
|
43
|
+
return undefined;
|
|
44
|
+
}
|
|
45
|
+
const trimmedValue = value.trim();
|
|
46
|
+
return trimmedValue || undefined;
|
|
47
|
+
};
|
|
41
48
|
const resolveCdnUrl = (scdnConfig) => {
|
|
42
49
|
if (scdnConfig.customSubdomain) {
|
|
43
50
|
return `https://${scdnConfig.customSubdomain}.smoothcdn.com`;
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
export type CdnLoadingMode = {
|
|
2
|
+
isCritical?: boolean;
|
|
3
|
+
};
|
|
4
|
+
export type ImageVariantSource = {
|
|
5
|
+
width: number;
|
|
6
|
+
url: string;
|
|
7
|
+
};
|
|
8
|
+
export type ImageSnippetAttributes = {
|
|
9
|
+
src: string;
|
|
10
|
+
srcSet?: string;
|
|
11
|
+
sizes?: string;
|
|
12
|
+
loading?: "lazy";
|
|
13
|
+
decoding: "async" | "sync";
|
|
14
|
+
fetchPriority?: "high";
|
|
15
|
+
width?: number | string;
|
|
16
|
+
height?: number | string;
|
|
17
|
+
};
|
|
18
|
+
export type MediaSnippetAttributes = {
|
|
19
|
+
preload: "auto" | "none";
|
|
20
|
+
};
|
|
21
|
+
export type ScriptSnippetAttributes = {
|
|
22
|
+
async?: true;
|
|
23
|
+
defer?: true;
|
|
24
|
+
preload?: true;
|
|
25
|
+
};
|
|
26
|
+
export type StyleSnippetAttributes = {
|
|
27
|
+
preload?: true;
|
|
28
|
+
};
|
|
29
|
+
export declare function getImageSnippetAttributes({ src, variants, alt, isCritical, width, height, }: {
|
|
30
|
+
src: string;
|
|
31
|
+
variants?: ImageVariantSource[];
|
|
32
|
+
alt: string;
|
|
33
|
+
isCritical?: boolean;
|
|
34
|
+
width?: number | string;
|
|
35
|
+
height?: number | string;
|
|
36
|
+
}): ImageSnippetAttributes & {
|
|
37
|
+
alt: string;
|
|
38
|
+
};
|
|
39
|
+
export declare function getMediaSnippetAttributes({ isCritical }?: CdnLoadingMode): MediaSnippetAttributes;
|
|
40
|
+
export declare function getScriptSnippetAttributes({ isCritical }?: CdnLoadingMode): ScriptSnippetAttributes;
|
|
41
|
+
export declare function getStyleSnippetAttributes({ isCritical }?: CdnLoadingMode): StyleSnippetAttributes;
|
|
42
|
+
//# sourceMappingURL=html-snippets.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"html-snippets.d.ts","sourceRoot":"","sources":["../../src/core/html-snippets.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,cAAc,GAAG;IACzB,UAAU,CAAC,EAAE,OAAO,CAAC;CACxB,CAAC;AAEF,MAAM,MAAM,kBAAkB,GAAG;IAC7B,KAAK,EAAE,MAAM,CAAC;IACd,GAAG,EAAE,MAAM,CAAC;CACf,CAAC;AAEF,MAAM,MAAM,sBAAsB,GAAG;IACjC,GAAG,EAAE,MAAM,CAAC;IACZ,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,OAAO,GAAG,MAAM,CAAC;IAC3B,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,KAAK,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;IACxB,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;CAC5B,CAAC;AAEF,MAAM,MAAM,sBAAsB,GAAG;IACjC,OAAO,EAAE,MAAM,GAAG,MAAM,CAAC;CAC5B,CAAC;AAEF,MAAM,MAAM,uBAAuB,GAAG;IAClC,KAAK,CAAC,EAAE,IAAI,CAAC;IACb,KAAK,CAAC,EAAE,IAAI,CAAC;IACb,OAAO,CAAC,EAAE,IAAI,CAAC;CAClB,CAAC;AAEF,MAAM,MAAM,sBAAsB,GAAG;IACjC,OAAO,CAAC,EAAE,IAAI,CAAC;CAClB,CAAC;AAEF,wBAAgB,yBAAyB,CACrC,EACI,GAAG,EACH,QAAa,EACb,GAAG,EACH,UAAkB,EAClB,KAAK,EACL,MAAM,GACT,EAAE;IACC,GAAG,EAAE,MAAM,CAAC;IACZ,QAAQ,CAAC,EAAE,kBAAkB,EAAE,CAAC;IAChC,GAAG,EAAE,MAAM,CAAC;IACZ,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,KAAK,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;IACxB,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;CAC5B,GACF,sBAAsB,GAAG;IAAE,GAAG,EAAE,MAAM,CAAA;CAAE,CAgB1C;AAED,wBAAgB,yBAAyB,CAAC,EAAC,UAAkB,EAAC,GAAE,cAAmB,GAAG,sBAAsB,CAI3G;AAED,wBAAgB,0BAA0B,CAAC,EAAC,UAAkB,EAAC,GAAE,cAAmB,GAAG,uBAAuB,CAI7G;AAED,wBAAgB,yBAAyB,CAAC,EAAC,UAAkB,EAAC,GAAE,cAAmB,GAAG,sBAAsB,CAE3G"}
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
export function getImageSnippetAttributes({ src, variants = [], alt, isCritical = false, width, height, }) {
|
|
2
|
+
const srcSet = getImageSrcSet(variants);
|
|
3
|
+
const sizes = getImageSizes(width, srcSet);
|
|
4
|
+
const fallbackSrc = variants.length ? variants[variants.length - 1]?.url || src : src;
|
|
5
|
+
return {
|
|
6
|
+
src: fallbackSrc,
|
|
7
|
+
alt,
|
|
8
|
+
...(srcSet ? { srcSet } : {}),
|
|
9
|
+
...(sizes ? { sizes } : {}),
|
|
10
|
+
...(isCritical
|
|
11
|
+
? { fetchPriority: "high", decoding: "sync" }
|
|
12
|
+
: { loading: "lazy", decoding: "async" }),
|
|
13
|
+
...(width ? { width } : {}),
|
|
14
|
+
...(height ? { height } : {}),
|
|
15
|
+
};
|
|
16
|
+
}
|
|
17
|
+
export function getMediaSnippetAttributes({ isCritical = false } = {}) {
|
|
18
|
+
return {
|
|
19
|
+
preload: isCritical ? "auto" : "none",
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
export function getScriptSnippetAttributes({ isCritical = false } = {}) {
|
|
23
|
+
return isCritical
|
|
24
|
+
? { preload: true, defer: true }
|
|
25
|
+
: { defer: true };
|
|
26
|
+
}
|
|
27
|
+
export function getStyleSnippetAttributes({ isCritical = false } = {}) {
|
|
28
|
+
return isCritical ? { preload: true } : {};
|
|
29
|
+
}
|
|
30
|
+
const getImageSrcSet = (variants) => {
|
|
31
|
+
if (!variants.length) {
|
|
32
|
+
return "";
|
|
33
|
+
}
|
|
34
|
+
const uniqueVariants = new Map();
|
|
35
|
+
for (const variant of variants) {
|
|
36
|
+
if (!variant.url || !Number.isFinite(variant.width) || variant.width <= 0) {
|
|
37
|
+
continue;
|
|
38
|
+
}
|
|
39
|
+
uniqueVariants.set(variant.width, variant.url);
|
|
40
|
+
}
|
|
41
|
+
return Array.from(uniqueVariants.entries())
|
|
42
|
+
.sort((a, b) => a[0] - b[0])
|
|
43
|
+
.map(([width, url]) => `${url} ${width}w`)
|
|
44
|
+
.join(", ");
|
|
45
|
+
};
|
|
46
|
+
const getImageSizes = (width, srcSet) => {
|
|
47
|
+
if (!srcSet) {
|
|
48
|
+
return "";
|
|
49
|
+
}
|
|
50
|
+
const numericWidth = Number(width);
|
|
51
|
+
if (Number.isFinite(numericWidth) && numericWidth > 0) {
|
|
52
|
+
return `(max-width: ${numericWidth}px) 100vw, ${numericWidth}px`;
|
|
53
|
+
}
|
|
54
|
+
return "100vw";
|
|
55
|
+
};
|
package/dist/core/index.d.ts
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
export { createLoader } from "./createLoader.js";
|
|
2
2
|
export { getConfig, initConfig, normalizeConfig } from "./config.js";
|
|
3
|
+
export { getImageSnippetAttributes, getMediaSnippetAttributes, getScriptSnippetAttributes, getStyleSnippetAttributes, } from "./html-snippets.js";
|
|
3
4
|
export { buildUrl, normalizePath, resolveDefaultVariantSlug } from "./utils.js";
|
|
5
|
+
export type * from "./html-snippets.js";
|
|
4
6
|
export type * from "./types.js";
|
|
5
7
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/core/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/core/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,YAAY,EAAC,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAC,SAAS,EAAE,UAAU,EAAE,eAAe,EAAC,MAAM,aAAa,CAAC;AACnE,OAAO,EAAC,QAAQ,EAAE,aAAa,EAAE,yBAAyB,EAAC,MAAM,YAAY,CAAC;AAC9E,mBAAmB,YAAY,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/core/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,YAAY,EAAC,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAC,SAAS,EAAE,UAAU,EAAE,eAAe,EAAC,MAAM,aAAa,CAAC;AACnE,OAAO,EACH,yBAAyB,EACzB,yBAAyB,EACzB,0BAA0B,EAC1B,yBAAyB,GAC5B,MAAM,oBAAoB,CAAC;AAC5B,OAAO,EAAC,QAAQ,EAAE,aAAa,EAAE,yBAAyB,EAAC,MAAM,YAAY,CAAC;AAC9E,mBAAmB,oBAAoB,CAAC;AACxC,mBAAmB,YAAY,CAAC"}
|
package/dist/core/index.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
1
|
export { createLoader } from "./createLoader.js";
|
|
2
2
|
export { getConfig, initConfig, normalizeConfig } from "./config.js";
|
|
3
|
+
export { getImageSnippetAttributes, getMediaSnippetAttributes, getScriptSnippetAttributes, getStyleSnippetAttributes, } from "./html-snippets.js";
|
|
3
4
|
export { buildUrl, normalizePath, resolveDefaultVariantSlug } from "./utils.js";
|
package/dist/core/utils.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/core/utils.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAElD,wBAAgB,SAAS,IAAI,OAAO,CAEnC;AAED,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAKlD;AAED,wBAAgB,gBAAgB,CAAC,SAAS,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,MAAM,CAgBhG;AAED,wBAAgB,yBAAyB,IAAI,MAAM,CAKlD;AAED,wBAAgB,QAAQ,CAAC,SAAS,EAAE,MAAM,EAAE,oBAAoB,CAAC,EAAE,MAAM,GAAG,eAAe,GAAG,MAAM,
|
|
1
|
+
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../src/core/utils.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAElD,wBAAgB,SAAS,IAAI,OAAO,CAEnC;AAED,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAKlD;AAED,wBAAgB,gBAAgB,CAAC,SAAS,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,MAAM,CAgBhG;AAED,wBAAgB,yBAAyB,IAAI,MAAM,CAKlD;AAED,wBAAgB,QAAQ,CAAC,SAAS,EAAE,MAAM,EAAE,oBAAoB,CAAC,EAAE,MAAM,GAAG,eAAe,GAAG,MAAM,CA0BnG"}
|
package/dist/core/utils.js
CHANGED
|
@@ -35,12 +35,15 @@ export function buildUrl(assetPath, variantSlugOrOptions) {
|
|
|
35
35
|
const options = typeof variantSlugOrOptions === "string"
|
|
36
36
|
? { variantSlug: variantSlugOrOptions }
|
|
37
37
|
: variantSlugOrOptions || {};
|
|
38
|
-
const
|
|
39
|
-
const
|
|
38
|
+
const defaultVariantSlug = resolveDefaultVariantSlug();
|
|
39
|
+
const variantSlug = options.variantSlug && options.variantSlug !== defaultVariantSlug
|
|
40
|
+
? options.variantSlug
|
|
41
|
+
: undefined;
|
|
42
|
+
const version = normalizeOptionalString(options.version ?? config.version);
|
|
40
43
|
const normalizedAssetPath = normalizePath(applyReplacePath(assetPath, config.replacePath));
|
|
41
44
|
const pathname = config.customSubdomain
|
|
42
|
-
?
|
|
43
|
-
:
|
|
45
|
+
? joinUrlPath(version, normalizedAssetPath)
|
|
46
|
+
: joinUrlPath(config.userSlug, config.projectSlug, version, variantSlug, normalizedAssetPath);
|
|
44
47
|
const url = new URL(pathname, config.cdnUrl || "https://cdn.smoothcdn.com");
|
|
45
48
|
return url.toString();
|
|
46
49
|
}
|
|
@@ -48,3 +51,16 @@ const toLocalAssetPath = (assetPath) => {
|
|
|
48
51
|
const normalizedAssetPath = normalizePath(assetPath);
|
|
49
52
|
return `/${normalizedAssetPath.replace(/^public\//, "")}`;
|
|
50
53
|
};
|
|
54
|
+
const normalizeOptionalString = (value) => {
|
|
55
|
+
if (typeof value !== "string") {
|
|
56
|
+
return value;
|
|
57
|
+
}
|
|
58
|
+
const trimmedValue = value.trim();
|
|
59
|
+
return trimmedValue || undefined;
|
|
60
|
+
};
|
|
61
|
+
const joinUrlPath = (...segments) => {
|
|
62
|
+
return `/${segments
|
|
63
|
+
.filter((segment) => typeof segment === "string" && segment.length > 0)
|
|
64
|
+
.map((segment) => normalizePath(segment))
|
|
65
|
+
.join("/")}`;
|
|
66
|
+
};
|
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
export { createLoader } from "./core/createLoader.js";
|
|
2
2
|
export { initConfig, normalizeConfig } from "./core/config.js";
|
|
3
|
+
export { getImageSnippetAttributes, getMediaSnippetAttributes, getScriptSnippetAttributes, getStyleSnippetAttributes, } from "./core/html-snippets.js";
|
|
3
4
|
export { buildUrl } from "./core/utils.js";
|
|
5
|
+
export type * from "./core/html-snippets.js";
|
|
4
6
|
export type * from "./core/types.js";
|
|
5
7
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAC/D,OAAO,EAAE,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAC3C,mBAAmB,iBAAiB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AACtD,OAAO,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAC/D,OAAO,EACH,yBAAyB,EACzB,yBAAyB,EACzB,0BAA0B,EAC1B,yBAAyB,GAC5B,MAAM,yBAAyB,CAAC;AACjC,OAAO,EAAE,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAC3C,mBAAmB,yBAAyB,CAAC;AAC7C,mBAAmB,iBAAiB,CAAC"}
|
package/dist/index.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
1
|
export { createLoader } from "./core/createLoader.js";
|
|
2
2
|
export { initConfig, normalizeConfig } from "./core/config.js";
|
|
3
|
+
export { getImageSnippetAttributes, getMediaSnippetAttributes, getScriptSnippetAttributes, getStyleSnippetAttributes, } from "./core/html-snippets.js";
|
|
3
4
|
export { buildUrl } from "./core/utils.js";
|
package/dist/next/CDNImage.d.ts
CHANGED
|
@@ -1,8 +1,3 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
export type CDNImageProps<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap> = {
|
|
4
|
-
assetPath: LoaderImagePath<TAssets>;
|
|
5
|
-
variantSlug?: LoaderVariantSlug<TAssets>;
|
|
6
|
-
} & Omit<ImageProps, "src">;
|
|
7
|
-
export declare function CDNImage<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, ...props }: CDNImageProps<TAssets>): import("react/jsx-runtime").JSX.Element;
|
|
1
|
+
export { CDNImage } from "../react/CDNImage.js";
|
|
2
|
+
export type { CDNImageProps } from "../react/CDNImage.js";
|
|
8
3
|
//# sourceMappingURL=CDNImage.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CDNImage.d.ts","sourceRoot":"","sources":["../../src/next/CDNImage.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"CDNImage.d.ts","sourceRoot":"","sources":["../../src/next/CDNImage.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAC,QAAQ,EAAC,MAAM,sBAAsB,CAAC;AAC9C,YAAY,EAAC,aAAa,EAAC,MAAM,sBAAsB,CAAC"}
|
package/dist/next/CDNImage.js
CHANGED
|
@@ -1,6 +1 @@
|
|
|
1
|
-
|
|
2
|
-
import Image from "next/image";
|
|
3
|
-
import { buildUrl } from "../core/utils.js";
|
|
4
|
-
export function CDNImage({ assetPath, variantSlug, ...props }) {
|
|
5
|
-
return _jsx(Image, { src: buildUrl(assetPath, variantSlug), ...props });
|
|
6
|
-
}
|
|
1
|
+
export { CDNImage } from "../react/CDNImage.js";
|
package/dist/next/Script.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import type { LoaderAssetMap, LoaderDefaultAssetMap, LoaderScriptPath, LoaderVariantSlug } from "../core/types.js";
|
|
2
|
-
export declare function Script<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug,
|
|
2
|
+
export declare function Script<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, isCritical, }: {
|
|
3
3
|
assetPath: LoaderScriptPath<TAssets>;
|
|
4
4
|
variantSlug?: LoaderVariantSlug<TAssets>;
|
|
5
|
-
|
|
5
|
+
isCritical?: boolean;
|
|
6
6
|
}): import("react/jsx-runtime").JSX.Element;
|
|
7
7
|
//# sourceMappingURL=Script.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Script.d.ts","sourceRoot":"","sources":["../../src/next/Script.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"Script.d.ts","sourceRoot":"","sources":["../../src/next/Script.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAC,cAAc,EAAE,qBAAqB,EAAE,gBAAgB,EAAE,iBAAiB,EAAC,MAAM,kBAAkB,CAAC;AAEjH,wBAAgB,MAAM,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,EAC9F,EACI,SAAS,EACT,WAAW,EACX,UAAkB,GACrB,EAAE;IACC,SAAS,EAAE,gBAAgB,CAAC,OAAO,CAAC,CAAC;IACrC,WAAW,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC;IACzC,UAAU,CAAC,EAAE,OAAO,CAAC;CACxB,2CAaJ"}
|
package/dist/next/Script.js
CHANGED
|
@@ -1,7 +1,10 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
3
|
import NextScript from "next/script";
|
|
4
|
+
import { getScriptSnippetAttributes } from "../core/html-snippets.js";
|
|
4
5
|
import { buildUrl } from "../core/utils.js";
|
|
5
|
-
export function Script({ assetPath, variantSlug,
|
|
6
|
-
|
|
6
|
+
export function Script({ assetPath, variantSlug, isCritical = false, }) {
|
|
7
|
+
const src = buildUrl(assetPath, variantSlug);
|
|
8
|
+
const snippetAttributes = getScriptSnippetAttributes({ isCritical });
|
|
9
|
+
return (_jsxs(_Fragment, { children: [snippetAttributes.preload ? _jsx("link", { rel: "preload", as: "script", href: src }) : null, _jsx(NextScript, { src: src, strategy: isCritical ? "beforeInteractive" : "afterInteractive" })] }));
|
|
7
10
|
}
|
package/dist/next/Style.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import type { LoaderAssetMap, LoaderDefaultAssetMap, LoaderStylePath, LoaderVariantSlug } from "../core/types.js";
|
|
2
|
-
export declare function Style<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, }: {
|
|
2
|
+
export declare function Style<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, isCritical, }: {
|
|
3
3
|
assetPath: LoaderStylePath<TAssets>;
|
|
4
4
|
variantSlug?: LoaderVariantSlug<TAssets>;
|
|
5
|
+
isCritical?: boolean;
|
|
5
6
|
}): import("react/jsx-runtime").JSX.Element;
|
|
6
7
|
//# sourceMappingURL=Style.d.ts.map
|
package/dist/next/Style.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Style.d.ts","sourceRoot":"","sources":["../../src/next/Style.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"Style.d.ts","sourceRoot":"","sources":["../../src/next/Style.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAC,cAAc,EAAE,qBAAqB,EAAE,eAAe,EAAE,iBAAiB,EAAC,MAAM,kBAAkB,CAAC;AAEhH,wBAAgB,KAAK,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,EAC7F,EACI,SAAS,EACT,WAAW,EACX,UAAkB,GACrB,EAAE;IACC,SAAS,EAAE,eAAe,CAAC,OAAO,CAAC,CAAC;IACpC,WAAW,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC;IACzC,UAAU,CAAC,EAAE,OAAO,CAAC;CACxB,2CAUJ"}
|
package/dist/next/Style.js
CHANGED
|
@@ -1,7 +1,10 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
3
|
import Head from "next/head";
|
|
4
|
+
import { getStyleSnippetAttributes } from "../core/html-snippets.js";
|
|
4
5
|
import { buildUrl } from "../core/utils.js";
|
|
5
|
-
export function Style({ assetPath, variantSlug, }) {
|
|
6
|
-
|
|
6
|
+
export function Style({ assetPath, variantSlug, isCritical = false, }) {
|
|
7
|
+
const href = buildUrl(assetPath, variantSlug);
|
|
8
|
+
const snippetAttributes = getStyleSnippetAttributes({ isCritical });
|
|
9
|
+
return (_jsxs(Head, { children: [snippetAttributes.preload ? _jsx("link", { rel: "preload", as: "style", href: href }) : null, _jsx("link", { rel: "stylesheet", href: href })] }));
|
|
7
10
|
}
|
package/dist/next/index.d.ts
CHANGED
package/dist/next/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/next/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/next/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AACzC,OAAO,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AAChD,OAAO,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AAChD,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AACrC,OAAO,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AAEnC,OAAO,EACH,QAAQ,EACR,QAAQ,EACR,SAAS,EACT,QAAQ,GACX,MAAM,UAAU,CAAC"}
|
package/dist/next/index.js
CHANGED
package/dist/react/CDNAudio.d.ts
CHANGED
|
@@ -8,7 +8,10 @@ export interface CDNMediaSource<TAssetPath extends string, TVariant extends stri
|
|
|
8
8
|
export type CDNAudioProps<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap> = {
|
|
9
9
|
assetPath: LoaderAudioPath<TAssets>;
|
|
10
10
|
variantSlug?: LoaderVariantSlug<TAssets>;
|
|
11
|
+
isCritical?: boolean;
|
|
12
|
+
controls?: boolean;
|
|
13
|
+
loop?: boolean;
|
|
11
14
|
sources?: Array<CDNMediaSource<LoaderAudioPath<TAssets>, LoaderVariantSlug<TAssets>>>;
|
|
12
|
-
} & Omit<React.AudioHTMLAttributes<HTMLAudioElement>, "src">;
|
|
13
|
-
export declare function CDNAudio<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, sources, children, ...props }: CDNAudioProps<TAssets>): import("react/jsx-runtime").JSX.Element;
|
|
15
|
+
} & Omit<React.AudioHTMLAttributes<HTMLAudioElement>, "controls" | "loop" | "preload" | "src">;
|
|
16
|
+
export declare function CDNAudio<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, isCritical, sources, children, ...props }: CDNAudioProps<TAssets>): import("react/jsx-runtime").JSX.Element;
|
|
14
17
|
//# sourceMappingURL=CDNAudio.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CDNAudio.d.ts","sourceRoot":"","sources":["../../src/react/CDNAudio.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;
|
|
1
|
+
{"version":3,"file":"CDNAudio.d.ts","sourceRoot":"","sources":["../../src/react/CDNAudio.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAG1B,OAAO,KAAK,EAAC,cAAc,EAAE,qBAAqB,EAAE,eAAe,EAAE,iBAAiB,EAAC,MAAM,kBAAkB,CAAC;AAEhH,MAAM,WAAW,cAAc,CAAC,UAAU,SAAS,MAAM,EAAE,QAAQ,SAAS,MAAM;IAC9E,SAAS,EAAE,UAAU,CAAC;IACtB,WAAW,CAAC,EAAE,QAAQ,CAAC;IACvB,IAAI,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,MAAM,aAAa,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,IAAI;IACrG,SAAS,EAAE,eAAe,CAAC,OAAO,CAAC,CAAC;IACpC,WAAW,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC;IACzC,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,OAAO,CAAC,EAAE,KAAK,CAAC,cAAc,CAAC,eAAe,CAAC,OAAO,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;CACzF,GAAG,IAAI,CAAC,KAAK,CAAC,mBAAmB,CAAC,gBAAgB,CAAC,EAAE,UAAU,GAAG,MAAM,GAAG,SAAS,GAAG,KAAK,CAAC,CAAC;AAE/F,wBAAgB,QAAQ,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,EAChG,EACI,SAAS,EACT,WAAW,EACX,UAAkB,EAClB,OAAO,EACP,QAAQ,EACR,GAAG,KAAK,EACX,EAAE,aAAa,CAAC,OAAO,CAAC,2CAiB5B"}
|
package/dist/react/CDNAudio.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { getMediaSnippetAttributes } from "../core/html-snippets.js";
|
|
2
3
|
import { buildUrl } from "../core/utils.js";
|
|
3
|
-
export function CDNAudio({ assetPath, variantSlug, sources, children, ...props }) {
|
|
4
|
-
return (_jsxs("audio", { src: sources?.length ? undefined : buildUrl(assetPath, variantSlug), ...props, children: [sources?.map((source) => (_jsx("source", { src: buildUrl(source.assetPath, source.variantSlug), type: source.type }, `${source.assetPath}:${source.variantSlug || ""}:${source.type || ""}`))), children] }));
|
|
4
|
+
export function CDNAudio({ assetPath, variantSlug, isCritical = false, sources, children, ...props }) {
|
|
5
|
+
return (_jsxs("audio", { src: sources?.length ? undefined : buildUrl(assetPath, variantSlug), ...getMediaSnippetAttributes({ isCritical }), ...props, children: [sources?.map((source) => (_jsx("source", { src: buildUrl(source.assetPath, source.variantSlug), type: source.type }, `${source.assetPath}:${source.variantSlug || ""}:${source.type || ""}`))), children] }));
|
|
5
6
|
}
|
package/dist/react/CDNImage.d.ts
CHANGED
|
@@ -4,8 +4,9 @@ export type CDNImageProps<TAssets extends Partial<LoaderAssetMap> | undefined =
|
|
|
4
4
|
assetPath: LoaderImagePath<TAssets>;
|
|
5
5
|
variantSlug?: LoaderVariantSlug<TAssets>;
|
|
6
6
|
alt: string;
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
7
|
+
isCritical?: boolean;
|
|
8
|
+
width?: number | string;
|
|
9
|
+
height?: number | string;
|
|
10
|
+
} & Omit<React.ImgHTMLAttributes<HTMLImageElement>, "alt" | "decoding" | "fetchPriority" | "height" | "loading" | "sizes" | "src" | "srcSet" | "width">;
|
|
11
|
+
export declare function CDNImage<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, alt, isCritical, width, height, ...props }: CDNImageProps<TAssets>): import("react/jsx-runtime").JSX.Element;
|
|
11
12
|
//# sourceMappingURL=CDNImage.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CDNImage.d.ts","sourceRoot":"","sources":["../../src/react/CDNImage.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;
|
|
1
|
+
{"version":3,"file":"CDNImage.d.ts","sourceRoot":"","sources":["../../src/react/CDNImage.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAI1B,OAAO,KAAK,EAAC,cAAc,EAAE,qBAAqB,EAAE,eAAe,EAAE,iBAAiB,EAAC,MAAM,kBAAkB,CAAC;AAEhH,MAAM,MAAM,aAAa,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,IAAI;IACrG,SAAS,EAAE,eAAe,CAAC,OAAO,CAAC,CAAC;IACpC,WAAW,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC;IACzC,GAAG,EAAE,MAAM,CAAC;IACZ,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,KAAK,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;IACxB,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;CAC5B,GAAG,IAAI,CACJ,KAAK,CAAC,iBAAiB,CAAC,gBAAgB,CAAC,EACzC,KAAK,GAAG,UAAU,GAAG,eAAe,GAAG,QAAQ,GAAG,SAAS,GAAG,OAAO,GAAG,KAAK,GAAG,QAAQ,GAAG,OAAO,CACrG,CAAC;AAEF,wBAAgB,QAAQ,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,EAChG,EACI,SAAS,EACT,WAAW,EACX,GAAQ,EACR,UAAkB,EAClB,KAAK,EACL,MAAM,EACN,GAAG,KAAK,EACX,EAAE,aAAa,CAAC,OAAO,CAAC,2CAuB5B"}
|
package/dist/react/CDNImage.js
CHANGED
|
@@ -1,23 +1,28 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { tryGetConfig } from "../core/config.js";
|
|
3
|
+
import { getImageSnippetAttributes } from "../core/html-snippets.js";
|
|
3
4
|
import { buildUrl } from "../core/utils.js";
|
|
4
|
-
|
|
5
|
-
export function CDNImage({ assetPath, variantSlug, alt = '', responsive = false, variants, sizes, ...props }) {
|
|
5
|
+
export function CDNImage({ assetPath, variantSlug, alt = '', isCritical = false, width, height, ...props }) {
|
|
6
6
|
const src = buildUrl(assetPath, variantSlug);
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
7
|
+
const availableVariants = resolveImageVariants().filter((variantWidth) => typeof width === "number" ? variantWidth <= width : true);
|
|
8
|
+
const snippetAttributes = getImageSnippetAttributes({
|
|
9
|
+
src,
|
|
10
|
+
alt,
|
|
11
|
+
isCritical,
|
|
12
|
+
width,
|
|
13
|
+
height,
|
|
14
|
+
variants: availableVariants.map((variantWidth) => ({
|
|
15
|
+
width: variantWidth,
|
|
16
|
+
url: getVariantSrc(src, variantWidth),
|
|
17
|
+
})),
|
|
18
|
+
});
|
|
19
|
+
return (_jsx("img", { ...snippetAttributes, ...props }));
|
|
14
20
|
}
|
|
15
|
-
const resolveImageVariants = (
|
|
16
|
-
if (variants && variants.length > 0) {
|
|
17
|
-
return variants;
|
|
18
|
-
}
|
|
21
|
+
const resolveImageVariants = () => {
|
|
19
22
|
const configVariants = Object.values(tryGetConfig()?.imageVariants || {});
|
|
20
|
-
return configVariants
|
|
23
|
+
return configVariants
|
|
24
|
+
.filter((variantWidth) => Number.isFinite(variantWidth) && variantWidth > 0)
|
|
25
|
+
.sort((a, b) => a - b);
|
|
21
26
|
};
|
|
22
27
|
const getVariantSrc = (src, width) => {
|
|
23
28
|
const extensionIndex = src.lastIndexOf(".");
|
package/dist/react/CDNVideo.d.ts
CHANGED
|
@@ -6,7 +6,10 @@ export type CDNVideoProps<TAssets extends Partial<LoaderAssetMap> | undefined =
|
|
|
6
6
|
variantSlug?: LoaderVariantSlug<TAssets>;
|
|
7
7
|
posterAssetPath?: LoaderImagePath<TAssets>;
|
|
8
8
|
posterVariantSlug?: LoaderVariantSlug<TAssets>;
|
|
9
|
+
isCritical?: boolean;
|
|
10
|
+
controls?: boolean;
|
|
11
|
+
loop?: boolean;
|
|
9
12
|
sources?: Array<CDNMediaSource<LoaderVideoPath<TAssets>, LoaderVariantSlug<TAssets>>>;
|
|
10
|
-
} & Omit<React.VideoHTMLAttributes<HTMLVideoElement>, "
|
|
11
|
-
export declare function CDNVideo<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, posterAssetPath, posterVariantSlug, sources, children, ...props }: CDNVideoProps<TAssets>): import("react/jsx-runtime").JSX.Element;
|
|
13
|
+
} & Omit<React.VideoHTMLAttributes<HTMLVideoElement>, "controls" | "loop" | "poster" | "preload" | "src">;
|
|
14
|
+
export declare function CDNVideo<TAssets extends Partial<LoaderAssetMap> | undefined = LoaderDefaultAssetMap>({ assetPath, variantSlug, posterAssetPath, posterVariantSlug, isCritical, sources, children, ...props }: CDNVideoProps<TAssets>): import("react/jsx-runtime").JSX.Element;
|
|
12
15
|
//# sourceMappingURL=CDNVideo.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CDNVideo.d.ts","sourceRoot":"","sources":["../../src/react/CDNVideo.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;
|
|
1
|
+
{"version":3,"file":"CDNVideo.d.ts","sourceRoot":"","sources":["../../src/react/CDNVideo.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAG1B,OAAO,KAAK,EAAC,cAAc,EAAE,qBAAqB,EAAE,eAAe,EAAE,iBAAiB,EAAE,eAAe,EAAC,MAAM,kBAAkB,CAAC;AACjI,OAAO,KAAK,EAAC,cAAc,EAAC,MAAM,eAAe,CAAC;AAElD,MAAM,MAAM,aAAa,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,IAAI;IACrG,SAAS,EAAE,eAAe,CAAC,OAAO,CAAC,CAAC;IACpC,WAAW,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC;IACzC,eAAe,CAAC,EAAE,eAAe,CAAC,OAAO,CAAC,CAAC;IAC3C,iBAAiB,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC;IAC/C,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,OAAO,CAAC,EAAE,KAAK,CAAC,cAAc,CAAC,eAAe,CAAC,OAAO,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;CACzF,GAAG,IAAI,CAAC,KAAK,CAAC,mBAAmB,CAAC,gBAAgB,CAAC,EAAE,UAAU,GAAG,MAAM,GAAG,QAAQ,GAAG,SAAS,GAAG,KAAK,CAAC,CAAC;AAE1G,wBAAgB,QAAQ,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,EAChG,EACI,SAAS,EACT,WAAW,EACX,eAAe,EACf,iBAAiB,EACjB,UAAkB,EAClB,OAAO,EACP,QAAQ,EACR,GAAG,KAAK,EACX,EAAE,aAAa,CAAC,OAAO,CAAC,2CAkB5B"}
|
package/dist/react/CDNVideo.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { getMediaSnippetAttributes } from "../core/html-snippets.js";
|
|
2
3
|
import { buildUrl } from "../core/utils.js";
|
|
3
|
-
export function CDNVideo({ assetPath, variantSlug, posterAssetPath, posterVariantSlug, sources, children, ...props }) {
|
|
4
|
-
return (_jsxs("video", { src: sources?.length ? undefined : buildUrl(assetPath, variantSlug), poster: posterAssetPath ? buildUrl(posterAssetPath, posterVariantSlug) : undefined, ...props, children: [sources?.map((source) => (_jsx("source", { src: buildUrl(source.assetPath, source.variantSlug), type: source.type }, `${source.assetPath}:${source.variantSlug || ""}:${source.type || ""}`))), children] }));
|
|
4
|
+
export function CDNVideo({ assetPath, variantSlug, posterAssetPath, posterVariantSlug, isCritical = false, sources, children, ...props }) {
|
|
5
|
+
return (_jsxs("video", { src: sources?.length ? undefined : buildUrl(assetPath, variantSlug), poster: posterAssetPath ? buildUrl(posterAssetPath, posterVariantSlug) : undefined, ...getMediaSnippetAttributes({ isCritical }), ...props, children: [sources?.map((source) => (_jsx("source", { src: buildUrl(source.assetPath, source.variantSlug), type: source.type }, `${source.assetPath}:${source.variantSlug || ""}:${source.type || ""}`))), children] }));
|
|
5
6
|
}
|
package/dist/vue/CDNImage.d.ts
CHANGED
|
@@ -4,7 +4,10 @@ export type CDNImageProps<TAssets extends Partial<LoaderAssetMap> | undefined =
|
|
|
4
4
|
assetPath: LoaderImagePath<TAssets>;
|
|
5
5
|
variantSlug?: LoaderVariantSlug<TAssets>;
|
|
6
6
|
alt?: string;
|
|
7
|
-
|
|
7
|
+
isCritical?: boolean;
|
|
8
|
+
width?: number | string;
|
|
9
|
+
height?: number | string;
|
|
10
|
+
} & Omit<ImgHTMLAttributes, "alt" | "decoding" | "fetchpriority" | "height" | "loading" | "sizes" | "src" | "srcset" | "width">;
|
|
8
11
|
export declare const CDNImage: import("vue").DefineComponent<import("vue").ExtractPropTypes<{
|
|
9
12
|
assetPath: {
|
|
10
13
|
type: PropType<string>;
|
|
@@ -18,6 +21,18 @@ export declare const CDNImage: import("vue").DefineComponent<import("vue").Extra
|
|
|
18
21
|
type: StringConstructor;
|
|
19
22
|
default: string;
|
|
20
23
|
};
|
|
24
|
+
isCritical: {
|
|
25
|
+
type: BooleanConstructor;
|
|
26
|
+
default: boolean;
|
|
27
|
+
};
|
|
28
|
+
width: {
|
|
29
|
+
type: PropType<number | string | undefined>;
|
|
30
|
+
required: false;
|
|
31
|
+
};
|
|
32
|
+
height: {
|
|
33
|
+
type: PropType<number | string | undefined>;
|
|
34
|
+
required: false;
|
|
35
|
+
};
|
|
21
36
|
}>, () => import("vue").VNode<import("vue").RendererNode, import("vue").RendererElement, {
|
|
22
37
|
[key: string]: any;
|
|
23
38
|
}>, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {}, string, import("vue").PublicProps, Readonly<import("vue").ExtractPropTypes<{
|
|
@@ -33,7 +48,20 @@ export declare const CDNImage: import("vue").DefineComponent<import("vue").Extra
|
|
|
33
48
|
type: StringConstructor;
|
|
34
49
|
default: string;
|
|
35
50
|
};
|
|
51
|
+
isCritical: {
|
|
52
|
+
type: BooleanConstructor;
|
|
53
|
+
default: boolean;
|
|
54
|
+
};
|
|
55
|
+
width: {
|
|
56
|
+
type: PropType<number | string | undefined>;
|
|
57
|
+
required: false;
|
|
58
|
+
};
|
|
59
|
+
height: {
|
|
60
|
+
type: PropType<number | string | undefined>;
|
|
61
|
+
required: false;
|
|
62
|
+
};
|
|
36
63
|
}>> & Readonly<{}>, {
|
|
37
64
|
alt: string;
|
|
65
|
+
isCritical: boolean;
|
|
38
66
|
}, {}, {}, {}, string, import("vue").ComponentProvideOptions, true, {}, any>;
|
|
39
67
|
//# sourceMappingURL=CDNImage.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CDNImage.d.ts","sourceRoot":"","sources":["../../src/vue/CDNImage.ts"],"names":[],"mappings":"AAAA,OAAO,EAAqB,KAAK,iBAAiB,EAAE,KAAK,QAAQ,EAAC,MAAM,KAAK,CAAC;
|
|
1
|
+
{"version":3,"file":"CDNImage.d.ts","sourceRoot":"","sources":["../../src/vue/CDNImage.ts"],"names":[],"mappings":"AAAA,OAAO,EAAqB,KAAK,iBAAiB,EAAE,KAAK,QAAQ,EAAC,MAAM,KAAK,CAAC;AAI9E,OAAO,KAAK,EAAC,cAAc,EAAE,qBAAqB,EAAE,eAAe,EAAE,iBAAiB,EAAC,MAAM,kBAAkB,CAAC;AAEhH,MAAM,MAAM,aAAa,CAAC,OAAO,SAAS,OAAO,CAAC,cAAc,CAAC,GAAG,SAAS,GAAG,qBAAqB,IAAI;IACrG,SAAS,EAAE,eAAe,CAAC,OAAO,CAAC,CAAC;IACpC,WAAW,CAAC,EAAE,iBAAiB,CAAC,OAAO,CAAC,CAAC;IACzC,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,KAAK,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;IACxB,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,CAAC;CAC5B,GAAG,IAAI,CAAC,iBAAiB,EAAE,KAAK,GAAG,UAAU,GAAG,eAAe,GAAG,QAAQ,GAAG,SAAS,GAAG,OAAO,GAAG,KAAK,GAAG,QAAQ,GAAG,OAAO,CAAC,CAAC;AAEhI,eAAO,MAAM,QAAQ;;cAIO,QAAQ,CAAC,MAAM,CAAC;;;;cAIhB,QAAQ,CAAC,MAAM,GAAG,SAAS,CAAC;;;;;;;;;;;;cAYlB,QAAQ,CAAC,MAAM,GAAG,MAAM,GAAG,SAAS,CAAC;;;;cAIrC,QAAQ,CAAC,MAAM,GAAG,MAAM,GAAG,SAAS,CAAC;;;;;;;cApB/C,QAAQ,CAAC,MAAM,CAAC;;;;cAIhB,QAAQ,CAAC,MAAM,GAAG,SAAS,CAAC;;;;;;;;;;;;cAYlB,QAAQ,CAAC,MAAM,GAAG,MAAM,GAAG,SAAS,CAAC;;;;cAIrC,QAAQ,CAAC,MAAM,GAAG,MAAM,GAAG,SAAS,CAAC;;;;;;4EA4BzE,CAAC"}
|
package/dist/vue/CDNImage.js
CHANGED
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
import { defineComponent, h } from "vue";
|
|
2
|
+
import { tryGetConfig } from "../core/config.js";
|
|
3
|
+
import { getImageSnippetAttributes } from "../core/html-snippets.js";
|
|
2
4
|
import { buildUrl } from "../core/utils.js";
|
|
3
5
|
export const CDNImage = defineComponent({
|
|
4
6
|
name: "SmoothCDNImage",
|
|
@@ -14,13 +16,52 @@ export const CDNImage = defineComponent({
|
|
|
14
16
|
alt: {
|
|
15
17
|
type: String,
|
|
16
18
|
default: ""
|
|
19
|
+
},
|
|
20
|
+
isCritical: {
|
|
21
|
+
type: Boolean,
|
|
22
|
+
default: false
|
|
23
|
+
},
|
|
24
|
+
width: {
|
|
25
|
+
type: [Number, String],
|
|
26
|
+
required: false
|
|
27
|
+
},
|
|
28
|
+
height: {
|
|
29
|
+
type: [Number, String],
|
|
30
|
+
required: false
|
|
17
31
|
}
|
|
18
32
|
},
|
|
19
33
|
setup(props, { attrs }) {
|
|
20
|
-
return () =>
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
34
|
+
return () => {
|
|
35
|
+
const src = buildUrl(props.assetPath, props.variantSlug);
|
|
36
|
+
const availableVariants = resolveImageVariants().filter((variantWidth) => typeof props.width === "number" ? variantWidth <= props.width : true);
|
|
37
|
+
const snippetAttributes = getImageSnippetAttributes({
|
|
38
|
+
src,
|
|
39
|
+
alt: props.alt,
|
|
40
|
+
isCritical: props.isCritical,
|
|
41
|
+
width: props.width,
|
|
42
|
+
height: props.height,
|
|
43
|
+
variants: availableVariants.map((variantWidth) => ({
|
|
44
|
+
width: variantWidth,
|
|
45
|
+
url: getVariantSrc(src, variantWidth),
|
|
46
|
+
})),
|
|
47
|
+
});
|
|
48
|
+
return h("img", {
|
|
49
|
+
...snippetAttributes,
|
|
50
|
+
...attrs,
|
|
51
|
+
});
|
|
52
|
+
};
|
|
25
53
|
}
|
|
26
54
|
});
|
|
55
|
+
const resolveImageVariants = () => {
|
|
56
|
+
const configVariants = Object.values(tryGetConfig()?.imageVariants || {});
|
|
57
|
+
return configVariants
|
|
58
|
+
.filter((variantWidth) => Number.isFinite(variantWidth) && variantWidth > 0)
|
|
59
|
+
.sort((a, b) => a - b);
|
|
60
|
+
};
|
|
61
|
+
const getVariantSrc = (src, width) => {
|
|
62
|
+
const extensionIndex = src.lastIndexOf(".");
|
|
63
|
+
if (extensionIndex === -1) {
|
|
64
|
+
return src;
|
|
65
|
+
}
|
|
66
|
+
return `${src.slice(0, extensionIndex)}_${width}${src.slice(extensionIndex)}`;
|
|
67
|
+
};
|
package/package.json
CHANGED
package/readme.md
CHANGED
|
@@ -12,6 +12,8 @@ It includes:
|
|
|
12
12
|
- Astro, SvelteKit and Remix entrypoints,
|
|
13
13
|
- TypeScript asset typing generated from `.scdn.json`.
|
|
14
14
|
|
|
15
|
+
Image, media, script and style components share the same loading semantics as Smooth CDN HTML snippets. Use `isCritical` for assets needed above the fold; the loader then applies the correct loading attributes. Image responsiveness is driven only by `imageVariants` in `.scdn.json`.
|
|
16
|
+
|
|
15
17
|
## Installation
|
|
16
18
|
|
|
17
19
|
```bash
|
|
@@ -60,7 +62,10 @@ URLs use the standard Smooth CDN path:
|
|
|
60
62
|
|
|
61
63
|
```ts
|
|
62
64
|
buildUrl("/public/logo.svg");
|
|
63
|
-
// https://cdn.smoothcdn.com/<userSlug>/<projectSlug>/<version
|
|
65
|
+
// https://cdn.smoothcdn.com/<userSlug>/<projectSlug>/<version>/public/logo.svg
|
|
66
|
+
|
|
67
|
+
// When version is not configured:
|
|
68
|
+
// https://cdn.smoothcdn.com/<userSlug>/<projectSlug>/public/logo.svg
|
|
64
69
|
```
|
|
65
70
|
|
|
66
71
|
## TypeScript Asset Typing
|
|
@@ -158,18 +163,18 @@ export function DataBlock() {
|
|
|
158
163
|
## Next.js
|
|
159
164
|
|
|
160
165
|
```tsx
|
|
161
|
-
import { Script, Style } from "@smoothcdn/loader/next";
|
|
162
|
-
import { CDNAudio, CDNImage, CDNVideo } from "@smoothcdn/loader/react";
|
|
166
|
+
import { CDNAudio, CDNImage, CDNVideo, Script, Style } from "@smoothcdn/loader/next";
|
|
163
167
|
|
|
164
168
|
export default function Page() {
|
|
165
169
|
return (
|
|
166
170
|
<>
|
|
167
|
-
<Style assetPath="/public/app.css" />
|
|
168
|
-
<Script assetPath="/public/app.js" />
|
|
171
|
+
<Style assetPath="/public/app.css" isCritical />
|
|
172
|
+
<Script assetPath="/public/app.js" isCritical />
|
|
169
173
|
|
|
170
174
|
<CDNImage
|
|
171
175
|
assetPath="/public/logo.svg"
|
|
172
176
|
alt="Smooth CDN"
|
|
177
|
+
isCritical
|
|
173
178
|
width={80}
|
|
174
179
|
height={80}
|
|
175
180
|
/>
|
|
@@ -182,6 +187,7 @@ export default function Page() {
|
|
|
182
187
|
<CDNVideo
|
|
183
188
|
assetPath="/public/demo.mp4"
|
|
184
189
|
posterAssetPath="/public/demo-poster.jpg"
|
|
190
|
+
isCritical
|
|
185
191
|
controls
|
|
186
192
|
width={1280}
|
|
187
193
|
height={720}
|
|
@@ -329,7 +335,9 @@ const loader = createLoader();
|
|
|
329
335
|
loader.image("/public/logo.png", "640");
|
|
330
336
|
```
|
|
331
337
|
|
|
332
|
-
|
|
338
|
+
When `.scdn.json` contains `imageVariants`, image components automatically build `srcSet` from those configured widths. When `imageVariants` is not configured, the same component renders a single CDN `src`.
|
|
339
|
+
|
|
340
|
+
`isCritical` controls loading behavior. Critical images get `fetchpriority="high"` and synchronous decoding. Non-critical images get `loading="lazy"` and async decoding.
|
|
333
341
|
|
|
334
342
|
```tsx
|
|
335
343
|
import { CDNImage } from "@smoothcdn/loader/react";
|
|
@@ -337,12 +345,11 @@ import { CDNImage } from "@smoothcdn/loader/react";
|
|
|
337
345
|
export function HeroImage() {
|
|
338
346
|
return (
|
|
339
347
|
<CDNImage
|
|
340
|
-
responsive
|
|
341
348
|
assetPath="/public/hero.png"
|
|
342
349
|
alt="Hero"
|
|
350
|
+
isCritical
|
|
343
351
|
width={1536}
|
|
344
352
|
height={1024}
|
|
345
|
-
sizes="(min-width: 1024px) 50vw, 100vw"
|
|
346
353
|
/>
|
|
347
354
|
);
|
|
348
355
|
}
|