Sort attributes before applying the diff - fixes #3402
This commit is contained in:
parent
c4a25637d6
commit
da8f825d42
@ -625,21 +625,30 @@ angular.module('OpenSlidesApp.motions.diff', ['OpenSlidesApp.motions.lineNumberi
|
||||
*/
|
||||
this._normalizeHtmlForDiff = function (html) {
|
||||
// Convert all HTML tags to uppercase, but leave the values of attributes unchanged
|
||||
// All attributes and CSS class names are sorted alphabetically
|
||||
html = html.replace(/<(\/?[a-z]*)( [^>]*)?>/ig, function (html, tag, attributes) {
|
||||
var tagNormalized = tag.toUpperCase();
|
||||
if (attributes === undefined) {
|
||||
attributes = "";
|
||||
}
|
||||
attributes = attributes.replace(/( [^"'=]*)(= *((["'])(.*?)\4))?/gi, function (attr, attrName, attrRest, attrRest2, quot, attrValue) {
|
||||
var attrNormalized = attrName.toUpperCase();
|
||||
if (attrRest !== undefined) {
|
||||
var attributesList = [],
|
||||
attributesMatcher = /( [^"'=]*)(= *((["'])(.*?)\4))?/gi,
|
||||
match;
|
||||
do {
|
||||
match = attributesMatcher.exec(attributes);
|
||||
if (match) {
|
||||
var attrNormalized = match[1].toUpperCase(),
|
||||
attrValue = match[5];
|
||||
if (match[2] !== undefined) {
|
||||
if (attrNormalized === ' CLASS') {
|
||||
attrValue = attrValue.split(' ').sort().join(' ');
|
||||
}
|
||||
attrNormalized += "=" + quot + attrValue + quot;
|
||||
attrNormalized += "=" + match[4] + attrValue + match[4];
|
||||
}
|
||||
return attrNormalized;
|
||||
});
|
||||
attributesList.push(attrNormalized);
|
||||
}
|
||||
} while (match);
|
||||
attributes = attributesList.sort().join('');
|
||||
return "<" + tagNormalized + attributes + ">";
|
||||
});
|
||||
|
||||
|
@ -5,10 +5,10 @@ describe('linenumbering', function () {
|
||||
var diffService, baseHtml1, baseHtmlDom1, baseHtml2, baseHtmlDom2, baseHtml3, baseHtmlDom3,
|
||||
brMarkup = function (no) {
|
||||
return '<br class="os-line-break">' +
|
||||
'<span class="line-number-' + no + ' os-line-number" data-line-number="' + no + '" contenteditable="false"> </span>';
|
||||
'<span class="line-number-' + no + ' os-line-number" contenteditable="false" data-line-number="' + no + '"> </span>';
|
||||
},
|
||||
noMarkup = function (no) {
|
||||
return '<span class="line-number-' + no + ' os-line-number" data-line-number="' + no + '" contenteditable="false"> </span>';
|
||||
return '<span class="line-number-' + no + ' os-line-number" contenteditable="false" data-line-number="' + no + '"> </span>';
|
||||
};
|
||||
|
||||
beforeEach(inject(function (_diffService_, _lineNumberingService_) {
|
||||
@ -374,12 +374,12 @@ describe('linenumbering', function () {
|
||||
expect(normalized).toBe('The <STRONG>brown</STRONG> fox')
|
||||
});
|
||||
|
||||
it('uppercases the names of html attributes, but not the values', function () {
|
||||
it('uppercases the names of html attributes, but not the values, and sort the attributes', function () {
|
||||
var unnormalized = 'This is our cool <a href="https://www.openslides.de/">home page</a> - have a look! ' +
|
||||
'<input type="checkbox" checked title=\'A title with "s\'>',
|
||||
normalized = diffService._normalizeHtmlForDiff(unnormalized);
|
||||
expect(normalized).toBe('This is our cool <A HREF="https://www.openslides.de/">home page</A> - have a look! ' +
|
||||
'<INPUT TYPE="checkbox" CHECKED TITLE=\'A title with "s\'>')
|
||||
'<INPUT CHECKED TITLE=\'A title with "s\' TYPE="checkbox">')
|
||||
});
|
||||
|
||||
it('strips unnecessary spaces', function () {
|
||||
@ -569,6 +569,14 @@ describe('linenumbering', function () {
|
||||
|
||||
expect(diff).toBe('<p>tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd <del>gubergren </del>bla, no sea takimata sanctus est Lorem ipsum dolor <ins>gubergren </ins>sit amet.</p>');
|
||||
});
|
||||
|
||||
it('works with style-tags in spans', function () {
|
||||
var before = '<p class="os-split-before os-split-after"><span class="os-line-number line-number-4" data-line-number="4" contenteditable="false"> </span><span style="color: #0000ff;" class="os-split-before os-split-after">sanctus est Lorem ipsum dolor sit amet. Lorem ipsum dolor sit amet, consetetur sadipscing </span></p>',
|
||||
after = '<p class="os-split-after os-split-before"><span class="os-split-after os-split-before" style="color: #0000ff;">sanctus est Lorem ipsum dolor sit amet. Test Lorem ipsum dolor sit amet, consetetur sadipscing </span></p>';
|
||||
var diff = diffService.diff(before, after);
|
||||
|
||||
expect(diff).toBe('<p class="os-split-after os-split-before"><span class="line-number-4 os-line-number" contenteditable="false" data-line-number="4"> </span><span class="os-split-after os-split-before" style="color: #0000ff;">sanctus est Lorem ipsum dolor sit amet. <ins>Test </ins>Lorem ipsum dolor sit amet, consetetur sadipscing </span></p>');
|
||||
});
|
||||
});
|
||||
|
||||
describe('ignoring line numbers', function () {
|
||||
|
Loading…
Reference in New Issue
Block a user