Skip to content
This repository has been archived by the owner on Dec 11, 2019. It is now read-only.

Handle failure in creating a state diff by logging (and crash-reporting) the full path of any keys that are null #13240

Merged
merged 1 commit into from
Feb 23, 2018

Conversation

petemill
Copy link
Member

@petemill petemill commented Feb 21, 2018

A null key path was fixed in #13234, but there may be other cases, so we should add better logging to the console and for the crash reports.

Performance should be unaffected since v8 can now optimize functions which contain a try...catch block.

Fix #13239

Submitter Checklist:

  • Submitted a ticket for my issue if one did not already exist.
  • Used Github auto-closing keywords in the commit message.
  • Added/updated tests for this change (for new code or code which already has tests).
  • Ran git rebase -i to squash commits (if needed).
  • Tagged reviewers and labelled the pull request as needed.
  • Request a security/privacy review as needed. (Ask a Brave employee to help if you cannot access this document.)

Test Plan:

This should cause no change in functionality, or extra log lines.
If a dev really wants to check the output in error conditions, they can force a null key path in the state, for example in appStore.js at the top of the emitChanges function:
appState = appState.setIn(['historySites', null], Immutable.fromJS({ hello: 'a' }))

Reviewer Checklist:

  • Request a security/privacy review as needed if one was not already requested.

Tests

  • Adequate test coverage exists to prevent regressions
  • Tests should be independent and work correctly when run individually or as a suite ref
  • New files have MPL2 license header

…ng) the full path of any keys that are null.

Fix #13239
@petemill petemill added this to the 0.21.x (Beta Channel) milestone Feb 21, 2018
@petemill petemill self-assigned this Feb 21, 2018
@codecov-io
Copy link

Codecov Report

Merging #13240 into master will decrease coverage by 0.01%.
The diff coverage is 45.16%.

@@            Coverage Diff             @@
##           master   #13240      +/-   ##
==========================================
- Coverage   55.94%   55.93%   -0.02%     
==========================================
  Files         281      281              
  Lines       27831    27873      +42     
  Branches     4563     4568       +5     
==========================================
+ Hits        15570    15590      +20     
- Misses      12261    12283      +22
Flag Coverage Δ
#unittest 55.93% <45.16%> (-0.02%) ⬇️
Impacted Files Coverage Δ
app/common/state/immutableUtil.js 97.91% <100%> (+0.77%) ⬆️
js/stores/appStore.js 16.57% <5.55%> (+0.43%) ⬆️

Copy link
Member

@bsclifton bsclifton left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

++

@bsclifton bsclifton merged commit a4a04cc into master Feb 23, 2018
@bsclifton bsclifton deleted the fix/log-state-null-key-paths branch February 23, 2018 06:43
bsclifton added a commit that referenced this pull request Feb 23, 2018
Handle failure in creating a state diff by logging (and crash-reporting) the full path of any keys that are null
bsclifton added a commit that referenced this pull request Feb 23, 2018
Handle failure in creating a state diff by logging (and crash-reporting) the full path of any keys that are null
@bsclifton
Copy link
Member

master a4a04cc
0.22.x dcba3fe
0.21.x 8fc13f5

// one possible reason immutablediff can throw an error
// is due to null keys, so let's log any that we find
const nullKeyPaths = findNullKeyPaths(appState)
const error = (typeof e === 'object')
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we should be more specific about the type of error before we do a null key check. We don't want to assume that all exceptions are this specific issue.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The trouble is that immutablediff does not throw an error object, just a (dynamic) string. This is the only case I've seen immutablediff fail so far, and I did not want to go down the route of either:

  • parsing the string, since it could change in a later immutablediff version
  • assuming string vs Error object would mean a null-key error, since that could also change

Again, since the app will be unusable in this state, I wanted to err on the side of caution with regards to making sure we get the right error output and reported, so that we can solve the issue. But happy to take advice on this.

nullKeys.push(keyPath)
}
// recursive, to find deep keys
nullKeys.push(...api.findNullKeyPaths(state.get(key), keyPath))
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

recursion will be substantially more expensive than iteration to go through all the keys

Copy link
Member Author

@petemill petemill Feb 24, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it worth spending the time to get this for...of...recurse loop into a flat iteration loop considering that if this code gets run the app is in an unusable state anyway? I do not believe it will further impact the user apart from making sure we get the correct error logged and therefore fixed more quickly.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So... I was intrigued by the challenge, and tested what I came up with for a non-recursive function. It runs ~30% slower than the recursive one https://jsperf.com/immutable-find-null-paths-recursion-vs-iteration Perhaps someone can improve on it.

image

@bsclifton bsclifton modified the milestones: 0.22.x (Developer Channel), 0.20.x Release 3 (Hotfix) Feb 25, 2018
bsclifton added a commit that referenced this pull request Feb 25, 2018
Handle failure in creating a state diff by logging (and crash-reporting) the full path of any keys that are null
@bsclifton
Copy link
Member

0.20.x 2c3f975

NejcZdovc pushed a commit that referenced this pull request Feb 25, 2018
Handle failure in creating a state diff by logging (and crash-reporting) the full path of any keys that are null
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

If state contains a [null] key, all actions will fail with little log evidence
4 participants