@utilix-tech/sdk 0.5.0 → 0.7.0
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/README.md +22 -6
- package/dist/{chunk-WWKPLYEP.js → chunk-5CKOJXFU.js} +249 -2
- package/dist/{chunk-YBBYFAOV.js → chunk-F57WMKZO.js} +69 -1
- package/dist/{chunk-FL53T24A.js → chunk-GEFVMGZR.js} +2 -8
- package/dist/index.cjs +318 -9
- package/dist/index.d.cts +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/index.js +3 -3
- package/dist/media-D66WnthC.d.cts +107 -0
- package/dist/media-D66WnthC.d.ts +107 -0
- package/dist/{text-CI7JAl7F.d.cts → text-Bbx-tZ43.d.cts} +23 -2
- package/dist/{text-CI7JAl7F.d.ts → text-Bbx-tZ43.d.ts} +23 -2
- package/dist/tools/hashing.cjs +2 -8
- package/dist/tools/hashing.js +1 -1
- package/dist/tools/media.cjs +247 -0
- package/dist/tools/media.d.cts +1 -1
- package/dist/tools/media.d.ts +1 -1
- package/dist/tools/media.js +1 -1
- package/dist/tools/text.cjs +68 -0
- package/dist/tools/text.d.cts +1 -1
- package/dist/tools/text.d.ts +1 -1
- package/dist/tools/text.js +1 -1
- package/package.json +3 -3
- package/dist/media-D-K5aZnq.d.cts +0 -53
- package/dist/media-D-K5aZnq.d.ts +0 -53
package/dist/index.cjs
CHANGED
|
@@ -1736,13 +1736,7 @@ function generateMd5Hash(password) {
|
|
|
1736
1736
|
return "$apr1$" + md5__default.default(password);
|
|
1737
1737
|
}
|
|
1738
1738
|
function generateBcryptHash(password, rounds = 10) {
|
|
1739
|
-
|
|
1740
|
-
let salt = "";
|
|
1741
|
-
for (let i = 0; i < 22; i++) salt += chars[Math.floor(Math.random() * chars.length)];
|
|
1742
|
-
const roundStr = rounds.toString().padStart(2, "0");
|
|
1743
|
-
let hash = "";
|
|
1744
|
-
for (let i = 0; i < 31; i++) hash += chars[Math.floor(Math.random() * chars.length)];
|
|
1745
|
-
return `$2b$${roundStr}$${salt}${hash}`;
|
|
1739
|
+
return bcrypt__default.default.hashSync(password, rounds);
|
|
1746
1740
|
}
|
|
1747
1741
|
function generatePlain(password) {
|
|
1748
1742
|
return password;
|
|
@@ -1751,7 +1745,7 @@ function createEntry(username, password, algorithm = "bcrypt") {
|
|
|
1751
1745
|
let hashedPassword;
|
|
1752
1746
|
switch (algorithm) {
|
|
1753
1747
|
case "bcrypt":
|
|
1754
|
-
hashedPassword = generateBcryptHash();
|
|
1748
|
+
hashedPassword = generateBcryptHash(password);
|
|
1755
1749
|
break;
|
|
1756
1750
|
case "sha1":
|
|
1757
1751
|
hashedPassword = generateSha1Hash(password);
|
|
@@ -1851,6 +1845,7 @@ __export(text_exports, {
|
|
|
1851
1845
|
readabilityScore: () => readabilityScore,
|
|
1852
1846
|
renderMarkdown: () => renderMarkdown,
|
|
1853
1847
|
romanToNumber: () => romanToNumber,
|
|
1848
|
+
scoreReadability: () => scoreReadability,
|
|
1854
1849
|
sentenceCount: () => sentenceCount,
|
|
1855
1850
|
slugify: () => slugify,
|
|
1856
1851
|
slugifyAll: () => slugifyAll,
|
|
@@ -4189,6 +4184,73 @@ function detectPassiveVoice(text) {
|
|
|
4189
4184
|
const passivePercent = totalSentences > 0 ? Math.round(passiveSentences / totalSentences * 1e3) / 10 : 0;
|
|
4190
4185
|
return { sentences: analyzed, totalSentences, passiveSentences, passivePercent };
|
|
4191
4186
|
}
|
|
4187
|
+
function countSyllables(word) {
|
|
4188
|
+
const w = word.toLowerCase().replace(/[^a-z]/g, "");
|
|
4189
|
+
if (w.length === 0) return 0;
|
|
4190
|
+
if (w.length <= 3) return 1;
|
|
4191
|
+
let count = 0;
|
|
4192
|
+
let prevWasVowel = false;
|
|
4193
|
+
for (const ch of w) {
|
|
4194
|
+
const isVowel = "aeiouy".includes(ch);
|
|
4195
|
+
if (isVowel && !prevWasVowel) count++;
|
|
4196
|
+
prevWasVowel = isVowel;
|
|
4197
|
+
}
|
|
4198
|
+
if (w.endsWith("e") && !w.endsWith("le") && count > 1) count--;
|
|
4199
|
+
if (w.endsWith("le") && w.length > 2 && !"aeiouy".includes(w[w.length - 3])) count++;
|
|
4200
|
+
return Math.max(count, 1);
|
|
4201
|
+
}
|
|
4202
|
+
function readabilityGradeLabel(fleschReadingEase) {
|
|
4203
|
+
if (fleschReadingEase >= 90) return "Very easy (5th grade)";
|
|
4204
|
+
if (fleschReadingEase >= 80) return "Easy (6th grade)";
|
|
4205
|
+
if (fleschReadingEase >= 70) return "Fairly easy (7th grade)";
|
|
4206
|
+
if (fleschReadingEase >= 60) return "Standard (8th-9th grade)";
|
|
4207
|
+
if (fleschReadingEase >= 50) return "Fairly difficult (10th-12th grade)";
|
|
4208
|
+
if (fleschReadingEase >= 30) return "Difficult (college)";
|
|
4209
|
+
return "Very difficult (college graduate)";
|
|
4210
|
+
}
|
|
4211
|
+
function round1(n) {
|
|
4212
|
+
return Math.round(n * 10) / 10;
|
|
4213
|
+
}
|
|
4214
|
+
function scoreReadability(text) {
|
|
4215
|
+
const sentences = splitIntoSentences(text);
|
|
4216
|
+
const words = text.match(/[a-zA-Z']+/g) ?? [];
|
|
4217
|
+
const sentenceCount2 = Math.max(sentences.length, 1);
|
|
4218
|
+
const wordCount = words.length;
|
|
4219
|
+
const syllableCounts = words.map(countSyllables);
|
|
4220
|
+
const syllableCount2 = syllableCounts.reduce((a, b) => a + b, 0);
|
|
4221
|
+
const complexWordCount = syllableCounts.filter((c) => c >= 3).length;
|
|
4222
|
+
if (wordCount === 0) {
|
|
4223
|
+
return {
|
|
4224
|
+
wordCount: 0,
|
|
4225
|
+
sentenceCount: 0,
|
|
4226
|
+
syllableCount: 0,
|
|
4227
|
+
complexWordCount: 0,
|
|
4228
|
+
avgWordsPerSentence: 0,
|
|
4229
|
+
avgSyllablesPerWord: 0,
|
|
4230
|
+
fleschReadingEase: 0,
|
|
4231
|
+
fleschKincaidGrade: 0,
|
|
4232
|
+
gunningFog: 0,
|
|
4233
|
+
readingLevel: "No text to score"
|
|
4234
|
+
};
|
|
4235
|
+
}
|
|
4236
|
+
const avgWordsPerSentence = wordCount / sentenceCount2;
|
|
4237
|
+
const avgSyllablesPerWord = syllableCount2 / wordCount;
|
|
4238
|
+
const fleschReadingEase = round1(206.835 - 1.015 * avgWordsPerSentence - 84.6 * avgSyllablesPerWord);
|
|
4239
|
+
const fleschKincaidGrade = round1(0.39 * avgWordsPerSentence + 11.8 * avgSyllablesPerWord - 15.59);
|
|
4240
|
+
const gunningFog = round1(0.4 * (avgWordsPerSentence + 100 * (complexWordCount / wordCount)));
|
|
4241
|
+
return {
|
|
4242
|
+
wordCount,
|
|
4243
|
+
sentenceCount: sentences.length,
|
|
4244
|
+
syllableCount: syllableCount2,
|
|
4245
|
+
complexWordCount,
|
|
4246
|
+
avgWordsPerSentence: round1(avgWordsPerSentence),
|
|
4247
|
+
avgSyllablesPerWord: round1(avgSyllablesPerWord),
|
|
4248
|
+
fleschReadingEase,
|
|
4249
|
+
fleschKincaidGrade,
|
|
4250
|
+
gunningFog,
|
|
4251
|
+
readingLevel: readabilityGradeLabel(fleschReadingEase)
|
|
4252
|
+
};
|
|
4253
|
+
}
|
|
4192
4254
|
|
|
4193
4255
|
// src/tools/data.ts
|
|
4194
4256
|
var data_exports = {};
|
|
@@ -16934,8 +16996,10 @@ function summarizeForLlm(text, maxTokens = 200, strategy = "extractive") {
|
|
|
16934
16996
|
// src/tools/media.ts
|
|
16935
16997
|
var media_exports = {};
|
|
16936
16998
|
__export(media_exports, {
|
|
16999
|
+
readExifData: () => readExifData,
|
|
16937
17000
|
readImageInfo: () => readImageInfo,
|
|
16938
|
-
readPdfMetadata: () => readPdfMetadata
|
|
17001
|
+
readPdfMetadata: () => readPdfMetadata,
|
|
17002
|
+
readWavInfo: () => readWavInfo
|
|
16939
17003
|
});
|
|
16940
17004
|
function readU32BE(bytes, offset) {
|
|
16941
17005
|
return (bytes[offset] << 24 | bytes[offset + 1] << 16 | bytes[offset + 2] << 8 | bytes[offset + 3]) >>> 0;
|
|
@@ -17062,6 +17126,195 @@ function readImageInfo(bytes) {
|
|
|
17062
17126
|
}
|
|
17063
17127
|
return { error: "Unrecognized image format. Supported formats: PNG, JPEG, GIF, WebP, BMP" };
|
|
17064
17128
|
}
|
|
17129
|
+
var ORIENTATION_LABELS = {
|
|
17130
|
+
1: "Normal",
|
|
17131
|
+
2: "Mirrored horizontal",
|
|
17132
|
+
3: "Rotated 180\xB0",
|
|
17133
|
+
4: "Mirrored vertical",
|
|
17134
|
+
5: "Mirrored horizontal, rotated 90\xB0 CCW",
|
|
17135
|
+
6: "Rotated 90\xB0 CW",
|
|
17136
|
+
7: "Mirrored horizontal, rotated 90\xB0 CW",
|
|
17137
|
+
8: "Rotated 90\xB0 CCW"
|
|
17138
|
+
};
|
|
17139
|
+
function tu16(r, o) {
|
|
17140
|
+
return r.view.getUint16(o, r.little);
|
|
17141
|
+
}
|
|
17142
|
+
function tu32(r, o) {
|
|
17143
|
+
return r.view.getUint32(o, r.little);
|
|
17144
|
+
}
|
|
17145
|
+
function readIfdEntries(r, ifdOffset) {
|
|
17146
|
+
if (ifdOffset < 0 || ifdOffset + 2 > r.bytes.length) return null;
|
|
17147
|
+
const numEntries = tu16(r, ifdOffset);
|
|
17148
|
+
const entries = [];
|
|
17149
|
+
for (let i = 0; i < numEntries; i++) {
|
|
17150
|
+
const entryOffset = ifdOffset + 2 + i * 12;
|
|
17151
|
+
if (entryOffset + 12 > r.bytes.length) break;
|
|
17152
|
+
entries.push({
|
|
17153
|
+
tag: tu16(r, entryOffset),
|
|
17154
|
+
type: tu16(r, entryOffset + 2),
|
|
17155
|
+
count: tu32(r, entryOffset + 4),
|
|
17156
|
+
valueOffsetField: entryOffset + 8
|
|
17157
|
+
});
|
|
17158
|
+
}
|
|
17159
|
+
return { entries };
|
|
17160
|
+
}
|
|
17161
|
+
function findEntry(entries, tag) {
|
|
17162
|
+
return entries.find((e) => e.tag === tag);
|
|
17163
|
+
}
|
|
17164
|
+
function readAscii(r, entry) {
|
|
17165
|
+
const size = entry.count;
|
|
17166
|
+
const inline = size <= 4;
|
|
17167
|
+
const dataOffset = inline ? entry.valueOffsetField : r.tiffStart + tu32(r, entry.valueOffsetField);
|
|
17168
|
+
if (dataOffset < 0 || dataOffset + size > r.bytes.length) return null;
|
|
17169
|
+
let out = "";
|
|
17170
|
+
for (let i = 0; i < size; i++) {
|
|
17171
|
+
const c = r.bytes[dataOffset + i];
|
|
17172
|
+
if (c === 0) break;
|
|
17173
|
+
out += String.fromCharCode(c);
|
|
17174
|
+
}
|
|
17175
|
+
const trimmed = out.trim();
|
|
17176
|
+
return trimmed || null;
|
|
17177
|
+
}
|
|
17178
|
+
function readRational(r, entry) {
|
|
17179
|
+
const dataOffset = r.tiffStart + tu32(r, entry.valueOffsetField);
|
|
17180
|
+
if (dataOffset < 0 || dataOffset + 8 > r.bytes.length) return null;
|
|
17181
|
+
return { num: tu32(r, dataOffset), den: tu32(r, dataOffset + 4) };
|
|
17182
|
+
}
|
|
17183
|
+
function readGpsCoordinate(r, entries, valueTag, refTag) {
|
|
17184
|
+
const valueEntry = findEntry(entries, valueTag);
|
|
17185
|
+
if (!valueEntry) return null;
|
|
17186
|
+
const dataOffset = r.tiffStart + tu32(r, valueEntry.valueOffsetField);
|
|
17187
|
+
if (dataOffset < 0 || dataOffset + 24 > r.bytes.length) return null;
|
|
17188
|
+
const deg = tu32(r, dataOffset) / (tu32(r, dataOffset + 4) || 1);
|
|
17189
|
+
const min = tu32(r, dataOffset + 8) / (tu32(r, dataOffset + 12) || 1);
|
|
17190
|
+
const sec = tu32(r, dataOffset + 16) / (tu32(r, dataOffset + 20) || 1);
|
|
17191
|
+
let decimal = deg + min / 60 + sec / 3600;
|
|
17192
|
+
const refEntry = findEntry(entries, refTag);
|
|
17193
|
+
const ref = refEntry ? readAscii(r, refEntry) : null;
|
|
17194
|
+
if (ref === "S" || ref === "W") decimal = -decimal;
|
|
17195
|
+
return Math.round(decimal * 1e6) / 1e6;
|
|
17196
|
+
}
|
|
17197
|
+
function gcd2(a, b) {
|
|
17198
|
+
return b === 0 ? a : gcd2(b, a % b);
|
|
17199
|
+
}
|
|
17200
|
+
function round2(n) {
|
|
17201
|
+
return Math.round(n * 100) / 100;
|
|
17202
|
+
}
|
|
17203
|
+
function formatExposureTime(num, den) {
|
|
17204
|
+
if (num === 0) return "0s";
|
|
17205
|
+
if (num >= den) return `${round2(num / den)}s`;
|
|
17206
|
+
const divisor = gcd2(num, den) || 1;
|
|
17207
|
+
const n = num / divisor;
|
|
17208
|
+
const d = den / divisor;
|
|
17209
|
+
return `1/${Math.round(d / n)}`;
|
|
17210
|
+
}
|
|
17211
|
+
function readExifData(bytes) {
|
|
17212
|
+
if (bytes.length < 4 || bytes[0] !== 255 || bytes[1] !== 216) {
|
|
17213
|
+
return { error: "Not a JPEG file (EXIF is only read from JPEG files)" };
|
|
17214
|
+
}
|
|
17215
|
+
let offset = 2;
|
|
17216
|
+
let exifStart = -1;
|
|
17217
|
+
while (offset + 4 <= bytes.length) {
|
|
17218
|
+
if (bytes[offset] !== 255) {
|
|
17219
|
+
offset++;
|
|
17220
|
+
continue;
|
|
17221
|
+
}
|
|
17222
|
+
const marker = bytes[offset + 1];
|
|
17223
|
+
if (marker === 216 || marker === 1 || marker >= 208 && marker <= 215) {
|
|
17224
|
+
offset += 2;
|
|
17225
|
+
continue;
|
|
17226
|
+
}
|
|
17227
|
+
if (marker === 217 || marker === 218) break;
|
|
17228
|
+
const segmentLength = bytes[offset + 2] << 8 | bytes[offset + 3];
|
|
17229
|
+
if (marker === 225) {
|
|
17230
|
+
const idOffset = offset + 4;
|
|
17231
|
+
if (idOffset + 6 <= bytes.length && bytes[idOffset] === 69 && bytes[idOffset + 1] === 120 && bytes[idOffset + 2] === 105 && bytes[idOffset + 3] === 102 && bytes[idOffset + 4] === 0 && bytes[idOffset + 5] === 0) {
|
|
17232
|
+
exifStart = idOffset + 6;
|
|
17233
|
+
break;
|
|
17234
|
+
}
|
|
17235
|
+
}
|
|
17236
|
+
offset += 2 + segmentLength;
|
|
17237
|
+
}
|
|
17238
|
+
if (exifStart === -1) return { error: "No EXIF segment found in this JPEG" };
|
|
17239
|
+
if (exifStart + 8 > bytes.length) return { error: "Truncated EXIF segment" };
|
|
17240
|
+
const byteOrder = String.fromCharCode(bytes[exifStart], bytes[exifStart + 1]);
|
|
17241
|
+
if (byteOrder !== "II" && byteOrder !== "MM") return { error: "Invalid TIFF byte order marker in EXIF data" };
|
|
17242
|
+
const little = byteOrder === "II";
|
|
17243
|
+
const view = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
|
|
17244
|
+
const r = { bytes, view, little, tiffStart: exifStart };
|
|
17245
|
+
if (tu16(r, exifStart + 2) !== 42) return { error: "Invalid TIFF magic number in EXIF data" };
|
|
17246
|
+
const ifd0Offset = exifStart + tu32(r, exifStart + 4);
|
|
17247
|
+
const ifd0 = readIfdEntries(r, ifd0Offset);
|
|
17248
|
+
if (!ifd0) return { error: "Could not read IFD0 from EXIF data" };
|
|
17249
|
+
const result = { tagCount: ifd0.entries.length };
|
|
17250
|
+
const makeEntry = findEntry(ifd0.entries, 271);
|
|
17251
|
+
if (makeEntry) {
|
|
17252
|
+
const v = readAscii(r, makeEntry);
|
|
17253
|
+
if (v) result.make = v;
|
|
17254
|
+
}
|
|
17255
|
+
const modelEntry = findEntry(ifd0.entries, 272);
|
|
17256
|
+
if (modelEntry) {
|
|
17257
|
+
const v = readAscii(r, modelEntry);
|
|
17258
|
+
if (v) result.model = v;
|
|
17259
|
+
}
|
|
17260
|
+
const softwareEntry = findEntry(ifd0.entries, 305);
|
|
17261
|
+
if (softwareEntry) {
|
|
17262
|
+
const v = readAscii(r, softwareEntry);
|
|
17263
|
+
if (v) result.software = v;
|
|
17264
|
+
}
|
|
17265
|
+
const dateTimeEntry = findEntry(ifd0.entries, 306);
|
|
17266
|
+
if (dateTimeEntry) {
|
|
17267
|
+
const v = readAscii(r, dateTimeEntry);
|
|
17268
|
+
if (v) result.dateTime = v;
|
|
17269
|
+
}
|
|
17270
|
+
const orientEntry = findEntry(ifd0.entries, 274);
|
|
17271
|
+
if (orientEntry) {
|
|
17272
|
+
const v = tu16(r, orientEntry.valueOffsetField);
|
|
17273
|
+
result.orientation = v;
|
|
17274
|
+
result.orientationLabel = ORIENTATION_LABELS[v] ?? "Unknown";
|
|
17275
|
+
}
|
|
17276
|
+
const exifIfdPtr = findEntry(ifd0.entries, 34665);
|
|
17277
|
+
if (exifIfdPtr) {
|
|
17278
|
+
const subOffset = exifStart + tu32(r, exifIfdPtr.valueOffsetField);
|
|
17279
|
+
const sub = readIfdEntries(r, subOffset);
|
|
17280
|
+
if (sub) {
|
|
17281
|
+
const dtoEntry = findEntry(sub.entries, 36867);
|
|
17282
|
+
if (dtoEntry) {
|
|
17283
|
+
const v = readAscii(r, dtoEntry);
|
|
17284
|
+
if (v) result.dateTimeOriginal = v;
|
|
17285
|
+
}
|
|
17286
|
+
const expEntry = findEntry(sub.entries, 33434);
|
|
17287
|
+
if (expEntry) {
|
|
17288
|
+
const rat = readRational(r, expEntry);
|
|
17289
|
+
if (rat && rat.den !== 0) result.exposureTime = formatExposureTime(rat.num, rat.den);
|
|
17290
|
+
}
|
|
17291
|
+
const fEntry = findEntry(sub.entries, 33437);
|
|
17292
|
+
if (fEntry) {
|
|
17293
|
+
const rat = readRational(r, fEntry);
|
|
17294
|
+
if (rat && rat.den !== 0) result.fNumber = round2(rat.num / rat.den);
|
|
17295
|
+
}
|
|
17296
|
+
const isoEntry = findEntry(sub.entries, 34855);
|
|
17297
|
+
if (isoEntry) result.isoSpeed = tu16(r, isoEntry.valueOffsetField);
|
|
17298
|
+
const focalEntry = findEntry(sub.entries, 37386);
|
|
17299
|
+
if (focalEntry) {
|
|
17300
|
+
const rat = readRational(r, focalEntry);
|
|
17301
|
+
if (rat && rat.den !== 0) result.focalLength = round2(rat.num / rat.den);
|
|
17302
|
+
}
|
|
17303
|
+
}
|
|
17304
|
+
}
|
|
17305
|
+
const gpsIfdPtr = findEntry(ifd0.entries, 34853);
|
|
17306
|
+
if (gpsIfdPtr) {
|
|
17307
|
+
const gpsOffset = exifStart + tu32(r, gpsIfdPtr.valueOffsetField);
|
|
17308
|
+
const gps = readIfdEntries(r, gpsOffset);
|
|
17309
|
+
if (gps) {
|
|
17310
|
+
const lat = readGpsCoordinate(r, gps.entries, 2, 1);
|
|
17311
|
+
const lon = readGpsCoordinate(r, gps.entries, 4, 3);
|
|
17312
|
+
if (lat !== null) result.gpsLatitude = lat;
|
|
17313
|
+
if (lon !== null) result.gpsLongitude = lon;
|
|
17314
|
+
}
|
|
17315
|
+
}
|
|
17316
|
+
return result;
|
|
17317
|
+
}
|
|
17065
17318
|
function bytesToLatin1(bytes) {
|
|
17066
17319
|
let out = "";
|
|
17067
17320
|
const CHUNK = 32768;
|
|
@@ -17204,6 +17457,62 @@ function readPdfMetadata(bytes) {
|
|
|
17204
17457
|
encrypted
|
|
17205
17458
|
};
|
|
17206
17459
|
}
|
|
17460
|
+
var AUDIO_FORMAT_LABELS = {
|
|
17461
|
+
1: "PCM",
|
|
17462
|
+
3: "IEEE float",
|
|
17463
|
+
6: "A-law",
|
|
17464
|
+
7: "mu-law",
|
|
17465
|
+
65534: "Extensible"
|
|
17466
|
+
};
|
|
17467
|
+
function readAscii4(bytes, offset) {
|
|
17468
|
+
return String.fromCharCode(bytes[offset], bytes[offset + 1], bytes[offset + 2], bytes[offset + 3]);
|
|
17469
|
+
}
|
|
17470
|
+
function readWavInfo(bytes) {
|
|
17471
|
+
if (bytes.length < 12) return { error: "File is too small to be a valid WAV file" };
|
|
17472
|
+
if (readAscii4(bytes, 0) !== "RIFF") return { error: 'Not a RIFF file (missing "RIFF" header)' };
|
|
17473
|
+
if (readAscii4(bytes, 8) !== "WAVE") return { error: 'Not a WAVE file (missing "WAVE" format marker)' };
|
|
17474
|
+
const view = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
|
|
17475
|
+
const fileSize = view.getUint32(4, true) + 8;
|
|
17476
|
+
let offset = 12;
|
|
17477
|
+
let fmt = null;
|
|
17478
|
+
let dataSize = null;
|
|
17479
|
+
while (offset + 8 <= bytes.length) {
|
|
17480
|
+
const chunkId = readAscii4(bytes, offset);
|
|
17481
|
+
const chunkSize = view.getUint32(offset + 4, true);
|
|
17482
|
+
const dataOffset = offset + 8;
|
|
17483
|
+
if (chunkId === "fmt ") {
|
|
17484
|
+
if (dataOffset + 16 > bytes.length) return { error: 'Truncated "fmt " chunk' };
|
|
17485
|
+
fmt = {
|
|
17486
|
+
audioFormat: view.getUint16(dataOffset, true),
|
|
17487
|
+
channels: view.getUint16(dataOffset + 2, true),
|
|
17488
|
+
sampleRate: view.getUint32(dataOffset + 4, true),
|
|
17489
|
+
byteRate: view.getUint32(dataOffset + 8, true),
|
|
17490
|
+
blockAlign: view.getUint16(dataOffset + 12, true),
|
|
17491
|
+
bitsPerSample: view.getUint16(dataOffset + 14, true)
|
|
17492
|
+
};
|
|
17493
|
+
} else if (chunkId === "data") {
|
|
17494
|
+
dataSize = Math.min(chunkSize, bytes.length - dataOffset);
|
|
17495
|
+
}
|
|
17496
|
+
offset = dataOffset + chunkSize + chunkSize % 2;
|
|
17497
|
+
if (fmt && dataSize !== null) break;
|
|
17498
|
+
}
|
|
17499
|
+
if (!fmt) return { error: 'No "fmt " chunk found in this WAV file' };
|
|
17500
|
+
if (dataSize === null) return { error: 'No "data" chunk found in this WAV file' };
|
|
17501
|
+
if (fmt.byteRate <= 0) return { error: 'Invalid byte rate in "fmt " chunk' };
|
|
17502
|
+
const durationSeconds = Math.round(dataSize / fmt.byteRate * 1e3) / 1e3;
|
|
17503
|
+
return {
|
|
17504
|
+
audioFormat: fmt.audioFormat,
|
|
17505
|
+
audioFormatLabel: AUDIO_FORMAT_LABELS[fmt.audioFormat] ?? `Unknown (0x${fmt.audioFormat.toString(16)})`,
|
|
17506
|
+
channels: fmt.channels,
|
|
17507
|
+
sampleRate: fmt.sampleRate,
|
|
17508
|
+
byteRate: fmt.byteRate,
|
|
17509
|
+
blockAlign: fmt.blockAlign,
|
|
17510
|
+
bitsPerSample: fmt.bitsPerSample,
|
|
17511
|
+
dataSize,
|
|
17512
|
+
durationSeconds,
|
|
17513
|
+
fileSize
|
|
17514
|
+
};
|
|
17515
|
+
}
|
|
17207
17516
|
|
|
17208
17517
|
// src/index.ts
|
|
17209
17518
|
var version = "0.1.0";
|
package/dist/index.d.cts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
export { j as json } from './json-BjSoIS1h.cjs';
|
|
2
2
|
export { e as encoding } from './encoding-7gmq-vkV.cjs';
|
|
3
3
|
export { h as hashing } from './hashing-CnetQFD_.cjs';
|
|
4
|
-
export { t as text } from './text-
|
|
4
|
+
export { t as text } from './text-Bbx-tZ43.cjs';
|
|
5
5
|
export { d as data } from './data-CakDxAcT.cjs';
|
|
6
6
|
export { g as generators } from './generators-BGtRGpJZ.cjs';
|
|
7
7
|
export { t as time } from './time-DbT8fjaF.cjs';
|
|
@@ -13,7 +13,7 @@ export { c as color } from './color-tPwZCr9H.cjs';
|
|
|
13
13
|
export { c as css } from './css-Cf7AMGM-.cjs';
|
|
14
14
|
export { m as misc } from './misc-CA3N198T.cjs';
|
|
15
15
|
export { a as ai_agent } from './ai_agent-CcpkV2DR.cjs';
|
|
16
|
-
export { m as media } from './media-
|
|
16
|
+
export { m as media } from './media-D66WnthC.cjs';
|
|
17
17
|
|
|
18
18
|
declare const version = "0.1.0";
|
|
19
19
|
|
package/dist/index.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
export { j as json } from './json-BjSoIS1h.js';
|
|
2
2
|
export { e as encoding } from './encoding-7gmq-vkV.js';
|
|
3
3
|
export { h as hashing } from './hashing-CnetQFD_.js';
|
|
4
|
-
export { t as text } from './text-
|
|
4
|
+
export { t as text } from './text-Bbx-tZ43.js';
|
|
5
5
|
export { d as data } from './data-CakDxAcT.js';
|
|
6
6
|
export { g as generators } from './generators-BGtRGpJZ.js';
|
|
7
7
|
export { t as time } from './time-DbT8fjaF.js';
|
|
@@ -13,7 +13,7 @@ export { c as color } from './color-tPwZCr9H.js';
|
|
|
13
13
|
export { c as css } from './css-Cf7AMGM-.js';
|
|
14
14
|
export { m as misc } from './misc-CA3N198T.js';
|
|
15
15
|
export { a as ai_agent } from './ai_agent-CcpkV2DR.js';
|
|
16
|
-
export { m as media } from './media-
|
|
16
|
+
export { m as media } from './media-D66WnthC.js';
|
|
17
17
|
|
|
18
18
|
declare const version = "0.1.0";
|
|
19
19
|
|
package/dist/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export { media_exports as media } from './chunk-
|
|
1
|
+
export { media_exports as media } from './chunk-5CKOJXFU.js';
|
|
2
2
|
export { units_exports as units } from './chunk-QJE743LY.js';
|
|
3
3
|
export { network_exports as network } from './chunk-V5JKVDBA.js';
|
|
4
4
|
export { api_exports as api } from './chunk-Q3B3YWOA.js';
|
|
@@ -9,8 +9,8 @@ export { misc_exports as misc } from './chunk-GX7H6TAX.js';
|
|
|
9
9
|
export { ai_agent_exports as ai_agent } from './chunk-M35VJETW.js';
|
|
10
10
|
export { json_exports as json } from './chunk-TSAGO3XP.js';
|
|
11
11
|
export { encoding_exports as encoding } from './chunk-IPR7FSX4.js';
|
|
12
|
-
export { hashing_exports as hashing } from './chunk-
|
|
13
|
-
export { text_exports as text } from './chunk-
|
|
12
|
+
export { hashing_exports as hashing } from './chunk-GEFVMGZR.js';
|
|
13
|
+
export { text_exports as text } from './chunk-F57WMKZO.js';
|
|
14
14
|
export { data_exports as data } from './chunk-DNCOIO5N.js';
|
|
15
15
|
export { generators_exports as generators } from './chunk-2CJSLYWI.js';
|
|
16
16
|
export { time_exports as time } from './chunk-ZPQZEIXP.js';
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
type ImageFormat = 'png' | 'jpeg' | 'gif' | 'webp' | 'bmp';
|
|
2
|
+
interface ImageInfo {
|
|
3
|
+
format: ImageFormat;
|
|
4
|
+
width: number;
|
|
5
|
+
height: number;
|
|
6
|
+
bitDepth?: number;
|
|
7
|
+
colorType?: string;
|
|
8
|
+
hasAlpha?: boolean;
|
|
9
|
+
}
|
|
10
|
+
interface ImageInfoError {
|
|
11
|
+
error: string;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Read image format, dimensions, and basic color info straight from file
|
|
15
|
+
* bytes — no decoding, no image library, no canvas. Supports PNG, JPEG,
|
|
16
|
+
* GIF, WebP, and BMP.
|
|
17
|
+
*/
|
|
18
|
+
declare function readImageInfo(bytes: Uint8Array): ImageInfo | ImageInfoError;
|
|
19
|
+
interface ExifData {
|
|
20
|
+
make?: string;
|
|
21
|
+
model?: string;
|
|
22
|
+
software?: string;
|
|
23
|
+
orientation?: number;
|
|
24
|
+
orientationLabel?: string;
|
|
25
|
+
dateTime?: string;
|
|
26
|
+
dateTimeOriginal?: string;
|
|
27
|
+
exposureTime?: string;
|
|
28
|
+
fNumber?: number;
|
|
29
|
+
isoSpeed?: number;
|
|
30
|
+
focalLength?: number;
|
|
31
|
+
gpsLatitude?: number;
|
|
32
|
+
gpsLongitude?: number;
|
|
33
|
+
tagCount: number;
|
|
34
|
+
}
|
|
35
|
+
interface ExifError {
|
|
36
|
+
error: string;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Read common EXIF tags (make, model, orientation, timestamps, exposure
|
|
40
|
+
* settings, GPS coordinates) directly from a JPEG's APP1 segment. Only
|
|
41
|
+
* JPEG is supported: PNG, WebP, and other formats don't carry EXIF the
|
|
42
|
+
* same way and are rejected with an error.
|
|
43
|
+
*/
|
|
44
|
+
declare function readExifData(bytes: Uint8Array): ExifData | ExifError;
|
|
45
|
+
interface PdfMetadata {
|
|
46
|
+
version: string | null;
|
|
47
|
+
pageCount: number | null;
|
|
48
|
+
title: string | null;
|
|
49
|
+
author: string | null;
|
|
50
|
+
subject: string | null;
|
|
51
|
+
keywords: string | null;
|
|
52
|
+
creator: string | null;
|
|
53
|
+
producer: string | null;
|
|
54
|
+
creationDate: string | null;
|
|
55
|
+
modDate: string | null;
|
|
56
|
+
encrypted: boolean;
|
|
57
|
+
}
|
|
58
|
+
interface PdfMetadataError {
|
|
59
|
+
error: string;
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Read PDF metadata (title, author, dates, page count, encryption flag)
|
|
63
|
+
* straight from the file's trailer/Info dictionary and page tree — no
|
|
64
|
+
* pdf.js or other PDF rendering library required.
|
|
65
|
+
*/
|
|
66
|
+
declare function readPdfMetadata(bytes: Uint8Array): PdfMetadata | PdfMetadataError;
|
|
67
|
+
interface WavInfo {
|
|
68
|
+
audioFormat: number;
|
|
69
|
+
audioFormatLabel: string;
|
|
70
|
+
channels: number;
|
|
71
|
+
sampleRate: number;
|
|
72
|
+
byteRate: number;
|
|
73
|
+
blockAlign: number;
|
|
74
|
+
bitsPerSample: number;
|
|
75
|
+
dataSize: number;
|
|
76
|
+
durationSeconds: number;
|
|
77
|
+
fileSize: number;
|
|
78
|
+
}
|
|
79
|
+
interface WavInfoError {
|
|
80
|
+
error: string;
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* Read a WAV file's RIFF/fmt/data chunk headers to report sample rate,
|
|
84
|
+
* channel count, bit depth, and duration, without decoding any audio
|
|
85
|
+
* samples. Only the canonical RIFF/WAVE container is supported (not the
|
|
86
|
+
* rarer RF64 variant used for files over 4GB).
|
|
87
|
+
*/
|
|
88
|
+
declare function readWavInfo(bytes: Uint8Array): WavInfo | WavInfoError;
|
|
89
|
+
|
|
90
|
+
type media_ExifData = ExifData;
|
|
91
|
+
type media_ExifError = ExifError;
|
|
92
|
+
type media_ImageFormat = ImageFormat;
|
|
93
|
+
type media_ImageInfo = ImageInfo;
|
|
94
|
+
type media_ImageInfoError = ImageInfoError;
|
|
95
|
+
type media_PdfMetadata = PdfMetadata;
|
|
96
|
+
type media_PdfMetadataError = PdfMetadataError;
|
|
97
|
+
type media_WavInfo = WavInfo;
|
|
98
|
+
type media_WavInfoError = WavInfoError;
|
|
99
|
+
declare const media_readExifData: typeof readExifData;
|
|
100
|
+
declare const media_readImageInfo: typeof readImageInfo;
|
|
101
|
+
declare const media_readPdfMetadata: typeof readPdfMetadata;
|
|
102
|
+
declare const media_readWavInfo: typeof readWavInfo;
|
|
103
|
+
declare namespace media {
|
|
104
|
+
export { type media_ExifData as ExifData, type media_ExifError as ExifError, type media_ImageFormat as ImageFormat, type media_ImageInfo as ImageInfo, type media_ImageInfoError as ImageInfoError, type media_PdfMetadata as PdfMetadata, type media_PdfMetadataError as PdfMetadataError, type media_WavInfo as WavInfo, type media_WavInfoError as WavInfoError, media_readExifData as readExifData, media_readImageInfo as readImageInfo, media_readPdfMetadata as readPdfMetadata, media_readWavInfo as readWavInfo };
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
export { type ExifData as E, type ImageFormat as I, type PdfMetadata as P, type WavInfo as W, type ExifError as a, type ImageInfo as b, type ImageInfoError as c, type PdfMetadataError as d, type WavInfoError as e, readImageInfo as f, readPdfMetadata as g, readWavInfo as h, media as m, readExifData as r };
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
type ImageFormat = 'png' | 'jpeg' | 'gif' | 'webp' | 'bmp';
|
|
2
|
+
interface ImageInfo {
|
|
3
|
+
format: ImageFormat;
|
|
4
|
+
width: number;
|
|
5
|
+
height: number;
|
|
6
|
+
bitDepth?: number;
|
|
7
|
+
colorType?: string;
|
|
8
|
+
hasAlpha?: boolean;
|
|
9
|
+
}
|
|
10
|
+
interface ImageInfoError {
|
|
11
|
+
error: string;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Read image format, dimensions, and basic color info straight from file
|
|
15
|
+
* bytes — no decoding, no image library, no canvas. Supports PNG, JPEG,
|
|
16
|
+
* GIF, WebP, and BMP.
|
|
17
|
+
*/
|
|
18
|
+
declare function readImageInfo(bytes: Uint8Array): ImageInfo | ImageInfoError;
|
|
19
|
+
interface ExifData {
|
|
20
|
+
make?: string;
|
|
21
|
+
model?: string;
|
|
22
|
+
software?: string;
|
|
23
|
+
orientation?: number;
|
|
24
|
+
orientationLabel?: string;
|
|
25
|
+
dateTime?: string;
|
|
26
|
+
dateTimeOriginal?: string;
|
|
27
|
+
exposureTime?: string;
|
|
28
|
+
fNumber?: number;
|
|
29
|
+
isoSpeed?: number;
|
|
30
|
+
focalLength?: number;
|
|
31
|
+
gpsLatitude?: number;
|
|
32
|
+
gpsLongitude?: number;
|
|
33
|
+
tagCount: number;
|
|
34
|
+
}
|
|
35
|
+
interface ExifError {
|
|
36
|
+
error: string;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Read common EXIF tags (make, model, orientation, timestamps, exposure
|
|
40
|
+
* settings, GPS coordinates) directly from a JPEG's APP1 segment. Only
|
|
41
|
+
* JPEG is supported: PNG, WebP, and other formats don't carry EXIF the
|
|
42
|
+
* same way and are rejected with an error.
|
|
43
|
+
*/
|
|
44
|
+
declare function readExifData(bytes: Uint8Array): ExifData | ExifError;
|
|
45
|
+
interface PdfMetadata {
|
|
46
|
+
version: string | null;
|
|
47
|
+
pageCount: number | null;
|
|
48
|
+
title: string | null;
|
|
49
|
+
author: string | null;
|
|
50
|
+
subject: string | null;
|
|
51
|
+
keywords: string | null;
|
|
52
|
+
creator: string | null;
|
|
53
|
+
producer: string | null;
|
|
54
|
+
creationDate: string | null;
|
|
55
|
+
modDate: string | null;
|
|
56
|
+
encrypted: boolean;
|
|
57
|
+
}
|
|
58
|
+
interface PdfMetadataError {
|
|
59
|
+
error: string;
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Read PDF metadata (title, author, dates, page count, encryption flag)
|
|
63
|
+
* straight from the file's trailer/Info dictionary and page tree — no
|
|
64
|
+
* pdf.js or other PDF rendering library required.
|
|
65
|
+
*/
|
|
66
|
+
declare function readPdfMetadata(bytes: Uint8Array): PdfMetadata | PdfMetadataError;
|
|
67
|
+
interface WavInfo {
|
|
68
|
+
audioFormat: number;
|
|
69
|
+
audioFormatLabel: string;
|
|
70
|
+
channels: number;
|
|
71
|
+
sampleRate: number;
|
|
72
|
+
byteRate: number;
|
|
73
|
+
blockAlign: number;
|
|
74
|
+
bitsPerSample: number;
|
|
75
|
+
dataSize: number;
|
|
76
|
+
durationSeconds: number;
|
|
77
|
+
fileSize: number;
|
|
78
|
+
}
|
|
79
|
+
interface WavInfoError {
|
|
80
|
+
error: string;
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* Read a WAV file's RIFF/fmt/data chunk headers to report sample rate,
|
|
84
|
+
* channel count, bit depth, and duration, without decoding any audio
|
|
85
|
+
* samples. Only the canonical RIFF/WAVE container is supported (not the
|
|
86
|
+
* rarer RF64 variant used for files over 4GB).
|
|
87
|
+
*/
|
|
88
|
+
declare function readWavInfo(bytes: Uint8Array): WavInfo | WavInfoError;
|
|
89
|
+
|
|
90
|
+
type media_ExifData = ExifData;
|
|
91
|
+
type media_ExifError = ExifError;
|
|
92
|
+
type media_ImageFormat = ImageFormat;
|
|
93
|
+
type media_ImageInfo = ImageInfo;
|
|
94
|
+
type media_ImageInfoError = ImageInfoError;
|
|
95
|
+
type media_PdfMetadata = PdfMetadata;
|
|
96
|
+
type media_PdfMetadataError = PdfMetadataError;
|
|
97
|
+
type media_WavInfo = WavInfo;
|
|
98
|
+
type media_WavInfoError = WavInfoError;
|
|
99
|
+
declare const media_readExifData: typeof readExifData;
|
|
100
|
+
declare const media_readImageInfo: typeof readImageInfo;
|
|
101
|
+
declare const media_readPdfMetadata: typeof readPdfMetadata;
|
|
102
|
+
declare const media_readWavInfo: typeof readWavInfo;
|
|
103
|
+
declare namespace media {
|
|
104
|
+
export { type media_ExifData as ExifData, type media_ExifError as ExifError, type media_ImageFormat as ImageFormat, type media_ImageInfo as ImageInfo, type media_ImageInfoError as ImageInfoError, type media_PdfMetadata as PdfMetadata, type media_PdfMetadataError as PdfMetadataError, type media_WavInfo as WavInfo, type media_WavInfoError as WavInfoError, media_readExifData as readExifData, media_readImageInfo as readImageInfo, media_readPdfMetadata as readPdfMetadata, media_readWavInfo as readWavInfo };
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
export { type ExifData as E, type ImageFormat as I, type PdfMetadata as P, type WavInfo as W, type ExifError as a, type ImageInfo as b, type ImageInfoError as c, type PdfMetadataError as d, type WavInfoError as e, readImageInfo as f, readPdfMetadata as g, readWavInfo as h, media as m, readExifData as r };
|