question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

didInsert called with null node.el when mount() is followed by immediate redraw()

See original GitHub issue

Hi,

I’m seeing didInsert being called twice - once with the node and once without. So you can effectively ignore the faulty one (it IS faulty and a bug, right?) by simply doing “if (!node) return”

I have an Dashboard view with Chart views. The chart views have didInsert hooks that are called twice.

Something like this:

var insert_counter = 1 // didInsert counter - is called 6 times
var nodes_counter = 1 // didInsert with valid node's - called 3 times

function Chart (vm, opts) {
  function didInsert (node) {
    console.log("counter: " + insert_counter++)
    if (!node) return
    console.log("valid nodes counter: " + nodes_counter++)
  }
  return ['div.chart',
    ['canvas', {_hooks: {didInsert: didInsert}}]
  ]
}

function Dashboard (vm, store) {
  return function () {
    ['div.dashboard',
      ['div', [Chart, opts]],
      ['div', [Chart, opts]],
      ['div', [Chart, opts]]
    ]
  }
}

Issue Analytics

  • State:closed
  • Created 7 years ago
  • Comments:22 (10 by maintainers)

github_iconTop GitHub Comments

1reaction
lawrence-dolcommented, May 17, 2016

I’m not convinced there’s a fundamental need for re-work here

Nor am I. I was just hoping to shed more light on the general problem in case it was helpful. It does not affect me, since I am already deferring and coalescing redraws, and any user of DOMVM can do the same in a few lines of code. But, just in case more things like this come out of the woodwork, I thought this might be useful information.

1reaction
leeoniyacommented, May 14, 2016

So turns out this is a bit of a thorny issue. Here are some details.

vm.redraw is debounced/coalesced so if you call it 20 times within the same requestAnimationFrame, it will only fire the last invocation on the tail end of the frame. In addition, did* hook firing is delayed by 1-2 frames to ensure that the created DOM elements are “live” and are useful to you.

What’s happening here is that the queue is filled with the callbacks and current nodes/args via the implicit redraw() as part of mount(), but the did* hooks don’t fire until the next frame. If you call another redraw() before the queue is drained, those nodes in the queue become stale because they are regenerated on each redraw and the el transferred/recycled to the new vnodes. So when the hooks do fire, you’re getting stale nodes that should be garbage collected.

What I’m gonna do is have domvm queue any redraw() calls if the didHooks queue is non-empty to prevent node replacement/recycling prior to hook invocation. Since the didHooks queue (and now pendRedraws queue) is global and cannot really be contained to a specific view, the solution is not a general one and may cause odd interactions in cases of significant complexity or asynchronicity WRT implicit sub-sub-subview redraw containing deep did* hooks cases. But it should cover multiple common cases such as explicit view redraw like the one here.

Read more comments on GitHub >

github_iconTop Results From Across the Web

The Component Lifecycle - Ember Guides
Ember guarantees that, by the time didInsertElement() is called: The component's element has been both created and inserted into the DOM.
Read more >
ember_guides_combined - gists · GitHub
Welcome to Ember.js! This guide will take you through creating a simple application using Ember.js and briefly explain the core concepts behind the...
Read more >
Scenekit move node - Caritas Castellaneta
SceneKit itself uses a scene-graph model, in which nodes are positioned ... Jun 27, 2018 · The didAdd() is called whenever a new...
Read more >
The domvm from domvm - GithubHelp
Rendering a view to the DOM is called mounting. ... You can access any view's parent view via vm.parent() and the great granddaddy...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found