Parcel packager plugin for handling raw URL references without transformation
npx @tessl/cli install tessl/npm-parcel--packager-raw-url@2.15.0The @parcel/packager-raw-url package is a specialized Parcel packager plugin that handles raw URL assets by preserving their original URL references without applying any transformations. It ensures raw bundles maintain their absolute URL paths and contain exactly one asset per bundle.
npm install @parcel/packager-raw-urlimport RawUrlPackager from "@parcel/packager-raw-url";For CommonJS:
const RawUrlPackager = require("@parcel/packager-raw-url");For Flow type annotations:
import type {Packager} from "@parcel/plugin";
import {Packager} from "@parcel/plugin";
import {replaceURLReferences} from "@parcel/utils";This package is typically used through Parcel's plugin system rather than directly in application code. Parcel automatically uses this packager for raw URL asset types.
// Parcel configuration (.parcelrc)
{
"extends": "@parcel/config-default",
"packagers": {
"raw-url:*": "@parcel/packager-raw-url"
}
}The raw URL packager is built as a Parcel plugin that integrates with Parcel's bundling pipeline:
Packager base class from @parcel/plugin@parcel/utils URL replacement utilities to maintain absolute URLsThe default export is a Packager plugin instance configured specifically for raw URL asset handling.
/**
* Default export: Packager plugin instance for raw URL assets
* Automatically configured with package method for processing raw URL bundles
*/
declare const RawUrlPackager: Packager;
/**
* Package method configuration within the Packager instance
* @param bundle - Bundle object containing assets to process
* @param bundleGraph - Complete bundle graph for URL resolution
* @returns Promise resolving to object with processed contents
*/
interface PackageMethodParams {
bundle: Bundle;
bundleGraph: BundleGraph;
}
interface PackageMethodReturn {
contents: string;
}
/**
* Internal package method (not directly callable)
* Processes raw URL bundles by preserving original URLs
*/
function package(params: PackageMethodParams): Promise<PackageMethodReturn>;
/**
* Utility function from @parcel/utils used for URL replacement
* Replaces URL references in asset contents with bundle URLs
*/
function replaceURLReferences({
bundle,
bundleGraph,
contents,
relative = true,
map,
getReplacement = s => s,
}: {|
bundle: Bundle,
bundleGraph: BundleGraph<Bundle>,
contents: string,
relative?: boolean,
map?: ?SourceMap,
getReplacement?: string => string,
|}): {|+contents: string, +map: ?SourceMap|};/**
* Bundle object representing a collection of assets
* Provided by Parcel's bundling system
*/
interface Bundle {
/** The bundle id */
+id: string;
/** The type of the bundle */
+type: string;
/** The environment of the bundle */
+env: Environment;
/** The bundle's target */
+target: Target;
/** Indicates that the bundle's file name should be stable over time */
+needsStableName: ?boolean;
/** Controls the behavior of the bundle (inline, isolated) */
+bundleBehavior: ?BundleBehavior;
/** Whether the bundle can be split */
+isSplittable: ?boolean;
/** A placeholder for the bundle's content hash */
+hashReference: string;
/** Returns the assets that are executed immediately when the bundle is loaded */
getEntryAssets(): Array<Asset>;
/** Returns the main entry of the bundle, which will provide the bundle's exports */
getMainEntry(): ?Asset;
/** Returns whether the bundle includes the given asset */
hasAsset(asset: Asset): boolean;
/** Returns whether the bundle includes the given dependency */
hasDependency(dependency: Dependency): boolean;
/** Traverses the assets in the bundle */
traverseAssets<TContext>(
visit: GraphVisitor<Asset, TContext>,
startAsset?: Asset,
): ?TContext;
/** Traverses assets and dependencies in the bundle */
traverse<TContext>(
visit: GraphVisitor<BundleTraversable, TContext>,
): ?TContext;
/** Returns a hash of the contents of the bundle */
getContentHash(): string;
}
/**
* Asset object representing a single bundled asset
* Provided by Parcel's asset system
*/
interface Asset {
/** The id of the asset */
+id: string;
/** The file system where the source is located */
+fs: FileSystem;
/** The file path of the asset */
+filePath: FilePath;
/** The asset's type. This initially corresponds to the source file extension */
+type: string;
/** The transformer options for the asset from the dependency query string */
+query: URLSearchParams;
/** The environment of the asset */
+env: Environment;
/** Whether this asset is part of the project, and not an external dependency */
+isSource: boolean;
/** Plugin-specific metadata for the asset */
+meta: Meta;
/** Controls which bundle the asset is placed into (inline, isolated) */
+bundleBehavior: ?BundleBehavior;
/** If the asset is used as a bundle entry, controls whether that bundle can be split */
+isBundleSplittable: boolean;
/** Whether this asset can be omitted if none of its exports are being used */
+sideEffects: boolean;
/** Unique key to identify assets when a transformer returns multiple assets */
+uniqueKey: ?string;
/** The type of the AST */
+astGenerator: ?ASTGenerator;
/** The pipeline defined in .parcelrc that the asset should be processed with */
+pipeline: ?string;
/** The symbols that the asset exports */
+symbols: AssetSymbols;
/** Statistics about the asset */
+stats: Stats;
/** Returns the current AST */
getAST(): Promise<?AST>;
/** Returns the asset contents as a string */
getCode(): Promise<string>;
/** Returns the asset contents as a buffer */
getBuffer(): Promise<Buffer>;
/** Returns the asset contents as a stream */
getStream(): Readable;
/** Returns the source map for the asset, if available */
getMap(): Promise<?SourceMap>;
/** Returns a buffer representation of the source map, if available */
getMapBuffer(): Promise<?Buffer>;
/** Returns a list of dependencies for the asset */
getDependencies(): $ReadOnlyArray<Dependency>;
}
/**
* BundleGraph object representing the complete bundle graph
* Used for URL resolution and bundle relationships
*/
interface BundleGraph<TBundle: Bundle> {
/** Retrieves an asset by id */
getAssetById(id: string): Asset;
/** Returns the public (short) id for an asset */
getAssetPublicId(asset: Asset): string;
/** Returns a list of bundles in the bundle graph. By default, inline bundles are excluded */
getBundles(opts?: {|includeInline: boolean|}): Array<TBundle>;
/** Traverses the assets and dependencies in the bundle graph, in depth first order */
traverse<TContext>(
visit: GraphVisitor<BundleGraphTraversable, TContext>,
startAsset: ?Asset,
options?: {|skipUnusedDependencies?: boolean|},
): ?TContext;
/** Traverses all bundles in the bundle graph, including inline bundles, in depth first order */
traverseBundles<TContext>(
visit: GraphVisitor<TBundle, TContext>,
startBundle: ?Bundle,
): ?TContext;
/** Returns a list of bundle groups that load the given bundle */
getBundleGroupsContainingBundle(bundle: Bundle): Array<BundleGroup>;
/** Returns a list of bundles that load together in the given bundle group */
getBundlesInBundleGroup(
bundleGroup: BundleGroup,
opts?: {|
recursive?: boolean,
includeInline?: boolean,
includeIsolated?: boolean,
|},
): Array<TBundle>;
/** Returns a list of bundles that this bundle loads asynchronously */
getChildBundles(bundle: Bundle): Array<TBundle>;
/** Returns a list of bundles that load this bundle asynchronously */
getParentBundles(bundle: Bundle): Array<TBundle>;
/** Returns whether the bundle was loaded by another bundle of the given type */
hasParentBundleOfType(bundle: Bundle, type: string): boolean;
/** Returns a list of bundles that are referenced by this bundle */
getReferencedBundles(
bundle: Bundle,
opts?: {|
recursive?: boolean,
includeInline?: boolean,
includeIsolated?: boolean,
|},
): Array<TBundle>;
/** Returns a list of bundles that reference this bundle */
getReferencingBundles(bundle: Bundle): Array<TBundle>;
/** Get the dependencies that the asset requires */
getDependencies(asset: Asset): Array<Dependency>;
/** Get the dependencies that require the asset */
getIncomingDependencies(asset: Asset): Array<Dependency>;
/** Get the asset that created the dependency */
getAssetWithDependency(dep: Dependency): ?Asset;
/** Returns whether the given bundle group is an entry */
isEntryBundleGroup(bundleGroup: BundleGroup): boolean;
/** Returns whether a dependency was excluded because it had no used symbols */
isDependencySkipped(dependency: Dependency): boolean;
/** Returns the asset that the dependency resolved to */
getResolvedAsset(dependency: Dependency, bundle: ?Bundle): ?Asset;
/** Returns the bundle that a dependency in a given bundle references, if any */
getReferencedBundle(dependency: Dependency, bundle: Bundle): ?TBundle;
/** Returns a list of bundles that contain the given asset */
getBundlesWithAsset(asset: Asset): Array<TBundle>;
/** Returns a list of bundles that contain the given dependency */
getBundlesWithDependency(dependency: Dependency): Array<TBundle>;
/** Returns whether the given asset is reachable in a sibling or all possible ancestries of the given bundle */
isAssetReachableFromBundle(asset: Asset, bundle: Bundle): boolean;
/** Returns whether an asset is referenced outside the given bundle */
isAssetReferenced(bundle: Bundle, asset: Asset): boolean;
/** Returns a list of entry bundles */
getEntryBundles(): Array<TBundle>;
}
/**
* Packager base class from @parcel/plugin
* Base class for all Parcel packager plugins
*/
interface Packager {
// Packager implementation details handled by Parcel
}
// Supporting types used throughout the API
type Async<T> = T | Promise<T>;
type FilePath = string;
type Meta = {[string]: mixed};
type BundleBehavior = "inline" | "isolated";
interface Environment {
context: "node" | "browser" | "web-worker" | "service-worker" | "electron-main" | "electron-renderer";
engines: {[string]: string};
includeNodeModules: boolean | Array<string> | {[string]: boolean};
outputFormat: "global" | "esmodule" | "commonjs";
isLibrary: boolean;
shouldOptimize: boolean;
shouldScopeHoist: boolean;
sourceMap?: SourceMapOptions;
}
interface Target {
name: string;
distDir: FilePath;
distEntry?: ?FilePath;
publicUrl: string;
env: Environment;
sourceMap?: ?SourceMapOptions;
}
interface Dependency {
id: string;
specifier: string;
specifierType: DependencySpecifierType;
priority: DependencyPriority;
needsStableName: boolean;
bundleBehavior: ?BundleBehavior;
isEntry: boolean;
isOptional: boolean;
loc: ?SourceLocation;
env: Environment;
meta: Meta;
target: ?Target;
sourceAssetId: ?string;
sourcePath: ?FilePath;
resolveFrom: ?FilePath;
range: ?SemverRange;
symbols: ?Map<Symbol, {|local: Symbol, loc: ?SourceLocation, isWeak: boolean, meta?: ?Meta|}>;
pipeline: ?string;
}
interface BundleGroup {
target: Target;
entryAssetId: string;
}
interface Stats {
time: number;
size: number;
}
interface SourceMap {
// Source map structure
}
interface FileSystem {
// File system interface
}
interface AssetSymbols {
// Asset symbols structure
}
interface ASTGenerator {
// AST generator interface
}
interface AST {
// Abstract syntax tree structure
}
interface Buffer {
// Node.js Buffer interface
}
interface Readable {
// Node.js Readable stream interface
}
type GraphVisitor<TNode, TContext> = (
node: TNode,
context: ?TContext,
actions: TraversalActions,
) => ?TContext;
interface TraversalActions {
skipChildren(): void;
stop(): void;
}
type BundleTraversable = Asset | Dependency;
type BundleGraphTraversable = Asset | Dependency;
type DependencySpecifierType = "esm" | "commonjs" | "url" | "custom";
type DependencyPriority = "sync" | "parallel" | "lazy";
type Symbol = string;
type SourceLocation = {|
filePath: FilePath,
start: {|line: number, column: number|},
end: {|line: number, column: number|},
|};
type SemverRange = string;
type SourceMapOptions = {|
inline?: boolean,
inlineSources?: boolean,
sourceRoot?: string,
|};The packager enforces that raw URL bundles contain exactly one asset:
assert.equal for validationURL references are processed using Parcel's utility functions:
replaceURLReferences from @parcel/utilsrelative: false to maintain absolute URL pathss => s for URL replacement (no transformation)AssertionError when bundle doesn't contain exactly one asset