patchAttrs.spec.ts 3.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091
  1. import { patchProp } from '../src/patchProp'
  2. import { xlinkNS } from '../src/modules/attrs'
  3. describe('runtime-dom: attrs patching', () => {
  4. test('xlink attributes', () => {
  5. const el = document.createElementNS('http://www.w3.org/2000/svg', 'use')
  6. patchProp(el, 'xlink:href', null, 'a', 'svg')
  7. expect(el.getAttributeNS(xlinkNS, 'href')).toBe('a')
  8. patchProp(el, 'xlink:href', 'a', null, 'svg')
  9. expect(el.getAttributeNS(xlinkNS, 'href')).toBe(null)
  10. })
  11. test('textContent attributes /w svg', () => {
  12. const el = document.createElementNS('http://www.w3.org/2000/svg', 'use')
  13. patchProp(el, 'textContent', null, 'foo', 'svg')
  14. expect(el.attributes.length).toBe(0)
  15. expect(el.innerHTML).toBe('foo')
  16. })
  17. test('boolean attributes', () => {
  18. const el = document.createElement('input')
  19. patchProp(el, 'readonly', null, true)
  20. expect(el.getAttribute('readonly')).toBe('')
  21. patchProp(el, 'readonly', true, false)
  22. expect(el.getAttribute('readonly')).toBe(null)
  23. patchProp(el, 'readonly', false, '')
  24. expect(el.getAttribute('readonly')).toBe('')
  25. patchProp(el, 'readonly', '', 0)
  26. expect(el.getAttribute('readonly')).toBe(null)
  27. patchProp(el, 'readonly', 0, '0')
  28. expect(el.getAttribute('readonly')).toBe('')
  29. patchProp(el, 'readonly', '0', false)
  30. expect(el.getAttribute('readonly')).toBe(null)
  31. patchProp(el, 'readonly', false, 1)
  32. expect(el.getAttribute('readonly')).toBe('')
  33. patchProp(el, 'readonly', 1, undefined)
  34. expect(el.getAttribute('readonly')).toBe(null)
  35. })
  36. test('attributes', () => {
  37. const el = document.createElement('div')
  38. patchProp(el, 'foo', null, 'a')
  39. expect(el.getAttribute('foo')).toBe('a')
  40. patchProp(el, 'foo', 'a', null)
  41. expect(el.getAttribute('foo')).toBe(null)
  42. })
  43. // #949
  44. test('onxxx but non-listener attributes', () => {
  45. const el = document.createElement('div')
  46. patchProp(el, 'onwards', null, 'a')
  47. expect(el.getAttribute('onwards')).toBe('a')
  48. patchProp(el, 'onwards', 'a', null)
  49. expect(el.getAttribute('onwards')).toBe(null)
  50. })
  51. // #10597
  52. test('should allow setting attribute to symbol', () => {
  53. const el = document.createElement('div')
  54. const symbol = Symbol('foo')
  55. patchProp(el, 'foo', null, symbol)
  56. expect(el.getAttribute('foo')).toBe(symbol.toString())
  57. })
  58. // #10598
  59. test('should allow setting value to symbol', () => {
  60. const el = document.createElement('input')
  61. const symbol = Symbol('foo')
  62. patchProp(el, 'value', null, symbol)
  63. expect(el.value).toBe(symbol.toString())
  64. })
  65. // #11177
  66. test('should allow setting value to object, leaving stringification to the element/browser', () => {
  67. // normal behavior
  68. const el = document.createElement('div')
  69. const obj = { toString: () => 'foo' }
  70. patchProp(el, 'data-test', null, obj)
  71. expect(el.dataset.test).toBe('foo')
  72. const el2 = document.createElement('div')
  73. let testvalue: null | typeof obj = null
  74. // simulating a web component that implements its own setAttribute handler
  75. el2.setAttribute = (name, value) => {
  76. testvalue = value
  77. }
  78. patchProp(el2, 'data-test', null, obj)
  79. expect(el2.dataset.test).toBe(undefined)
  80. expect(testvalue).toBe(obj)
  81. })
  82. })