Cleanup proof hint flag code somewhat
This commit is contained in:
parent
2d4143fde6
commit
dd76692640
1 changed files with 12 additions and 127 deletions
|
|
@ -83,11 +83,6 @@ type FlagMatchInfo = {
|
||||||
re: string;
|
re: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
type FlagMatch = {
|
|
||||||
re: RegExp;
|
|
||||||
value: string;
|
|
||||||
};
|
|
||||||
|
|
||||||
const ruleScreenshot = (): FlagMatchRule[] => {
|
const ruleScreenshot = (): FlagMatchRule[] => {
|
||||||
return [
|
return [
|
||||||
{
|
{
|
||||||
|
|
@ -146,85 +141,19 @@ const aiHintFlags = (): FlagMatchRule[] => {
|
||||||
};
|
};
|
||||||
|
|
||||||
const matchFlag = (rules: FlagMatchRule[], file: any) => {
|
const matchFlag = (rules: FlagMatchRule[], file: any) => {
|
||||||
const matchParts = (parts: string[], o: any, re: RegExp[]): FlagMatch[] | undefined => {
|
|
||||||
if (parts.length == 0 || o == undefined) return undefined;
|
|
||||||
let part = parts[0];
|
|
||||||
const lastBracket = part.lastIndexOf("[");
|
|
||||||
if (part.endsWith("]") && lastBracket > 0) {
|
|
||||||
const optionalConstraint = part.substring(lastBracket + 1, part.length - 1);
|
|
||||||
part = part.substring(0, lastBracket);
|
|
||||||
if (o[part] != undefined) {
|
|
||||||
let opart: any[] = o[part];
|
|
||||||
if (!Array.isArray(opart)) {
|
|
||||||
opart = Object.values(opart) ?? [];
|
|
||||||
}
|
|
||||||
|
|
||||||
// Any constraints controlling what array object(s) to consider?
|
|
||||||
if (optionalConstraint) {
|
|
||||||
const [prop, val] = optionalConstraint.split("=");
|
|
||||||
opart = opart.filter((item) => item[prop] === val);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (parts.length == 1) {
|
|
||||||
let strings = opart as string[];
|
|
||||||
if (!strings) return undefined;
|
|
||||||
return strings.reduce((res: FlagMatch[] | undefined, s: any) => {
|
|
||||||
return re.reduce((res: FlagMatch[] | undefined, r: any) => {
|
|
||||||
if (r.test(s)) {
|
|
||||||
const r2 = res || [];
|
|
||||||
r2.push({ re: r, value: s as string });
|
|
||||||
return r2;
|
|
||||||
}
|
|
||||||
return res;
|
|
||||||
}, res);
|
|
||||||
}, undefined);
|
|
||||||
} else {
|
|
||||||
return opart.reduce((res: FlagMatch[] | undefined, o: any) => {
|
|
||||||
let matches = matchParts(parts.slice(1), o, re);
|
|
||||||
if (matches) {
|
|
||||||
const r2 = res || [];
|
|
||||||
r2.push(...matches);
|
|
||||||
return r2;
|
|
||||||
}
|
|
||||||
return res;
|
|
||||||
}, undefined);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
return undefined;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (o[part] != undefined) {
|
|
||||||
if (parts.length == 1) {
|
|
||||||
return re.reduce((res: FlagMatch[] | undefined, r: any) => {
|
|
||||||
if (r.test(o[part])) {
|
|
||||||
const r2 = res || [];
|
|
||||||
r2.push({ re: r, value: o[part] as string });
|
|
||||||
return r2;
|
|
||||||
}
|
|
||||||
return res;
|
|
||||||
}, undefined);
|
|
||||||
} else {
|
|
||||||
return matchParts(parts.slice(1), o[part], re);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
return undefined;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
let result = false;
|
let result = false;
|
||||||
let resultInfo: FlagMatchInfo[] = [];
|
let resultInfo: FlagMatchInfo[] = [];
|
||||||
for (let rule of rules) {
|
for (let rule of rules) {
|
||||||
try {
|
try {
|
||||||
const re: RegExp[] = (!Array.isArray(rule.match) ? [rule.match] : rule.match).map((m) => new RegExp(m, "gi"));
|
const re: RegExp[] = (!Array.isArray(rule.match) ? [rule.match] : rule.match).map((m) => new RegExp(m, "gi"));
|
||||||
let parts = rule.field.split("/");
|
const values = extractFlagValues(rule.field, file);
|
||||||
let matches = matchParts(parts, file, re);
|
values.forEach((v) => {
|
||||||
if (matches) {
|
re.forEach((r) => {
|
||||||
matches.forEach((m) => {
|
if (r.test(v.value)) {
|
||||||
resultInfo.push({ field: rule.description, value: m.value, re: m.re.source });
|
resultInfo.push({ field: v.path, value: v.value, re: r.source })
|
||||||
|
}
|
||||||
});
|
});
|
||||||
result = true;
|
})
|
||||||
}
|
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
console.error("Invalid RE", e);
|
console.error("Invalid RE", e);
|
||||||
}
|
}
|
||||||
|
|
@ -300,11 +229,6 @@ const extractFlagValues = (flagPath: string, file: any): FlagMatchRuleValue[] =>
|
||||||
export const extractProofHintFlags = (proof?: Proof): ProofHintFlags | undefined => {
|
export const extractProofHintFlags = (proof?: Proof): ProofHintFlags | undefined => {
|
||||||
if (!proof) return undefined;
|
if (!proof) return undefined;
|
||||||
|
|
||||||
let foundCreated = false;
|
|
||||||
|
|
||||||
let screenshot = false;
|
|
||||||
let camera = false;
|
|
||||||
let aiGenerated = false;
|
|
||||||
let aiEdited = false;
|
let aiEdited = false;
|
||||||
let valid = false;
|
let valid = false;
|
||||||
|
|
||||||
|
|
@ -313,55 +237,16 @@ export const extractProofHintFlags = (proof?: Proof): ProofHintFlags | undefined
|
||||||
if (results) {
|
if (results) {
|
||||||
valid = results.failure.length == 0 && results.success.length > 0;
|
valid = results.failure.length == 0 && results.success.length > 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
const manifests = Object.values(proof.integrity?.c2pa?.manifest_info.manifests ?? {});
|
|
||||||
for (const manifest of manifests) {
|
|
||||||
for (const assertion of manifest.assertions) {
|
|
||||||
if (assertion.label === "c2pa.actions") {
|
|
||||||
const actions = (assertion.data as C2PAActionsAssertion)?.actions ?? [];
|
|
||||||
const a = actions.find((a) => a.action === "c2pa.created");
|
|
||||||
if (a) {
|
|
||||||
// creator.value = a.softwareAgent;
|
|
||||||
// dateCreated.value = dayjs(Date.parse(manifest.signature_info.time));
|
|
||||||
if (a.digitalSourceType === C2PASourceTypeScreenCapture) {
|
|
||||||
screenshot = true;
|
|
||||||
}
|
|
||||||
if (
|
|
||||||
a.digitalSourceType === C2PASourceTypeDigitalCapture ||
|
|
||||||
a.digitalSourceType === C2PASourceTypeComputationalCapture ||
|
|
||||||
a.digitalSourceType === C2PASourceTypeCompositeCapture
|
|
||||||
) {
|
|
||||||
camera = true;
|
|
||||||
}
|
|
||||||
if (
|
|
||||||
a.digitalSourceType === C2PASourceTypeTrainedAlgorithmicMedia ||
|
|
||||||
a.digitalSourceType === C2PASourceTypeCompositeWithTrainedAlgorithmicMedia
|
|
||||||
) {
|
|
||||||
aiGenerated = true;
|
|
||||||
}
|
|
||||||
foundCreated = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (foundCreated) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (foundCreated) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (valid) {
|
if (valid) {
|
||||||
|
|
||||||
const dateCreated = extractFlagValues("integrity/c2pa/manifest_info/manifests[]/assertions[label=c2pa.actions]/data/actions[action=c2pa.created]/../../../../signature_info/issuer", proof);
|
const dateCreated = extractFlagValues("integrity/c2pa/manifest_info/manifests[]/assertions[label=c2pa.actions]/data/actions[action=c2pa.created]/../../../../signature_info/time", proof);
|
||||||
console.error("DATE CREATED", dateCreated);
|
console.log("DATE CREATED", dateCreated);
|
||||||
|
|
||||||
screenshot = matchFlag(ruleScreenshot(), proof).result;
|
|
||||||
const flags: ProofHintFlags = {
|
const flags: ProofHintFlags = {
|
||||||
aiGenerated,
|
aiGenerated: matchFlag(ruleAiGenerated(), proof).result,
|
||||||
aiEdited,
|
aiEdited,
|
||||||
screenshot,
|
screenshot: matchFlag(ruleScreenshot(), proof).result,
|
||||||
camera,
|
camera: matchFlag(ruleCamera(), proof).result,
|
||||||
};
|
};
|
||||||
return flags;
|
return flags;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue