Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Code snippet hmr, fix #1309 #1316

Closed
wants to merge 11 commits into from

Conversation

shigma
Copy link
Collaborator

@shigma shigma commented Feb 19, 2019

Summary

What kind of change does this PR introduce? (check at least one)

  • Bugfix
  • Feature
  • Code style update
  • Refactor
  • Docs
  • Build-related changes
  • Other, please describe:

If changing the UI of default theme, please provide the before/after screenshot:

Does this PR introduce a breaking change? (check one)

  • Yes
  • No

If yes, please describe the impact and migration path for existing applications:

The PR fulfills these requirements:

  • When resolving a specific issue, it's referenced in the PR's title (e.g. fix #xxx[,#xxx], where "xxx" is the issue number)

You have tested in the following browsers: (Providing a detailed version will be better.)

  • Chrome
  • Firefox
  • Safari
  • Edge
  • IE

If adding a new feature, the PR's description includes:

  • A convincing reason for adding this feature
  • Related documents have been updated
  • Related tests have been updated

To avoid wasting your time, it's best to open a feature request issue first and wait for approval before working on it.

Other information:

@shigma
Copy link
Collaborator Author

shigma commented Feb 19, 2019

Something to be discussed before merge

We use cache to speed up md.parse:

const parse = md.parse
const cache = new LRUCache({ max: 1000 })
md.parse = (src, env) => {
  const key = hash(src + env.relPath)
  const cached = cache.get(key)
  if (cached) {
    return cached
  } else {
    const tokens = parse.call(md, src, env)
    cache.set(key, tokens)
    return tokens
  }
}

And these will lead to a problem: if someone changes one of those tokens during render process, it will be a disaster, because changing one of those tokens mean changing cache during render.

Here is an example (markdown/lib/link.js):

-  return Object.assign({}, token, {
-    tag: 'router-link'
+  return Object.create(token, {
+    tag: { value: 'router-link' }
   })

What is the difference? The former use assign, which will drop all the prototype methods (like Token.prototype.attrIndex, and will lead to an error at next time:

const hrefIndex = token.attrIndex('href')
// Error: token.attrIndex is not a function

How can we fix it?

By copy all the tokens before get and set:

md.parse = (src, env) => {
  const key = hash(src + env.relPath)
  const cached = cache.get(key)
  if (cached) {
    return copyTokens(cached)
  } else {
    const tokens = parse.call(md, src, env)
    cache.set(key, copyTokens(tokens))
    return tokens
  }
}

// I actually don't know whether we should
// prevent modification to cached tokens
function copyTokens (tokens) {
  return tokens.map((token) => {
    if (token.children) {
      token.children = copyTokens(token.children)
    }
    return Object.create(token)
  })
}

However, I still don't know whether we should do such thing, because I think users should not change those tokens during rendering process.

@shigma
Copy link
Collaborator Author

shigma commented Feb 19, 2019

@BuptStEve Can you check if this pr fix #1309? And what do you think about the question above?

@BuptStEve
Copy link
Contributor

@BuptStEve Can you check if this pr fix #1309? And what do you think about the question above?

It works.
Just some ideas. Maybe in markdown-loader, we call md.parse to check the cache and we cache the result of md.render?

@shigma
Copy link
Collaborator Author

shigma commented Feb 20, 2019

Just some ideas. Maybe in markdown-loader, we call md.parse to check the cache and we cache the result of md.render?

I think it will not work. Because addDependency was called in the rendering process.

@shigma
Copy link
Collaborator Author

shigma commented Feb 26, 2019

It may be better splitted into some smaller PRs. Closed.

@shigma shigma closed this Feb 26, 2019
@shigma shigma reopened this Feb 27, 2019
@shigma shigma closed this Feb 27, 2019
@shigma shigma deleted the code-snippet-hmr-parser-cache branch February 27, 2019 01:42
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Not rerender when code snippet file changes
2 participants