tar-xz 0.1.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.
Files changed (63) hide show
  1. package/LICENSE +165 -0
  2. package/README.md +201 -0
  3. package/lib/browser/create.d.ts +27 -0
  4. package/lib/browser/create.d.ts.map +1 -0
  5. package/lib/browser/create.js +113 -0
  6. package/lib/browser/create.js.map +1 -0
  7. package/lib/browser/extract.d.ts +24 -0
  8. package/lib/browser/extract.d.ts.map +1 -0
  9. package/lib/browser/extract.js +112 -0
  10. package/lib/browser/extract.js.map +1 -0
  11. package/lib/browser/index.d.ts +7 -0
  12. package/lib/browser/index.d.ts.map +1 -0
  13. package/lib/browser/index.js +7 -0
  14. package/lib/browser/index.js.map +1 -0
  15. package/lib/browser/list.d.ts +23 -0
  16. package/lib/browser/list.d.ts.map +1 -0
  17. package/lib/browser/list.js +81 -0
  18. package/lib/browser/list.js.map +1 -0
  19. package/lib/index.browser.d.ts +12 -0
  20. package/lib/index.browser.d.ts.map +1 -0
  21. package/lib/index.browser.js +14 -0
  22. package/lib/index.browser.js.map +1 -0
  23. package/lib/index.d.ts +12 -0
  24. package/lib/index.d.ts.map +1 -0
  25. package/lib/index.js +14 -0
  26. package/lib/index.js.map +1 -0
  27. package/lib/node/create.d.ts +22 -0
  28. package/lib/node/create.d.ts.map +1 -0
  29. package/lib/node/create.js +155 -0
  30. package/lib/node/create.js.map +1 -0
  31. package/lib/node/extract.d.ts +30 -0
  32. package/lib/node/extract.d.ts.map +1 -0
  33. package/lib/node/extract.js +274 -0
  34. package/lib/node/extract.js.map +1 -0
  35. package/lib/node/index.d.ts +7 -0
  36. package/lib/node/index.d.ts.map +1 -0
  37. package/lib/node/index.js +7 -0
  38. package/lib/node/index.js.map +1 -0
  39. package/lib/node/list.d.ts +20 -0
  40. package/lib/node/list.d.ts.map +1 -0
  41. package/lib/node/list.js +115 -0
  42. package/lib/node/list.js.map +1 -0
  43. package/lib/tar/checksum.d.ts +40 -0
  44. package/lib/tar/checksum.d.ts.map +1 -0
  45. package/lib/tar/checksum.js +91 -0
  46. package/lib/tar/checksum.js.map +1 -0
  47. package/lib/tar/format.d.ts +87 -0
  48. package/lib/tar/format.d.ts.map +1 -0
  49. package/lib/tar/format.js +244 -0
  50. package/lib/tar/format.js.map +1 -0
  51. package/lib/tar/index.d.ts +8 -0
  52. package/lib/tar/index.d.ts.map +1 -0
  53. package/lib/tar/index.js +6 -0
  54. package/lib/tar/index.js.map +1 -0
  55. package/lib/tar/pax.d.ts +82 -0
  56. package/lib/tar/pax.d.ts.map +1 -0
  57. package/lib/tar/pax.js +185 -0
  58. package/lib/tar/pax.js.map +1 -0
  59. package/lib/types.d.ts +144 -0
  60. package/lib/types.d.ts.map +1 -0
  61. package/lib/types.js +26 -0
  62. package/lib/types.js.map +1 -0
  63. package/package.json +80 -0
@@ -0,0 +1,87 @@
1
+ /**
2
+ * TAR format parsing and creation (POSIX ustar format)
3
+ *
4
+ * TAR header structure (512 bytes):
5
+ * - name: 100 bytes (file name)
6
+ * - mode: 8 bytes (octal permissions)
7
+ * - uid: 8 bytes (octal user id)
8
+ * - gid: 8 bytes (octal group id)
9
+ * - size: 12 bytes (octal file size)
10
+ * - mtime: 12 bytes (octal modification time)
11
+ * - chksum: 8 bytes (header checksum)
12
+ * - typeflag: 1 byte (entry type)
13
+ * - linkname: 100 bytes (link target)
14
+ * - magic: 6 bytes ("ustar\0")
15
+ * - version: 2 bytes ("00")
16
+ * - uname: 32 bytes (user name)
17
+ * - gname: 32 bytes (group name)
18
+ * - devmajor: 8 bytes (device major)
19
+ * - devminor: 8 bytes (device minor)
20
+ * - prefix: 155 bytes (path prefix for long names)
21
+ * - padding: 12 bytes (unused)
22
+ */
23
+ import type { TarEntry, TarEntryTypeValue } from '../types.js';
24
+ import { calculateChecksum, verifyChecksum } from './checksum.js';
25
+ /** TAR block size */
26
+ export declare const BLOCK_SIZE = 512;
27
+ /**
28
+ * Check if a header block is empty (end of archive marker)
29
+ */
30
+ export declare function isEmptyBlock(block: Uint8Array): boolean;
31
+ /**
32
+ * Check if header has valid USTAR magic
33
+ */
34
+ export declare function isUstarHeader(header: Uint8Array): boolean;
35
+ /**
36
+ * Parse TAR header into entry metadata
37
+ *
38
+ * @param header - 512-byte header block
39
+ * @returns Parsed entry or null if empty block
40
+ * @throws Error if header is invalid
41
+ */
42
+ export declare function parseHeader(header: Uint8Array): TarEntry | null;
43
+ /**
44
+ * Options for creating a TAR header
45
+ */
46
+ export interface CreateHeaderOptions {
47
+ /** File name */
48
+ name: string;
49
+ /** Entry type (default: FILE or DIRECTORY based on trailing slash) */
50
+ type?: TarEntryTypeValue;
51
+ /** File size in bytes (default: 0) */
52
+ size?: number;
53
+ /** File mode (default: 0o644 for files, 0o755 for directories) */
54
+ mode?: number;
55
+ /** User ID (default: 0) */
56
+ uid?: number;
57
+ /** Group ID (default: 0) */
58
+ gid?: number;
59
+ /** Modification time in seconds (default: now) */
60
+ mtime?: number;
61
+ /** User name (default: "") */
62
+ uname?: string;
63
+ /** Group name (default: "") */
64
+ gname?: string;
65
+ /** Link target for symlinks (default: "") */
66
+ linkname?: string;
67
+ }
68
+ /**
69
+ * Create TAR header block
70
+ *
71
+ * @param options - Header options
72
+ * @returns 512-byte header block
73
+ */
74
+ export declare function createHeader(options: CreateHeaderOptions): Uint8Array;
75
+ /**
76
+ * Create padding to align to block boundary
77
+ *
78
+ * @param size - Content size
79
+ * @returns Padding bytes needed (0 to 511)
80
+ */
81
+ export declare function calculatePadding(size: number): number;
82
+ /**
83
+ * Create end-of-archive marker (two empty blocks)
84
+ */
85
+ export declare function createEndOfArchive(): Uint8Array;
86
+ export { calculateChecksum, verifyChecksum };
87
+ //# sourceMappingURL=format.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"format.d.ts","sourceRoot":"","sources":["../../src/tar/format.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAEH,OAAO,KAAK,EAAE,QAAQ,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAE/D,OAAO,EAAE,iBAAiB,EAAc,cAAc,EAAiB,MAAM,eAAe,CAAC;AAE7F,qBAAqB;AACrB,eAAO,MAAM,UAAU,MAAM,CAAC;AA4F9B;;GAEG;AACH,wBAAgB,YAAY,CAAC,KAAK,EAAE,UAAU,GAAG,OAAO,CAOvD;AAED;;GAEG;AACH,wBAAgB,aAAa,CAAC,MAAM,EAAE,UAAU,GAAG,OAAO,CAGzD;AAED;;;;;;GAMG;AACH,wBAAgB,WAAW,CAAC,MAAM,EAAE,UAAU,GAAG,QAAQ,GAAG,IAAI,CA8C/D;AAED;;GAEG;AACH,MAAM,WAAW,mBAAmB;IAClC,gBAAgB;IAChB,IAAI,EAAE,MAAM,CAAC;IACb,sEAAsE;IACtE,IAAI,CAAC,EAAE,iBAAiB,CAAC;IACzB,sCAAsC;IACtC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,kEAAkE;IAClE,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,2BAA2B;IAC3B,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,4BAA4B;IAC5B,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,kDAAkD;IAClD,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,8BAA8B;IAC9B,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,+BAA+B;IAC/B,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,6CAA6C;IAC7C,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED;;;;;GAKG;AACH,wBAAgB,YAAY,CAAC,OAAO,EAAE,mBAAmB,GAAG,UAAU,CAkErE;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAGrD;AAED;;GAEG;AACH,wBAAgB,kBAAkB,IAAI,UAAU,CAE/C;AAED,OAAO,EAAE,iBAAiB,EAAE,cAAc,EAAE,CAAC"}
@@ -0,0 +1,244 @@
1
+ /**
2
+ * TAR format parsing and creation (POSIX ustar format)
3
+ *
4
+ * TAR header structure (512 bytes):
5
+ * - name: 100 bytes (file name)
6
+ * - mode: 8 bytes (octal permissions)
7
+ * - uid: 8 bytes (octal user id)
8
+ * - gid: 8 bytes (octal group id)
9
+ * - size: 12 bytes (octal file size)
10
+ * - mtime: 12 bytes (octal modification time)
11
+ * - chksum: 8 bytes (header checksum)
12
+ * - typeflag: 1 byte (entry type)
13
+ * - linkname: 100 bytes (link target)
14
+ * - magic: 6 bytes ("ustar\0")
15
+ * - version: 2 bytes ("00")
16
+ * - uname: 32 bytes (user name)
17
+ * - gname: 32 bytes (group name)
18
+ * - devmajor: 8 bytes (device major)
19
+ * - devminor: 8 bytes (device minor)
20
+ * - prefix: 155 bytes (path prefix for long names)
21
+ * - padding: 12 bytes (unused)
22
+ */
23
+ import { TarEntryType } from '../types.js';
24
+ import { calculateChecksum, parseOctal, verifyChecksum, writeChecksum } from './checksum.js';
25
+ /** TAR block size */
26
+ export const BLOCK_SIZE = 512;
27
+ /** USTAR magic string */
28
+ const USTAR_MAGIC = 'ustar\0';
29
+ const USTAR_VERSION = '00';
30
+ /** Header field offsets */
31
+ const OFFSETS = {
32
+ name: 0,
33
+ mode: 100,
34
+ uid: 108,
35
+ gid: 116,
36
+ size: 124,
37
+ mtime: 136,
38
+ chksum: 148,
39
+ typeflag: 156,
40
+ linkname: 157,
41
+ magic: 257,
42
+ version: 263,
43
+ uname: 265,
44
+ gname: 297,
45
+ devmajor: 329,
46
+ devminor: 337,
47
+ prefix: 345,
48
+ };
49
+ /** Header field lengths */
50
+ const LENGTHS = {
51
+ name: 100,
52
+ mode: 8,
53
+ uid: 8,
54
+ gid: 8,
55
+ size: 12,
56
+ mtime: 12,
57
+ chksum: 8,
58
+ typeflag: 1,
59
+ linkname: 100,
60
+ magic: 6,
61
+ version: 2,
62
+ uname: 32,
63
+ gname: 32,
64
+ devmajor: 8,
65
+ devminor: 8,
66
+ prefix: 155,
67
+ };
68
+ const textEncoder = new TextEncoder();
69
+ const textDecoder = new TextDecoder('utf-8', { fatal: false });
70
+ /**
71
+ * Parse string from header field (null-terminated or full length)
72
+ */
73
+ function parseString(header, offset, length) {
74
+ let end = offset;
75
+ const limit = offset + length;
76
+ while (end < limit && header[end] !== 0) {
77
+ end++;
78
+ }
79
+ return textDecoder.decode(header.subarray(offset, end));
80
+ }
81
+ /**
82
+ * Write string to header field (null-terminated if fits)
83
+ */
84
+ function writeString(header, offset, length, value) {
85
+ const bytes = textEncoder.encode(value);
86
+ const writeLen = Math.min(bytes.length, length);
87
+ for (let i = 0; i < writeLen; i++) {
88
+ header[offset + i] = bytes[i];
89
+ }
90
+ // Null-terminate if there's room
91
+ if (writeLen < length) {
92
+ header[offset + writeLen] = 0;
93
+ }
94
+ }
95
+ /**
96
+ * Write octal number to header field
97
+ */
98
+ function writeOctal(header, offset, length, value) {
99
+ // Leave room for null terminator
100
+ const octalStr = value.toString(8).padStart(length - 1, '0');
101
+ for (let i = 0; i < length - 1; i++) {
102
+ header[offset + i] = octalStr.charCodeAt(i);
103
+ }
104
+ header[offset + length - 1] = 0; // null terminator
105
+ }
106
+ /**
107
+ * Check if a header block is empty (end of archive marker)
108
+ */
109
+ export function isEmptyBlock(block) {
110
+ for (let i = 0; i < block.length; i++) {
111
+ if (block[i] !== 0) {
112
+ return false;
113
+ }
114
+ }
115
+ return true;
116
+ }
117
+ /**
118
+ * Check if header has valid USTAR magic
119
+ */
120
+ export function isUstarHeader(header) {
121
+ const magic = parseString(header, OFFSETS.magic, LENGTHS.magic);
122
+ return magic === 'ustar' || magic === 'ustar\0';
123
+ }
124
+ /**
125
+ * Parse TAR header into entry metadata
126
+ *
127
+ * @param header - 512-byte header block
128
+ * @returns Parsed entry or null if empty block
129
+ * @throws Error if header is invalid
130
+ */
131
+ export function parseHeader(header) {
132
+ if (header.length !== BLOCK_SIZE) {
133
+ throw new Error(`Invalid header length: ${header.length}`);
134
+ }
135
+ // Check for end-of-archive marker (two empty blocks)
136
+ if (isEmptyBlock(header)) {
137
+ return null;
138
+ }
139
+ // Verify checksum
140
+ if (!verifyChecksum(header)) {
141
+ throw new Error('Invalid TAR header checksum');
142
+ }
143
+ // Parse name (may be split between prefix and name fields)
144
+ let name = parseString(header, OFFSETS.name, LENGTHS.name);
145
+ const prefix = parseString(header, OFFSETS.prefix, LENGTHS.prefix);
146
+ if (prefix.length > 0) {
147
+ name = `${prefix}/${name}`;
148
+ }
149
+ // Parse type flag
150
+ const typeFlagChar = String.fromCharCode(header[OFFSETS.typeflag]);
151
+ // Handle legacy type (null or empty = regular file)
152
+ const type = typeFlagChar === '\0' || typeFlagChar === ''
153
+ ? TarEntryType.FILE
154
+ : typeFlagChar;
155
+ return {
156
+ name,
157
+ type,
158
+ size: parseOctal(header, OFFSETS.size, LENGTHS.size),
159
+ mode: parseOctal(header, OFFSETS.mode, LENGTHS.mode),
160
+ uid: parseOctal(header, OFFSETS.uid, LENGTHS.uid),
161
+ gid: parseOctal(header, OFFSETS.gid, LENGTHS.gid),
162
+ mtime: parseOctal(header, OFFSETS.mtime, LENGTHS.mtime),
163
+ uname: parseString(header, OFFSETS.uname, LENGTHS.uname),
164
+ gname: parseString(header, OFFSETS.gname, LENGTHS.gname),
165
+ devmajor: parseOctal(header, OFFSETS.devmajor, LENGTHS.devmajor),
166
+ devminor: parseOctal(header, OFFSETS.devminor, LENGTHS.devminor),
167
+ linkname: parseString(header, OFFSETS.linkname, LENGTHS.linkname),
168
+ };
169
+ }
170
+ /**
171
+ * Create TAR header block
172
+ *
173
+ * @param options - Header options
174
+ * @returns 512-byte header block
175
+ */
176
+ export function createHeader(options) {
177
+ const header = new Uint8Array(BLOCK_SIZE);
178
+ let { name } = options;
179
+ const isDir = name.endsWith('/');
180
+ // Determine type
181
+ const type = options.type ?? (isDir ? TarEntryType.DIRECTORY : TarEntryType.FILE);
182
+ // Handle long names using prefix field
183
+ let prefix = '';
184
+ if (name.length > LENGTHS.name) {
185
+ // Find a good split point (at a path separator)
186
+ const maxPrefix = LENGTHS.prefix;
187
+ const splitIdx = name.lastIndexOf('/', maxPrefix);
188
+ if (splitIdx > 0 && name.length - splitIdx - 1 <= LENGTHS.name) {
189
+ prefix = name.substring(0, splitIdx);
190
+ name = name.substring(splitIdx + 1);
191
+ }
192
+ else {
193
+ throw new Error(`File name too long for TAR format: ${options.name} (use PAX for names > 255 chars)`);
194
+ }
195
+ }
196
+ // Default mode based on type
197
+ const defaultMode = type === TarEntryType.DIRECTORY ? 0o755 : 0o644;
198
+ const mode = options.mode ?? defaultMode;
199
+ // Default mtime to now
200
+ const mtime = options.mtime ?? Math.floor(Date.now() / 1000);
201
+ // Write fields
202
+ writeString(header, OFFSETS.name, LENGTHS.name, name);
203
+ writeOctal(header, OFFSETS.mode, LENGTHS.mode, mode);
204
+ writeOctal(header, OFFSETS.uid, LENGTHS.uid, options.uid ?? 0);
205
+ writeOctal(header, OFFSETS.gid, LENGTHS.gid, options.gid ?? 0);
206
+ writeOctal(header, OFFSETS.size, LENGTHS.size, options.size ?? 0);
207
+ writeOctal(header, OFFSETS.mtime, LENGTHS.mtime, mtime);
208
+ // Type flag
209
+ header[OFFSETS.typeflag] = type.charCodeAt(0);
210
+ // Link name
211
+ writeString(header, OFFSETS.linkname, LENGTHS.linkname, options.linkname ?? '');
212
+ // USTAR magic and version
213
+ writeString(header, OFFSETS.magic, LENGTHS.magic, USTAR_MAGIC);
214
+ writeString(header, OFFSETS.version, LENGTHS.version, USTAR_VERSION);
215
+ // User/group names
216
+ writeString(header, OFFSETS.uname, LENGTHS.uname, options.uname ?? '');
217
+ writeString(header, OFFSETS.gname, LENGTHS.gname, options.gname ?? '');
218
+ // Device numbers (0 for regular files)
219
+ writeOctal(header, OFFSETS.devmajor, LENGTHS.devmajor, 0);
220
+ writeOctal(header, OFFSETS.devminor, LENGTHS.devminor, 0);
221
+ // Prefix for long names
222
+ writeString(header, OFFSETS.prefix, LENGTHS.prefix, prefix);
223
+ // Calculate and write checksum
224
+ writeChecksum(header);
225
+ return header;
226
+ }
227
+ /**
228
+ * Create padding to align to block boundary
229
+ *
230
+ * @param size - Content size
231
+ * @returns Padding bytes needed (0 to 511)
232
+ */
233
+ export function calculatePadding(size) {
234
+ const remainder = size % BLOCK_SIZE;
235
+ return remainder === 0 ? 0 : BLOCK_SIZE - remainder;
236
+ }
237
+ /**
238
+ * Create end-of-archive marker (two empty blocks)
239
+ */
240
+ export function createEndOfArchive() {
241
+ return new Uint8Array(BLOCK_SIZE * 2);
242
+ }
243
+ export { calculateChecksum, verifyChecksum };
244
+ //# sourceMappingURL=format.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"format.js","sourceRoot":"","sources":["../../src/tar/format.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,8 @@
1
+ /**
2
+ * TAR format utilities
3
+ */
4
+ export type { CreateHeaderOptions } from './format.js';
5
+ export { BLOCK_SIZE, calculateChecksum, calculatePadding, createEndOfArchive, createHeader, isEmptyBlock, isUstarHeader, parseHeader, verifyChecksum, } from './format.js';
6
+ export type { PaxAttributes } from './pax.js';
7
+ export { applyPaxAttributes, createPaxData, createPaxHeaderBlocks, needsPaxHeaders, parsePaxData, } from './pax.js';
8
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/tar/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,YAAY,EAAE,mBAAmB,EAAE,MAAM,aAAa,CAAC;AACvD,OAAO,EACL,UAAU,EACV,iBAAiB,EACjB,gBAAgB,EAChB,kBAAkB,EAClB,YAAY,EACZ,YAAY,EACZ,aAAa,EACb,WAAW,EACX,cAAc,GACf,MAAM,aAAa,CAAC;AACrB,YAAY,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AAC9C,OAAO,EACL,kBAAkB,EAClB,aAAa,EACb,qBAAqB,EACrB,eAAe,EACf,YAAY,GACb,MAAM,UAAU,CAAC"}
@@ -0,0 +1,6 @@
1
+ /**
2
+ * TAR format utilities
3
+ */
4
+ export { BLOCK_SIZE, calculateChecksum, calculatePadding, createEndOfArchive, createHeader, isEmptyBlock, isUstarHeader, parseHeader, verifyChecksum, } from './format.js';
5
+ export { applyPaxAttributes, createPaxData, createPaxHeaderBlocks, needsPaxHeaders, parsePaxData, } from './pax.js';
6
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/tar/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAGH,OAAO,EACL,UAAU,EACV,iBAAiB,EACjB,gBAAgB,EAChB,kBAAkB,EAClB,YAAY,EACZ,YAAY,EACZ,aAAa,EACb,WAAW,EACX,cAAc,GACf,MAAM,aAAa,CAAC;AAErB,OAAO,EACL,kBAAkB,EAClB,aAAa,EACb,qBAAqB,EACrB,eAAe,EACf,YAAY,GACb,MAAM,UAAU,CAAC"}
@@ -0,0 +1,82 @@
1
+ /**
2
+ * PAX extended headers support
3
+ *
4
+ * PAX (Portable Archive eXchange) format allows:
5
+ * - Unlimited file name length
6
+ * - Unlimited link name length
7
+ * - Large file sizes (> 8GB)
8
+ * - Extended attributes
9
+ *
10
+ * PAX records format: "%d %s=%s\n" (length key=value\n)
11
+ * where length includes the length field itself, space, and newline.
12
+ */
13
+ import type { TarEntry } from '../types.js';
14
+ /**
15
+ * PAX extended header attributes
16
+ */
17
+ export interface PaxAttributes {
18
+ /** File path (overrides header name) */
19
+ path?: string;
20
+ /** Link path (overrides header linkname) */
21
+ linkpath?: string;
22
+ /** File size (for large files > 8GB) */
23
+ size?: number;
24
+ /** Modification time with sub-second precision */
25
+ mtime?: number;
26
+ /** Access time */
27
+ atime?: number;
28
+ /** Creation time */
29
+ ctime?: number;
30
+ /** User ID (for large UIDs) */
31
+ uid?: number;
32
+ /** Group ID (for large GIDs) */
33
+ gid?: number;
34
+ /** User name (longer than 32 chars) */
35
+ uname?: string;
36
+ /** Group name (longer than 32 chars) */
37
+ gname?: string;
38
+ /** Additional custom attributes */
39
+ [key: string]: string | number | undefined;
40
+ }
41
+ /**
42
+ * Create PAX extended header data
43
+ *
44
+ * @param attrs - PAX attributes to encode
45
+ * @returns Encoded PAX data as Uint8Array
46
+ */
47
+ export declare function createPaxData(attrs: PaxAttributes): Uint8Array;
48
+ /**
49
+ * Parse PAX extended header data
50
+ *
51
+ * @param data - PAX data bytes
52
+ * @returns Parsed attributes
53
+ */
54
+ export declare function parsePaxData(data: Uint8Array): PaxAttributes;
55
+ /**
56
+ * Check if an entry needs PAX headers
57
+ *
58
+ * @param entry - Entry to check
59
+ * @returns true if PAX headers are needed
60
+ */
61
+ export declare function needsPaxHeaders(entry: {
62
+ name: string;
63
+ linkname?: string;
64
+ size?: number;
65
+ }): boolean;
66
+ /**
67
+ * Create PAX extended header blocks
68
+ *
69
+ * @param originalName - Original file name (used to generate header name)
70
+ * @param attrs - PAX attributes
71
+ * @returns Array of blocks (header + data + padding)
72
+ */
73
+ export declare function createPaxHeaderBlocks(originalName: string, attrs: PaxAttributes): Uint8Array[];
74
+ /**
75
+ * Apply PAX attributes to an entry
76
+ *
77
+ * @param entry - Original entry
78
+ * @param attrs - PAX attributes to apply
79
+ * @returns Modified entry
80
+ */
81
+ export declare function applyPaxAttributes(entry: TarEntry, attrs: PaxAttributes): TarEntry;
82
+ //# sourceMappingURL=pax.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"pax.d.ts","sourceRoot":"","sources":["../../src/tar/pax.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAO5C;;GAEG;AACH,MAAM,WAAW,aAAa;IAC5B,wCAAwC;IACxC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,4CAA4C;IAC5C,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,wCAAwC;IACxC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,kDAAkD;IAClD,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,kBAAkB;IAClB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,oBAAoB;IACpB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,+BAA+B;IAC/B,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,gCAAgC;IAChC,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,uCAAuC;IACvC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,wCAAwC;IACxC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,mCAAmC;IACnC,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,GAAG,MAAM,GAAG,SAAS,CAAC;CAC5C;AAwBD;;;;;GAKG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,aAAa,GAAG,UAAU,CAa9D;AAED;;;;;GAKG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,UAAU,GAAG,aAAa,CAkD5D;AAED;;;;;GAKG;AACH,wBAAgB,eAAe,CAAC,KAAK,EAAE;IACrC,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf,GAAG,OAAO,CAiBV;AAED;;;;;;GAMG;AACH,wBAAgB,qBAAqB,CAAC,YAAY,EAAE,MAAM,EAAE,KAAK,EAAE,aAAa,GAAG,UAAU,EAAE,CAyB9F;AAED;;;;;;GAMG;AACH,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,QAAQ,EAAE,KAAK,EAAE,aAAa,GAAG,QAAQ,CA6BlF"}
package/lib/tar/pax.js ADDED
@@ -0,0 +1,185 @@
1
+ /**
2
+ * PAX extended headers support
3
+ *
4
+ * PAX (Portable Archive eXchange) format allows:
5
+ * - Unlimited file name length
6
+ * - Unlimited link name length
7
+ * - Large file sizes (> 8GB)
8
+ * - Extended attributes
9
+ *
10
+ * PAX records format: "%d %s=%s\n" (length key=value\n)
11
+ * where length includes the length field itself, space, and newline.
12
+ */
13
+ import { TarEntryType } from '../types.js';
14
+ import { calculatePadding, createHeader } from './format.js';
15
+ const textEncoder = new TextEncoder();
16
+ const textDecoder = new TextDecoder('utf-8', { fatal: false });
17
+ /**
18
+ * Create a PAX record for a key-value pair
19
+ *
20
+ * Format: "%d %s=%s\n" where %d is the total length including itself
21
+ */
22
+ function createPaxRecord(key, value) {
23
+ const content = ` ${key}=${value}\n`;
24
+ // Calculate length: we need to account for the length field itself
25
+ // Start with an estimate, then adjust
26
+ let lengthStr = content.length.toString();
27
+ let totalLength = lengthStr.length + content.length;
28
+ // Recalculate if adding digits changed the length
29
+ while (totalLength.toString().length !== lengthStr.length) {
30
+ lengthStr = totalLength.toString();
31
+ totalLength = lengthStr.length + content.length;
32
+ }
33
+ return `${totalLength}${content}`;
34
+ }
35
+ /**
36
+ * Create PAX extended header data
37
+ *
38
+ * @param attrs - PAX attributes to encode
39
+ * @returns Encoded PAX data as Uint8Array
40
+ */
41
+ export function createPaxData(attrs) {
42
+ let data = '';
43
+ for (const [key, value] of Object.entries(attrs)) {
44
+ if (value === undefined) {
45
+ continue;
46
+ }
47
+ const strValue = typeof value === 'number' ? value.toString() : value;
48
+ data += createPaxRecord(key, strValue);
49
+ }
50
+ return textEncoder.encode(data);
51
+ }
52
+ /**
53
+ * Parse PAX extended header data
54
+ *
55
+ * @param data - PAX data bytes
56
+ * @returns Parsed attributes
57
+ */
58
+ export function parsePaxData(data) {
59
+ const text = textDecoder.decode(data);
60
+ const attrs = {};
61
+ let pos = 0;
62
+ while (pos < text.length) {
63
+ // Find the space after length
64
+ const spaceIdx = text.indexOf(' ', pos);
65
+ if (spaceIdx === -1) {
66
+ break;
67
+ }
68
+ const length = Number.parseInt(text.substring(pos, spaceIdx), 10);
69
+ if (Number.isNaN(length) || length <= 0) {
70
+ break;
71
+ }
72
+ // Extract the record (length includes the length field and newline)
73
+ const record = text.substring(pos, pos + length);
74
+ const newlineIdx = record.indexOf('\n');
75
+ if (newlineIdx === -1) {
76
+ break;
77
+ }
78
+ // Parse key=value (after the "length " prefix)
79
+ const content = record.substring(spaceIdx - pos + 1, newlineIdx);
80
+ const eqIdx = content.indexOf('=');
81
+ if (eqIdx !== -1) {
82
+ const key = content.substring(0, eqIdx);
83
+ const value = content.substring(eqIdx + 1);
84
+ // Convert numeric fields
85
+ if (key === 'size' ||
86
+ key === 'uid' ||
87
+ key === 'gid' ||
88
+ key === 'mtime' ||
89
+ key === 'atime' ||
90
+ key === 'ctime') {
91
+ attrs[key] = Number.parseFloat(value);
92
+ }
93
+ else {
94
+ attrs[key] = value;
95
+ }
96
+ }
97
+ pos += length;
98
+ }
99
+ return attrs;
100
+ }
101
+ /**
102
+ * Check if an entry needs PAX headers
103
+ *
104
+ * @param entry - Entry to check
105
+ * @returns true if PAX headers are needed
106
+ */
107
+ export function needsPaxHeaders(entry) {
108
+ // Name too long for ustar (100 chars name + 155 chars prefix)
109
+ if (entry.name.length > 255) {
110
+ return true;
111
+ }
112
+ // Link name too long
113
+ if (entry.linkname && entry.linkname.length > 100) {
114
+ return true;
115
+ }
116
+ // File size too large for 11-digit octal (> 8GB)
117
+ if (entry.size !== undefined && entry.size > 0o77777777777) {
118
+ return true;
119
+ }
120
+ return false;
121
+ }
122
+ /**
123
+ * Create PAX extended header blocks
124
+ *
125
+ * @param originalName - Original file name (used to generate header name)
126
+ * @param attrs - PAX attributes
127
+ * @returns Array of blocks (header + data + padding)
128
+ */
129
+ export function createPaxHeaderBlocks(originalName, attrs) {
130
+ const data = createPaxData(attrs);
131
+ const blocks = [];
132
+ // Create header for PAX data
133
+ // Use a shortened version of the original name for the PAX header entry
134
+ const paxName = `PaxHeader/${originalName.substring(0, 80)}`;
135
+ const header = createHeader({
136
+ name: paxName,
137
+ type: TarEntryType.PAX_HEADER,
138
+ size: data.length,
139
+ mode: 0o644,
140
+ });
141
+ blocks.push(header);
142
+ blocks.push(data);
143
+ // Add padding to align to block boundary
144
+ const padding = calculatePadding(data.length);
145
+ if (padding > 0) {
146
+ blocks.push(new Uint8Array(padding));
147
+ }
148
+ return blocks;
149
+ }
150
+ /**
151
+ * Apply PAX attributes to an entry
152
+ *
153
+ * @param entry - Original entry
154
+ * @param attrs - PAX attributes to apply
155
+ * @returns Modified entry
156
+ */
157
+ export function applyPaxAttributes(entry, attrs) {
158
+ const result = { ...entry };
159
+ if (attrs.path !== undefined) {
160
+ result.name = attrs.path;
161
+ }
162
+ if (attrs.linkpath !== undefined) {
163
+ result.linkname = attrs.linkpath;
164
+ }
165
+ if (attrs.size !== undefined) {
166
+ result.size = attrs.size;
167
+ }
168
+ if (attrs.mtime !== undefined) {
169
+ result.mtime = Math.floor(attrs.mtime);
170
+ }
171
+ if (attrs.uid !== undefined) {
172
+ result.uid = attrs.uid;
173
+ }
174
+ if (attrs.gid !== undefined) {
175
+ result.gid = attrs.gid;
176
+ }
177
+ if (attrs.uname !== undefined) {
178
+ result.uname = attrs.uname;
179
+ }
180
+ if (attrs.gname !== undefined) {
181
+ result.gname = attrs.gname;
182
+ }
183
+ return result;
184
+ }
185
+ //# sourceMappingURL=pax.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"pax.js","sourceRoot":"","sources":["../../src/tar/pax.ts"],"names":[],"mappings":"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"}