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

Filter diff operation by path #9

Open
thenikso opened this issue Oct 31, 2018 · 3 comments
Open

Filter diff operation by path #9

thenikso opened this issue Oct 31, 2018 · 3 comments

Comments

@thenikso
Copy link

I came to a point in a project I am developing where I'd need odiff to "ignore" an object entirely. ie:

// Original
{
  normal: { a: 1, b: 2 },
  ignore: { a: 1, b: 2 }
}

// New
{
  normal: { a: 1, b: 999 },
  ignore: { a: 1, b: 999 }
}

The odiff of those might look like:

[
  { type: 'SET', path: ['normal', 'b'], val: 999 },
  { type: 'SET', path: ['ignore', 'b'], val: 999 },
]

While I'd need to "ignore" the ignore path to produce something like this:

[
  { type: 'SET', path: ['normal', 'b'], val: 999 },
  { type: 'SET', path: ['ignore'], val:  { a: 1, b: 999 } },
]

I believe that deep-diff has a prefilter option to do that.
Is there any way to do that with odiff as it is today? Would it make sense instead to attempt a PR to add the "prefilter" thingy?

Thanks!

@fresheneesz
Copy link
Contributor

Hm, so you want some ability to configure odiff to have special behavior on pre-determined paths? What's the core reason for your use case? Is it that those objects are huge? Or do they have cycles? Something else?

I could imagine one might want to do some custom differencing in a similar way. What if we had an API like:

odiff(a,b, {customDiff: function(path, aValue, bValue) {
  // Returns no differences, essentially treating aValue and bValue as the same.
  return [] 
  // "Ignores" the objects (in I think the way you were describing) by treating bValue as a new value set 
  // on the object.
  return [{type:'set', path:path, val:bValue}] 
  // You could return some other array of items, potentially custom items with different structures than the
  // ones created by odiff itself. 
  return [
    ... 
  ]
}})

I'd be open to something like this. Thoughts on that?

@thenikso
Copy link
Author

thenikso commented Nov 1, 2018

To give some context, my use case is quite specific as I am using odiff to send changes to the server and this particular subfield is stored in JSON but treated like an object client side.

More generally speaking what I am looking for is for odiff to treat some values as scalars even if they are object/arrays. In fact a "workaround" that I was attempting now was to convert that path to JSON in both objects before odiffing.

The API you proposed should definitely do the trick. In fact being able to manually provide a diff could enable even more convoluted use cases (ie: you want to send only an ID of an object if it has changes).

That said I would suggest to allow the customDiff function to return true/false to say:

  • true treat aValue and bValue as scalars so if there are any changes, set bValue (aka the case I need)
  • false proceed as normal odiff behaviour

This would be to simplify the usage of that particular API.

UPDATE: I have currently fixed this problem with a smarter logic on my server. That is I compute the partial diff for that sub-object starting from the stored value.

@fresheneesz
Copy link
Contributor

I have currently fixed this problem with a smarter logic on my server.

Ah ok. Well I'm happy to accept a PR with code for your suggestion on top of my suggestion. But it sounds like maybe you don't need it now?

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

No branches or pull requests

2 participants