Skip to content

Commit 21fbd03

Browse files
committed
fix(@angular-devkit/schematics): add support for BOM to UpdateRecorder
Fixes angular/angular-cli#10644
1 parent fe12251 commit 21fbd03

File tree

3 files changed

+82
-1
lines changed

3 files changed

+82
-1
lines changed

packages/angular_devkit/schematics/src/tree/recorder.ts

+36
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,23 @@ export class UpdateRecorderBase implements UpdateRecorder {
2121
this._path = entry.path;
2222
}
2323

24+
static createFromFileEntry(entry: FileEntry): UpdateRecorder {
25+
const c0 = entry.content.readInt8(0, true);
26+
const c1 = entry.content.readInt8(1, true);
27+
const c2 = entry.content.readInt8(2), true;
28+
29+
// Check if we're BOM.
30+
if (c0 === 0xEF && c1 === 0xBF && c2 === 0xBE) {
31+
return new UpdateRecorderBom(entry);
32+
} else if (c0 === 0xFF && c1 == 0xFE) {
33+
return new UpdateRecorderBom(entry, 2);
34+
} else if (c0 === 0xFE && c1 == 0xFF) {
35+
return new UpdateRecorderBom(entry, 2);
36+
}
37+
38+
return new UpdateRecorderBase(entry);
39+
}
40+
2441
get path() { return this._path; }
2542

2643
// These just record changes.
@@ -50,3 +67,22 @@ export class UpdateRecorderBase implements UpdateRecorder {
5067
return this._content.generate();
5168
}
5269
}
70+
71+
72+
export class UpdateRecorderBom extends UpdateRecorderBase {
73+
constructor(entry: FileEntry, private _delta = 3) {
74+
super(entry);
75+
}
76+
77+
insertLeft(index: number, content: Buffer | string) {
78+
return super.insertLeft(index + this._delta, content);
79+
}
80+
81+
insertRight(index: number, content: Buffer | string) {
82+
return super.insertRight(index + this._delta, content);
83+
}
84+
85+
remove(index: number, length: number) {
86+
return super.remove(index + this._delta, length);
87+
}
88+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
/**
2+
* @license
3+
* Copyright Google Inc. All Rights Reserved.
4+
*
5+
* Use of this source code is governed by an MIT-style license that can be
6+
* found in the LICENSE file at https://angular.io/license
7+
*/
8+
import { normalize } from '@angular-devkit/core';
9+
import { SimpleFileEntry } from './entry';
10+
import { UpdateRecorderBase, UpdateRecorderBom } from './recorder';
11+
12+
13+
describe('UpdateRecorderBase', () => {
14+
it('works for simple files', () => {
15+
const buffer = new Buffer('Hello World');
16+
const entry = new SimpleFileEntry(normalize('/some/path'), buffer);
17+
18+
const recorder = new UpdateRecorderBase(entry);
19+
recorder.insertLeft(5, ' beautiful');
20+
const result = recorder.apply(buffer);
21+
expect(result.toString()).toBe('Hello beautiful World');
22+
});
23+
24+
it('works for simple files (2)', () => {
25+
const buffer = new Buffer('Hello World');
26+
const entry = new SimpleFileEntry(normalize('/some/path'), buffer);
27+
28+
const recorder = new UpdateRecorderBase(entry);
29+
recorder.insertRight(5, ' beautiful');
30+
const result = recorder.apply(buffer);
31+
expect(result.toString()).toBe('Hello beautiful World');
32+
});
33+
});
34+
35+
describe('UpdateRecorderBom', () => {
36+
it('works for simple files', () => {
37+
const buffer = new Buffer('\uFEFFHello World');
38+
const entry = new SimpleFileEntry(normalize('/some/path'), buffer);
39+
40+
const recorder = new UpdateRecorderBom(entry);
41+
recorder.insertLeft(5, ' beautiful');
42+
const result = recorder.apply(buffer);
43+
expect(result.toString()).toBe('\uFEFFHello beautiful World');
44+
});
45+
});

packages/angular_devkit/schematics/src/tree/virtual.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -186,7 +186,7 @@ export class VirtualTree implements Tree {
186186
throw new FileDoesNotExistException(path);
187187
}
188188

189-
return new UpdateRecorderBase(entry);
189+
return UpdateRecorderBase.createFromFileEntry(entry);
190190
}
191191

192192
commitUpdate(record: UpdateRecorder) {

0 commit comments

Comments
 (0)