affaan-m/ECC · error
Nasiko manifest layer is not a qualified gzip artifact.
Error message
Nasiko manifest layer is not a qualified gzip artifact.
What it means
validateManifest in scripts/lib/nasiko-release.js validates the single layer entry after the structure check: mediaType must be exactly 'application/gzip' and digest must match the sha256:<64 lowercase hex> pattern. Other media types (uncompressed layers, zstd-compressed layers, foreign layers) or malformed digests are rejected because extraction only supports the qualified gzip artifact format.
Source
Thrown at scripts/lib/nasiko-release.js:68
function digestBytes(bytes) {
return `sha256:${crypto.createHash('sha256').update(bytes).digest('hex')}`;
}
function assertDigest(bytes, expectedDigest, label) {
if (!SHA256_PATTERN.test(expectedDigest)) throw new Error(`${label} has an invalid expected digest.`);
const actual = digestBytes(bytes);
if (actual !== expectedDigest) throw new Error(`${label} digest mismatch: expected ${expectedDigest}, got ${actual}.`);
}
function validateManifest(bytes) {
let manifest;
try { manifest = JSON.parse(bytes.toString('utf8')); } catch (_error) { throw new Error('Nasiko manifest is not valid JSON.'); }
if (manifest.schemaVersion !== 2 || !Array.isArray(manifest.layers) || manifest.layers.length !== 1) {
throw new Error('Nasiko manifest must contain exactly one OCI layer.');
}
const layer = manifest.layers[0];
if (layer.mediaType !== 'application/gzip' || !SHA256_PATTERN.test(layer.digest)) {
throw new Error('Nasiko manifest layer is not a qualified gzip artifact.');
}
if (!Number.isSafeInteger(layer.size) || layer.size <= 0 || layer.size > MAX_ARCHIVE_BYTES) {
throw new Error('Nasiko manifest layer size is outside the allowed range.');
}
return { digest: layer.digest, size: layer.size };
}
function readTarString(block, offset, length) {
return block.subarray(offset, offset + length).toString('utf8').replace(/\0.*$/, '');
}
function extractQualifiedTarGzip(archiveBytes, expectedName) {
let tar;
try { tar = zlib.gunzipSync(archiveBytes, { maxOutputLength: MAX_BINARY_BYTES + 2048 }); }
catch (_error) { throw new Error('Nasiko archive is invalid or exceeds the decompressed size limit.'); }
let offset = 0;
let binary = null;
while (offset + 512 <= tar.length) {View on GitHub (pinned to 06c5e118c4)
Solutions
- Re-publish the release with a single application/gzip layer, or extend validation/extraction support if a new format is intentionally adopted
- Fix malformed digests in the manifest so they are full lowercase sha256:<64 hex> values
- Update the ECC checkout if upstream intentionally changed the qualified artifact format
Defensive patterns
Strategy: try-catch
Try / catch
try {
await installNasiko({ version: 'v0.1.0' });
} catch (error) {
if (/not a qualified gzip artifact/.test(String(error.message))) {
// The layer mediaType/digest shape changed upstream. Fix the publishing
// pipeline to emit application/gzip with a sha256:64hex digest.
}
throw error;
} Prevention
- Freeze the layer mediaType ('application/gzip') in the release pipeline
- Add a post-publish assertion that layer.digest matches /^sha256:[a-f0-9]{64}$/
- Avoid recompression steps (gzip -> zstd) without updating the installer
When it happens
Trigger: manifest.layers[0].mediaType is anything other than 'application/gzip' (for example 'application/vnd.docker.image.rootfs.diff.tar' or the zstd variant), or layer.digest fails /^sha256:[a-f0-9]{64}$/ (wrong algorithm prefix, uppercase hex, wrong length, missing prefix).
Common situations: Upstream recompressed layers with zstd to save bandwidth; a hand-crafted or modified manifest with a truncated digest string; mirrors that normalize or rewrite media types.
Related errors
- Nasiko manifest is not valid JSON.
- Nasiko manifest must contain exactly one OCI layer.
- Nasiko manifest layer size is outside the allowed range.
- Install module ${moduleId} has invalid targets; expected an
- Install module ${moduleId} has unsupported targets: ${unsupp
AI-assisted analysis of affaan-m/ECC@06c5e118c4 (2026-08-18).
Data as JSON: /api/errors/cd6816bf4b503df7.
Report an issue: GitHub.