diff --git a/src/api/attributes.spec.ts b/src/api/attributes.spec.ts
index 5b97d8ab63..959ad3a6e2 100644
--- a/src/api/attributes.spec.ts
+++ b/src/api/attributes.spec.ts
@@ -797,6 +797,22 @@ describe('$(...)', () => {
expect($text('body').html()).toBe(mixedText);
});
+
+ it('(KEY) : should be case-insensitive in HTML mode', () => {
+ const $html = load('
');
+ $html('div').removeAttr('CLASS');
+ expect($html('div').attr('class')).toBeUndefined();
+ });
+
+ it('(KEY) : should remain case-sensitive in XML mode', () => {
+ const $xml = load('', { xmlMode: true });
+ // A differently-cased name must not remove the attribute in XML mode.
+ $xml('Foo').removeAttr('BAR');
+ expect($xml('Foo').attr('Bar')).toBe('x');
+ // The exact name still removes it.
+ $xml('Foo').removeAttr('Bar');
+ expect($xml('Foo').attr('Bar')).toBeUndefined();
+ });
});
describe('.hasClass', () => {
diff --git a/src/api/attributes.ts b/src/api/attributes.ts
index dbd46dad9e..5529527c8d 100644
--- a/src/api/attributes.ts
+++ b/src/api/attributes.ts
@@ -880,8 +880,10 @@ export function removeAttr(
const attrNames = splitNames(name);
for (const attrName of attrNames) {
+ // HTML attribute names are case-insensitive; XML mode preserves case.
+ const lookup = this.options.xmlMode ? attrName : attrName.toLowerCase();
domEach(this, (elem) => {
- if (isTag(elem)) removeAttribute(elem, attrName);
+ if (isTag(elem)) removeAttribute(elem, lookup);
});
}