New Case Study:See how Anthropic automated 95% of dependency reviews with Socket.Learn More
Socket
Sign inDemoInstall
Socket

@eris/exif

Package Overview
Dependencies
Maintainers
1
Versions
109
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@eris/exif - npm Package Compare versions

Comparing version 0.3.1-alpha.1 to 0.3.1-alpha.2

8

dist/encoder/xmp-encoder.d.ts

@@ -7,6 +7,6 @@ import { IGenericMetadata, IBufferLike } from '../utils/types';

static encode(metadata: IGenericMetadata, original?: IBufferLike): IBufferLike;
private static _findExistingTag;
private static _handleKeywords;
private static _generateKeywordsPayload;
private static _findIndexOfRdfDescriptionEnd;
private static _processEntry;
private static _findExisting;
private static _findInsertionPoint;
private static _buildReplacement;
}

@@ -54,47 +54,9 @@ "use strict";

const tagName = key;
log(`examining ${tagName}`);
if (!(tagName in tags_1.xmpTags))
if (!(tagName in tags_1.xmpTags)) {
log(`skipping ${tagName} which is not an XMP tag`);
continue;
const value = metadata[tagName];
if (tagName === 'DCSubjectBagOfWords') {
const result = XMPEncoder._handleKeywords(xmpData, metadata);
xmpData = result.xmpData;
extraLength += result.extraLength;
continue;
}
if (typeof value === 'undefined') {
log(`unsetting ${tagName}`);
const existing = XMPEncoder._findExistingTag(xmpData, tagName);
if (!existing)
continue;
let preamble = xmpData.slice(0, existing.start);
const postamble = xmpData.slice(existing.start + existing.length);
if (postamble.startsWith('\n'))
preamble = preamble.replace(/\n +$/, '');
const beforeLength = xmpData.length;
xmpData = `${preamble}${postamble}`;
const afterLength = xmpData.length;
extraLength += afterLength - beforeLength;
continue;
}
log(`writing ${tagName} as "${value}"`);
const existing = XMPEncoder._findExistingTag(xmpData, tagName);
const replacement = `xmp:${tagName}="${value}"`;
if (existing) {
log(`found existing ${tagName} - ${existing.value}`);
const preamble = xmpData.slice(0, existing.start);
const postamble = xmpData.slice(existing.start + existing.length);
const additionalLength = replacement.length - existing.length;
xmpData = `${preamble}${replacement}${postamble}`;
extraLength += additionalLength;
}
else {
log(`did not find existing ${tagName}`);
const rdfEnd = XMPEncoder._findIndexOfRdfDescriptionEnd(xmpData);
const preamble = xmpData.slice(0, rdfEnd);
const postamble = xmpData.slice(rdfEnd);
const replacementWithNewline = `${BASE_NEWLINE}${replacement}`;
xmpData = `${preamble}${replacementWithNewline}${postamble}`;
extraLength += replacementWithNewline.length;
}
const newXmpData = XMPEncoder._processEntry(xmpData, tagName, metadata[tagName]);
extraLength += newXmpData.length - xmpData.length;
xmpData = newXmpData;
}

@@ -120,51 +82,64 @@ if (XMPEncoder.isWrappedInPacket(xmpData)) {

}
static _findExistingTag(xmp, tagName) {
const regex = new RegExp(`([a-z]+):(${tagName})="(.*?)"`, 'i');
const match = xmp.match(regex);
if (!match)
return undefined;
const [fullMatch, prefix, name, value] = match;
const start = xmp.indexOf(fullMatch);
return { start, length: fullMatch.length, prefix, name, value };
}
static _handleKeywords(xmpData, metadata) {
const newKeywords = keywords_parser_1.parseKeywords(metadata);
const existingKeywordsMatch = xmpData.match(/<dc:subject>(.|\s)*?<\/dc:subject>/);
if (!newKeywords || !newKeywords.length) {
// Nothing to remove, move on
if (!existingKeywordsMatch)
return { xmpData, extraLength: 0 };
// Remove the payload
const indexOfMatch = existingKeywordsMatch.index;
const original = existingKeywordsMatch[0];
const preamble = xmpData.slice(0, indexOfMatch);
const postamble = xmpData.slice(indexOfMatch + original.length);
return {
xmpData: `${preamble}${postamble}`,
extraLength: -original.length,
};
static _processEntry(xmpData, tagName, value) {
log(`processing ${tagName}`);
const existing = XMPEncoder._findExisting(xmpData, tagName);
// If we are unsetting, branch.
if (typeof value === 'undefined') {
if (!existing) {
// If we didn't have an existing value to begin with, we're done.
log(`${tagName} already missing from XMP, skipping`);
return xmpData;
}
log(`unsetting ${tagName}`);
// Remove the existing reference and cleanup whitespace
let preamble = xmpData.slice(0, existing.start);
const postamble = xmpData.slice(existing.start + existing.length);
if (postamble.match(/^(\n|>)/))
preamble = preamble.replace(/\n +$/, '');
return `${preamble}${postamble}`;
}
const replacement = XMPEncoder._generateKeywordsPayload(newKeywords);
if (existingKeywordsMatch) {
const indexOfMatch = existingKeywordsMatch.index;
const original = existingKeywordsMatch[0];
const preamble = xmpData.slice(0, indexOfMatch);
const postamble = xmpData.slice(indexOfMatch + original.length);
return {
xmpData: `${preamble}${replacement}${postamble}`,
extraLength: replacement.length - original.length,
};
log(`writing ${tagName} with value "${value}"`);
const replacement = XMPEncoder._buildReplacement(tagName, value);
if (existing) {
// If we have an existing value, replace the token range with our new payload
log(`found existing ${tagName}`);
const preamble = xmpData.slice(0, existing.start);
const postamble = xmpData.slice(existing.start + existing.length);
return `${preamble}${replacement}${postamble}`;
}
else {
const rdfEnd = XMPEncoder._findIndexOfRdfDescriptionEnd(xmpData) + 1;
const preamble = xmpData.slice(0, rdfEnd);
const postamble = xmpData.slice(rdfEnd);
// If we don't have an existing value, inject the payload with appropriate whitespace.
log(`did not find existing ${tagName}`);
const insertionIndex = XMPEncoder._findInsertionPoint(xmpData, tagName).start;
const preamble = xmpData.slice(0, insertionIndex);
const postamble = xmpData.slice(insertionIndex);
const replacementWithNewline = `${BASE_NEWLINE}${replacement}`;
return {
xmpData: `${preamble}${replacementWithNewline}${postamble}`,
extraLength: replacementWithNewline.length,
};
return `${preamble}${replacementWithNewline}${postamble}`;
}
}
static _generateKeywordsPayload(keywords) {
static _findExisting(xmp, tagName) {
const regex = tagName === 'DCSubjectBagOfWords'
? /<dc:subject>(.|\s)*?<\/dc:subject>/
: new RegExp(`([a-z]+):(${tagName})="(.*?)"`, 'i');
const match = xmp.match(regex);
if (!match)
return;
return { start: match.index, length: match[0].length };
}
static _findInsertionPoint(xmp, tagName) {
const regex = /<rdf:Description[^<]*?>/im;
const match = xmp.match(regex);
if (!match)
throw new Error('Unable to find end of rdf:description');
const rdfDescription = match[0];
const rdfDescriptionEndIndex = xmp.indexOf(rdfDescription) + rdfDescription.length - 1;
const start = rdfDescriptionEndIndex + (tagName === 'DCSubjectBagOfWords' ? 1 : 0);
return { start };
}
static _buildReplacement(tagName, value) {
if (tagName !== 'DCSubjectBagOfWords')
return `xmp:${tagName}="${value}"`;
const keywords = keywords_parser_1.parseKeywords({ DCSubjectBagOfWords: value });
if (!keywords)
throw new Error('Invalid keywords payload');
return [

@@ -178,12 +153,4 @@ `<dc:subject>`,

}
static _findIndexOfRdfDescriptionEnd(xmp) {
const regex = /<rdf:Description(\s*(\w+:\w+=".*?")\s*)*?>/im;
const match = xmp.match(regex);
if (!match)
throw new Error('Unable to find end of rdf:description');
const rdfDescription = match[0];
return xmp.indexOf(rdfDescription) + rdfDescription.length - 1;
}
}
exports.XMPEncoder = XMPEncoder;
//# sourceMappingURL=xmp-encoder.js.map

@@ -30,10 +30,2 @@ import {IGenericMetadata, IBufferLike} from '../utils/types'

interface TagLocation {
start: number
length: number
prefix: string
name: string
value: string
}
export class XMPEncoder {

@@ -73,49 +65,11 @@ public static isWrappedInPacket(xmpData: IBufferLike | string): boolean {

const tagName = key as keyof IGenericMetadata
log(`examining ${tagName}`)
if (!(tagName in xmpTags)) continue
const value = metadata[tagName]
if (tagName === 'DCSubjectBagOfWords') {
const result = XMPEncoder._handleKeywords(xmpData, metadata)
xmpData = result.xmpData
extraLength += result.extraLength
if (!(tagName in xmpTags)) {
log(`skipping ${tagName} which is not an XMP tag`)
continue
}
if (typeof value === 'undefined') {
log(`unsetting ${tagName}`)
const existing = XMPEncoder._findExistingTag(xmpData, tagName)
if (!existing) continue
let preamble = xmpData.slice(0, existing.start)
const postamble = xmpData.slice(existing.start + existing.length)
if (postamble.startsWith('\n')) preamble = preamble.replace(/\n +$/, '')
const beforeLength = xmpData.length
xmpData = `${preamble}${postamble}`
const afterLength = xmpData.length
extraLength += afterLength - beforeLength
continue
}
log(`writing ${tagName} as "${value}"`)
const existing = XMPEncoder._findExistingTag(xmpData, tagName)
const replacement = `xmp:${tagName}="${value}"`
if (existing) {
log(`found existing ${tagName} - ${existing.value}`)
const preamble = xmpData.slice(0, existing.start)
const postamble = xmpData.slice(existing.start + existing.length)
const additionalLength = replacement.length - existing.length
xmpData = `${preamble}${replacement}${postamble}`
extraLength += additionalLength
} else {
log(`did not find existing ${tagName}`)
const rdfEnd = XMPEncoder._findIndexOfRdfDescriptionEnd(xmpData)
const preamble = xmpData.slice(0, rdfEnd)
const postamble = xmpData.slice(rdfEnd)
const replacementWithNewline = `${BASE_NEWLINE}${replacement}`
xmpData = `${preamble}${replacementWithNewline}${postamble}`
extraLength += replacementWithNewline.length
}
const newXmpData = XMPEncoder._processEntry(xmpData, tagName, metadata[tagName])
extraLength += newXmpData.length - xmpData.length
xmpData = newXmpData
}

@@ -144,55 +98,81 @@

private static _findExistingTag(xmp: string, tagName: string): TagLocation | undefined {
const regex = new RegExp(`([a-z]+):(${tagName})="(.*?)"`, 'i')
const match = xmp.match(regex)
if (!match) return undefined
const [fullMatch, prefix, name, value] = match
const start = xmp.indexOf(fullMatch)
return {start, length: fullMatch.length, prefix, name, value}
}
private static _processEntry(
xmpData: string,
tagName: keyof IGenericMetadata,
value: string | number | undefined,
): string {
log(`processing ${tagName}`)
const existing = XMPEncoder._findExisting(xmpData, tagName)
private static _handleKeywords(
xmpData: string,
metadata: IGenericMetadata,
): {xmpData: string; extraLength: number} {
const newKeywords = parseKeywords(metadata)
const existingKeywordsMatch = xmpData.match(/<dc:subject>(.|\s)*?<\/dc:subject>/)
if (!newKeywords || !newKeywords.length) {
// Nothing to remove, move on
if (!existingKeywordsMatch) return {xmpData, extraLength: 0}
// Remove the payload
const indexOfMatch = existingKeywordsMatch.index!
const original = existingKeywordsMatch[0]
const preamble = xmpData.slice(0, indexOfMatch)
const postamble = xmpData.slice(indexOfMatch + original.length)
return {
xmpData: `${preamble}${postamble}`,
extraLength: -original.length,
// If we are unsetting, branch.
if (typeof value === 'undefined') {
if (!existing) {
// If we didn't have an existing value to begin with, we're done.
log(`${tagName} already missing from XMP, skipping`)
return xmpData
}
log(`unsetting ${tagName}`)
// Remove the existing reference and cleanup whitespace
let preamble = xmpData.slice(0, existing.start)
const postamble = xmpData.slice(existing.start + existing.length)
if (postamble.match(/^(\n|>)/)) preamble = preamble.replace(/\n +$/, '')
return `${preamble}${postamble}`
}
const replacement = XMPEncoder._generateKeywordsPayload(newKeywords)
if (existingKeywordsMatch) {
const indexOfMatch = existingKeywordsMatch.index!
const original = existingKeywordsMatch[0]
const preamble = xmpData.slice(0, indexOfMatch)
const postamble = xmpData.slice(indexOfMatch + original.length)
return {
xmpData: `${preamble}${replacement}${postamble}`,
extraLength: replacement.length - original.length,
}
log(`writing ${tagName} with value "${value}"`)
const replacement = XMPEncoder._buildReplacement(tagName, value)
if (existing) {
// If we have an existing value, replace the token range with our new payload
log(`found existing ${tagName}`)
const preamble = xmpData.slice(0, existing.start)
const postamble = xmpData.slice(existing.start + existing.length)
return `${preamble}${replacement}${postamble}`
} else {
const rdfEnd = XMPEncoder._findIndexOfRdfDescriptionEnd(xmpData) + 1
const preamble = xmpData.slice(0, rdfEnd)
const postamble = xmpData.slice(rdfEnd)
// If we don't have an existing value, inject the payload with appropriate whitespace.
log(`did not find existing ${tagName}`)
const insertionIndex = XMPEncoder._findInsertionPoint(xmpData, tagName).start
const preamble = xmpData.slice(0, insertionIndex)
const postamble = xmpData.slice(insertionIndex)
const replacementWithNewline = `${BASE_NEWLINE}${replacement}`
return {
xmpData: `${preamble}${replacementWithNewline}${postamble}`,
extraLength: replacementWithNewline.length,
}
return `${preamble}${replacementWithNewline}${postamble}`
}
}
private static _generateKeywordsPayload(keywords: string[]): string {
private static _findExisting(
xmp: string,
tagName: string,
): {start: number; length: number} | undefined {
const regex =
tagName === 'DCSubjectBagOfWords'
? /<dc:subject>(.|\s)*?<\/dc:subject>/
: new RegExp(`([a-z]+):(${tagName})="(.*?)"`, 'i')
const match = xmp.match(regex)
if (!match) return
return {start: match.index!, length: match[0].length}
}
private static _findInsertionPoint(
xmp: string,
tagName: keyof IGenericMetadata,
): {start: number} {
const regex = /<rdf:Description[^<]*?>/im
const match = xmp.match(regex)
if (!match) throw new Error('Unable to find end of rdf:description')
const rdfDescription = match[0]
const rdfDescriptionEndIndex = xmp.indexOf(rdfDescription) + rdfDescription.length - 1
const start = rdfDescriptionEndIndex + (tagName === 'DCSubjectBagOfWords' ? 1 : 0)
return {start}
}
private static _buildReplacement(
tagName: keyof IGenericMetadata,
value: string | number,
): string {
if (tagName !== 'DCSubjectBagOfWords') return `xmp:${tagName}="${value}"`
const keywords = parseKeywords({DCSubjectBagOfWords: value})
if (!keywords) throw new Error('Invalid keywords payload')
return [

@@ -206,10 +186,2 @@ `<dc:subject>`,

}
private static _findIndexOfRdfDescriptionEnd(xmp: string): number {
const regex = /<rdf:Description(\s*(\w+:\w+=".*?")\s*)*?>/im
const match = xmp.match(regex)
if (!match) throw new Error('Unable to find end of rdf:description')
const rdfDescription = match[0]
return xmp.indexOf(rdfDescription) + rdfDescription.length - 1
}
}
{
"name": "@eris/exif",
"version": "0.3.1-alpha.1",
"version": "0.3.1-alpha.2",
"description": "Parses EXIF data.",

@@ -49,3 +49,3 @@ "main": "./dist/index.js",

},
"gitHead": "3ecabcb8242310727ef6c247feae54977438f9d2"
"gitHead": "1be49b5ba3508e530c16a5b221c44d8e4886b3ae"
}

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc