mirror of https://github.com/vuejs/core.git
fix(custom-element): set prop runs pending mutations before disconnect (#13897)
close #13315
This commit is contained in:
parent
e388f1a09f
commit
c4a88cdd0d
|
@ -223,6 +223,31 @@ describe('defineCustomElement', () => {
|
|||
expect(e.getAttribute('baz-qux')).toBe('four')
|
||||
})
|
||||
|
||||
test('props via attributes and properties changed together', async () => {
|
||||
const e = new E()
|
||||
e.foo = 'foo1'
|
||||
e.bar = { x: 'bar1' }
|
||||
container.appendChild(e)
|
||||
await nextTick()
|
||||
expect(e.shadowRoot!.innerHTML).toBe('<div>foo1</div><div>bar1</div>')
|
||||
|
||||
// change attr then property
|
||||
e.setAttribute('foo', 'foo2')
|
||||
e.bar = { x: 'bar2' }
|
||||
await nextTick()
|
||||
expect(e.shadowRoot!.innerHTML).toBe('<div>foo2</div><div>bar2</div>')
|
||||
expect(e.getAttribute('foo')).toBe('foo2')
|
||||
expect(e.hasAttribute('bar')).toBe(false)
|
||||
|
||||
// change prop then attr
|
||||
e.bar = { x: 'bar3' }
|
||||
e.setAttribute('foo', 'foo3')
|
||||
await nextTick()
|
||||
expect(e.shadowRoot!.innerHTML).toBe('<div>foo3</div><div>bar3</div>')
|
||||
expect(e.getAttribute('foo')).toBe('foo3')
|
||||
expect(e.hasAttribute('bar')).toBe(false)
|
||||
})
|
||||
|
||||
test('props via hyphen property', async () => {
|
||||
const Comp = defineCustomElement({
|
||||
props: {
|
||||
|
|
|
@ -346,6 +346,12 @@ export class VueElement
|
|||
})
|
||||
}
|
||||
|
||||
private _processMutations(mutations: MutationRecord[]) {
|
||||
for (const m of mutations) {
|
||||
this._setAttr(m.attributeName!)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* resolve inner component definition (handle possible async component)
|
||||
*/
|
||||
|
@ -360,11 +366,7 @@ export class VueElement
|
|||
}
|
||||
|
||||
// watch future attr changes
|
||||
this._ob = new MutationObserver(mutations => {
|
||||
for (const m of mutations) {
|
||||
this._setAttr(m.attributeName!)
|
||||
}
|
||||
})
|
||||
this._ob = new MutationObserver(this._processMutations.bind(this))
|
||||
|
||||
this._ob.observe(this, { attributes: true })
|
||||
|
||||
|
@ -514,7 +516,10 @@ export class VueElement
|
|||
// reflect
|
||||
if (shouldReflect) {
|
||||
const ob = this._ob
|
||||
ob && ob.disconnect()
|
||||
if (ob) {
|
||||
this._processMutations(ob.takeRecords())
|
||||
ob.disconnect()
|
||||
}
|
||||
if (val === true) {
|
||||
this.setAttribute(hyphenate(key), '')
|
||||
} else if (typeof val === 'string' || typeof val === 'number') {
|
||||
|
|
Loading…
Reference in New Issue