Skip to content

Commit 48ad9fe

Browse files
committed
Merge branch 'master' of github.com:kpdecker/jsdiff
2 parents 94b63ff + d19bb90 commit 48ad9fe

File tree

11 files changed

+228
-208
lines changed

11 files changed

+228
-208
lines changed

README.md

+27-27
Original file line numberDiff line numberDiff line change
@@ -15,56 +15,56 @@ npm install diff --save
1515

1616
## API
1717

18-
* `JsDiff.diffChars(oldStr, newStr[, options])` - diffs two blocks of text, comparing character by character.
18+
* `Diff.diffChars(oldStr, newStr[, options])` - diffs two blocks of text, comparing character by character.
1919

2020
Returns a list of change objects (See below).
2121

2222
Options
2323
* `ignoreCase`: `true` to ignore casing difference. Defaults to `false`.
2424

25-
* `JsDiff.diffWords(oldStr, newStr[, options])` - diffs two blocks of text, comparing word by word, ignoring whitespace.
25+
* `Diff.diffWords(oldStr, newStr[, options])` - diffs two blocks of text, comparing word by word, ignoring whitespace.
2626

2727
Returns a list of change objects (See below).
2828

2929
Options
3030
* `ignoreCase`: Same as in `diffChars`.
3131

32-
* `JsDiff.diffWordsWithSpace(oldStr, newStr[, options])` - diffs two blocks of text, comparing word by word, treating whitespace as significant.
32+
* `Diff.diffWordsWithSpace(oldStr, newStr[, options])` - diffs two blocks of text, comparing word by word, treating whitespace as significant.
3333

3434
Returns a list of change objects (See below).
3535

36-
* `JsDiff.diffLines(oldStr, newStr[, options])` - diffs two blocks of text, comparing line by line.
36+
* `Diff.diffLines(oldStr, newStr[, options])` - diffs two blocks of text, comparing line by line.
3737

3838
Options
3939
* `ignoreWhitespace`: `true` to ignore leading and trailing whitespace. This is the same as `diffTrimmedLines`
4040
* `newlineIsToken`: `true` to treat newline characters as separate tokens. This allows for changes to the newline structure to occur independently of the line content and to be treated as such. In general this is the more human friendly form of `diffLines` and `diffLines` is better suited for patches and other computer friendly output.
4141

4242
Returns a list of change objects (See below).
4343

44-
* `JsDiff.diffTrimmedLines(oldStr, newStr[, options])` - diffs two blocks of text, comparing line by line, ignoring leading and trailing whitespace.
44+
* `Diff.diffTrimmedLines(oldStr, newStr[, options])` - diffs two blocks of text, comparing line by line, ignoring leading and trailing whitespace.
4545

4646
Returns a list of change objects (See below).
4747

48-
* `JsDiff.diffSentences(oldStr, newStr[, options])` - diffs two blocks of text, comparing sentence by sentence.
48+
* `Diff.diffSentences(oldStr, newStr[, options])` - diffs two blocks of text, comparing sentence by sentence.
4949

5050
Returns a list of change objects (See below).
5151

52-
* `JsDiff.diffCss(oldStr, newStr[, options])` - diffs two blocks of text, comparing CSS tokens.
52+
* `Diff.diffCss(oldStr, newStr[, options])` - diffs two blocks of text, comparing CSS tokens.
5353

5454
Returns a list of change objects (See below).
5555

56-
* `JsDiff.diffJson(oldObj, newObj[, options])` - diffs two JSON objects, comparing the fields defined on each. The order of fields, etc does not matter in this comparison.
56+
* `Diff.diffJson(oldObj, newObj[, options])` - diffs two JSON objects, comparing the fields defined on each. The order of fields, etc does not matter in this comparison.
5757

5858
Returns a list of change objects (See below).
5959

60-
* `JsDiff.diffArrays(oldArr, newArr[, options])` - diffs two arrays, comparing each item for strict equality (===).
60+
* `Diff.diffArrays(oldArr, newArr[, options])` - diffs two arrays, comparing each item for strict equality (===).
6161

6262
Options
6363
* `comparator`: `function(left, right)` for custom equality checks
6464

6565
Returns a list of change objects (See below).
6666

67-
* `JsDiff.createTwoFilesPatch(oldFileName, newFileName, oldStr, newStr, oldHeader, newHeader)` - creates a unified diff patch.
67+
* `Diff.createTwoFilesPatch(oldFileName, newFileName, oldStr, newStr, oldHeader, newHeader)` - creates a unified diff patch.
6868

6969
Parameters:
7070
* `oldFileName` : String to be output in the filename section of the patch for the removals
@@ -75,12 +75,12 @@ npm install diff --save
7575
* `newHeader` : Additional information to include in the new file header
7676
* `options` : An object with options. Currently, only `context` is supported and describes how many lines of context should be included.
7777

78-
* `JsDiff.createPatch(fileName, oldStr, newStr, oldHeader, newHeader)` - creates a unified diff patch.
78+
* `Diff.createPatch(fileName, oldStr, newStr, oldHeader, newHeader)` - creates a unified diff patch.
7979

80-
Just like JsDiff.createTwoFilesPatch, but with oldFileName being equal to newFileName.
80+
Just like Diff.createTwoFilesPatch, but with oldFileName being equal to newFileName.
8181

8282

83-
* `JsDiff.structuredPatch(oldFileName, newFileName, oldStr, newStr, oldHeader, newHeader, options)` - returns an object with an array of hunk objects.
83+
* `Diff.structuredPatch(oldFileName, newFileName, oldStr, newStr, oldHeader, newHeader, options)` - returns an object with an array of hunk objects.
8484

8585
This method is similar to createTwoFilesPatch, but returns a data structure
8686
suitable for further processing. Parameters are the same as createTwoFilesPatch. The data structure returned may look like this:
@@ -96,7 +96,7 @@ npm install diff --save
9696
}
9797
```
9898

99-
* `JsDiff.applyPatch(source, patch[, options])` - applies a unified diff patch.
99+
* `Diff.applyPatch(source, patch[, options])` - applies a unified diff patch.
100100

101101
Return a string containing new version of provided data. `patch` may be a string diff or the output from the `parsePatch` or `structuredPatch` methods.
102102

@@ -105,7 +105,7 @@ npm install diff --save
105105
- `fuzzFactor`: Number of lines that are allowed to differ before rejecting a patch. Defaults to 0.
106106
- `compareLine(lineNumber, line, operation, patchContent)`: Callback used to compare to given lines to determine if they should be considered equal when patching. Defaults to strict equality but may be overridden to provide fuzzier comparison. Should return false if the lines should be rejected.
107107

108-
* `JsDiff.applyPatches(patch, options)` - applies one or more patches.
108+
* `Diff.applyPatches(patch, options)` - applies one or more patches.
109109

110110
This method will iterate over the contents of the patch and apply to data provided through callbacks. The general flow for each patch index is:
111111

@@ -114,9 +114,9 @@ npm install diff --save
114114
115115
Once all patches have been applied or an error occurs, the `options.complete(err)` callback is made.
116116
117-
* `JsDiff.parsePatch(diffStr)` - Parses a patch into structured data
117+
* `Diff.parsePatch(diffStr)` - Parses a patch into structured data
118118
119-
Return a JSON object representation of the a patch, suitable for use with the `applyPatch` method. This parses to the same structure returned by `JsDiff.structuredPatch`.
119+
Return a JSON object representation of the a patch, suitable for use with the `applyPatch` method. This parses to the same structure returned by `Diff.structuredPatch`.
120120
121121
* `convertChangesToXML(changes)` - converts a list of changes to a serialized XML format
122122
@@ -138,17 +138,17 @@ Basic example in Node
138138
139139
```js
140140
require('colors');
141-
var jsdiff = require('diff');
141+
const Diff = require('diff');
142142
143-
var one = 'beep boop';
144-
var other = 'beep boob blah';
143+
const one = 'beep boop';
144+
const other = 'beep boob blah';
145145
146-
var diff = jsdiff.diffChars(one, other);
146+
const diff = Diff.diffChars(one, other);
147147
148-
diff.forEach(function(part){
148+
diff.forEach((part) => {
149149
// green for additions, red for deletions
150150
// grey for common parts
151-
var color = part.added ? 'green' :
151+
const color = part.added ? 'green' :
152152
part.removed ? 'red' : 'grey';
153153
process.stderr.write(part.value[color]);
154154
});
@@ -165,19 +165,19 @@ Basic example in a web page
165165
<pre id="display"></pre>
166166
<script src="diff.js"></script>
167167
<script>
168-
var one = 'beep boop',
168+
const one = 'beep boop',
169169
other = 'beep boob blah',
170170
color = '',
171171
span = null;
172172
173-
var diff = JsDiff.diffChars(one, other),
173+
const diff = Diff.diffChars(one, other),
174174
display = document.getElementById('display'),
175175
fragment = document.createDocumentFragment();
176176
177-
diff.forEach(function(part){
177+
diff.forEach((part) => {
178178
// green for additions, red for deletions
179179
// grey for common parts
180-
color = part.added ? 'green' :
180+
const color = part.added ? 'green' :
181181
part.removed ? 'red' : 'grey';
182182
span = document.createElement('span');
183183
span.style.color = color;

examples/node_example.js

+3-3
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
require('colors')
2-
var jsdiff = require('../');
2+
var Diff = require('../');
33

44
var one = 'beep boop';
55
var other = 'beep boob blah';
66

7-
var diff = jsdiff.diffChars(one, other);
7+
var diff = Diff.diffChars(one, other);
88

99
diff.forEach(function(part){
1010
// green for additions, red for deletions
@@ -14,4 +14,4 @@ diff.forEach(function(part){
1414
process.stderr.write(part.value[color]);
1515
});
1616

17-
console.log();
17+
console.log();

examples/web_example.html

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
color = '',
77
span = null;
88

9-
var diff = JsDiff.diffChars(one, other),
9+
var diff = Diff.diffChars(one, other),
1010
display = document.getElementById('display'),
1111
fragment = document.createDocumentFragment();
1212

package.json

+15
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,12 @@
44
"description": "A javascript text diff implementation.",
55
"keywords": [
66
"diff",
7+
"jsdiff",
8+
"compare",
9+
"patch",
10+
"text",
11+
"json",
12+
"css",
713
"javascript"
814
],
915
"maintainers": [
@@ -24,6 +30,15 @@
2430
"main": "./lib/index.js",
2531
"module": "./lib/index.es6.js",
2632
"browser": "./dist/diff.js",
33+
"unpkg": "./dist/diff.js",
34+
"exports": {
35+
".": {
36+
"import": "./lib/index.mjs",
37+
"require": "./lib/index.js"
38+
},
39+
"./package.json": "./package.json",
40+
"./": "./"
41+
},
2742
"scripts": {
2843
"clean": "rm -rf lib/ dist/",
2944
"build:node": "yarn babel --out-dir lib --source-maps=inline src",

rollup.config.js

+9-3
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,16 @@ export default [
88
output: [
99
{
1010
name: 'Diff',
11-
file: pkg.browser,
12-
format: 'umd'
11+
format: 'umd',
12+
file: pkg.browser
1313
},
14-
{ file: pkg.module, format: 'es' }
14+
{
15+
format: 'esm',
16+
file: pkg.module
17+
}, {
18+
format: 'esm',
19+
file: pkg['exports']['.'].import
20+
}
1521
],
1622
plugins: [
1723
babel({

src/diff/word.js

+2-1
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,8 @@ wordDiff.equals = function(left, right) {
3232
return left === right || (this.options.ignoreWhitespace && !reWhitespace.test(left) && !reWhitespace.test(right));
3333
};
3434
wordDiff.tokenize = function(value) {
35-
let tokens = value.split(/(\s+|[()[\]{}'"]|\b)/);
35+
// All whitespace symbols except newline group into one token, each newline - in separate token
36+
let tokens = value.split(/([^\S\r\n]+|[()[\]{}'"\r\n]|\b)/);
3637

3738
// Join the boundary splits that we do not consider to be boundaries. This is primarily the extended Latin character set.
3839
for (let i = 0; i < tokens.length - 1; i++) {

src/patch/create.js

+7-5
Original file line numberDiff line numberDiff line change
@@ -99,12 +99,10 @@ export function structuredPatch(oldFileName, newFileName, oldStr, newStr, oldHea
9999
};
100100
}
101101

102-
export function createTwoFilesPatch(oldFileName, newFileName, oldStr, newStr, oldHeader, newHeader, options) {
103-
const diff = structuredPatch(oldFileName, newFileName, oldStr, newStr, oldHeader, newHeader, options);
104-
102+
export function formatPatch(diff) {
105103
const ret = [];
106-
if (oldFileName == newFileName) {
107-
ret.push('Index: ' + oldFileName);
104+
if (diff.oldFileName == diff.newFileName) {
105+
ret.push('Index: ' + diff.oldFileName);
108106
}
109107
ret.push('===================================================================');
110108
ret.push('--- ' + diff.oldFileName + (typeof diff.oldHeader === 'undefined' ? '' : '\t' + diff.oldHeader));
@@ -123,6 +121,10 @@ export function createTwoFilesPatch(oldFileName, newFileName, oldStr, newStr, ol
123121
return ret.join('\n') + '\n';
124122
}
125123

124+
export function createTwoFilesPatch(oldFileName, newFileName, oldStr, newStr, oldHeader, newHeader, options) {
125+
return formatPatch(structuredPatch(oldFileName, newFileName, oldStr, newStr, oldHeader, newHeader, options));
126+
}
127+
126128
export function createPatch(fileName, oldStr, newStr, oldHeader, newHeader, options) {
127129
return createTwoFilesPatch(fileName, fileName, oldStr, newStr, oldHeader, newHeader, options);
128130
}

style.css

+6
Original file line numberDiff line numberDiff line change
@@ -79,3 +79,9 @@ ins {
7979
height: 99%; /* Hide scroll bar in Firefox */
8080
}
8181
}
82+
83+
// for readability, wrap words in results,
84+
// in case the original text does not have line breaks
85+
#result {
86+
white-space: pre-wrap;
87+
}

test/diff/word.js

+9
Original file line numberDiff line numberDiff line change
@@ -209,6 +209,15 @@ describe('WordDiff', function() {
209209
expect(convertChangesToXML(diffResult)).to.equal('&quot;<ins>word</ins>&quot;');
210210
});
211211

212+
it('should threat newline as separate token (issues #180, #211)', function() {
213+
// #180
214+
const diffResult1 = diffWordsWithSpace('foo\nbar', 'foo\n\n\nbar');
215+
expect(convertChangesToXML(diffResult1)).to.equal('foo\n<ins>\n\n</ins>bar');
216+
// #211
217+
const diffResult2 = diffWordsWithSpace('A\n\nB\n', 'A\nB\n');
218+
expect(convertChangesToXML(diffResult2)).to.equal('A\n<del>\n</del>B\n');
219+
});
220+
212221
it('should perform async operations', function(done) {
213222
diffWordsWithSpace('New Value ', 'New ValueMoreData ', function(err, diffResult) {
214223
expect(convertChangesToXML(diffResult)).to.equal('New<ins> ValueMoreData</ins> <del>Value </del>');

test/patch/create.js

+16-1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import {diffWords} from '../../lib';
2-
import {createPatch, createTwoFilesPatch, structuredPatch} from '../../lib/patch/create';
2+
import {createPatch, createTwoFilesPatch, formatPatch, structuredPatch} from '../../lib/patch/create';
33

44
import {expect} from 'chai';
55

@@ -651,4 +651,19 @@ describe('patch/create', function() {
651651
});
652652
});
653653
});
654+
655+
describe('#formatPatch', function() {
656+
it('should generate a patch string from an input diff', function() {
657+
const res = formatPatch(structuredPatch(
658+
'oldfile', 'newfile',
659+
'line2\nline3\nline4\n', 'line2\nline3\nline5',
660+
'header1', 'header2'
661+
));
662+
expect(res).to.equal(createTwoFilesPatch(
663+
'oldfile', 'newfile',
664+
'line2\nline3\nline4\n', 'line2\nline3\nline5',
665+
'header1', 'header2'
666+
));
667+
});
668+
});
654669
});

0 commit comments

Comments
 (0)