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

Determine conflict strategy for inserts with a function #3753

Closed
thelinuxlich opened this issue Feb 10, 2015 · 29 comments
Closed

Determine conflict strategy for inserts with a function #3753

thelinuxlich opened this issue Feb 10, 2015 · 29 comments
Assignees
Milestone

Comments

@thelinuxlich
Copy link

I'm inserting in batches with conflict: replace, but I stumbled upon a case where I'd need to change the strategy to error if the field status of my data is false. Without the possibility to do this dynamically I will have to avoid batch inserting for this specific table.

@danielmewes
Copy link
Member

Good idea. We should support it in the same way as #873 .

@marshall007
Copy link
Contributor

Just ran into this as well. I'm basically looking to do a replace while preserving a couple fields if they don't exist in the document being inserted. For example:

table.insert(values, {
  conflict: function (old_val, new_val) {
    return old_val.pluck('foo', 'bar').merge(new_val);
  }
})

@mlucy
Copy link
Member

mlucy commented Apr 22, 2015

I like the idea of passing the conflict resolution function as a conflict optarg.

@mlucy
Copy link
Member

mlucy commented Apr 22, 2015

We should also consider making the format be function (id, old_val, new_val) for consistency with #873.

@danielmewes
Copy link
Member

@mlucy Would the id be the primary key of the document? This seems somewhat different from #873 where the first argument would be the field name. I don't think it makes sense to add the id here.

@mlucy
Copy link
Member

mlucy commented Apr 28, 2015

Bumping to subsequent; #873 got bumped and we should settle this at the same time (hopefully for 2.2).

@thelinuxlich
Copy link
Author

Is this happening on 2.1 or 2.2? Now I need to insert in batches with conflict = update and there is a field that could be missing when updating that I would like to add(but only if it doesn't exist). Are there any alternatives?

@danielmewes
Copy link
Member

@thelinuxlich This is not happening for 2.1, hopefully for 2.2. Sorry.

Assuming that you need this to be atomic, I'm not sure if there's a work-around at the moment.
@mlucy do you have any idea for @thelinuxlich 's use case?

@mlucy
Copy link
Member

mlucy commented Jul 23, 2015

I don't think there's any way to do this while preserving the performance benefits of batched inserts in 2.0 or 2.1. Hopefully we can get this in for 2.2.

@mlucy mlucy modified the milestones: 2.2-polish, subsequent Jul 23, 2015
@mlucy
Copy link
Member

mlucy commented Jul 23, 2015

Bumping to 2.2 polish.

@danielmewes danielmewes modified the milestones: 2.2, 2.2-polish Jul 23, 2015
@marshall007
Copy link
Contributor

@danielmewes oops, sorry. At first glance I was thinking (as you just said) that the callback would be fired for every document with old_val = null in the case of new documents. It's definitely the cleanest solution to #4410 we've considered, but I think I agree. It's not worth making the more typical cases less convenient.

@danielmewes
Copy link
Member

Looks like we agree on

.insert(documents, {conflict: function(id, old_val, new_val) { ... } })

where the conflict function is only called when there actually is a conflict.
Marking settled.

@thelinuxlich
Copy link
Author

Another very good use case for this feature would be when you save timestamps for document updating and when replacing in batches, you want to drop documents which have a older timestamp than the document to be replaced, thus guaranteeing some kind of ordering.

@danielmewes
Copy link
Member

@thelinuxlich Very interesting use case!

@danielmewes danielmewes modified the milestones: 2.3, 2.2-polish Oct 29, 2015
@danielmewes danielmewes modified the milestones: 2.3, 2.3-polish Nov 19, 2015
@thelinuxlich
Copy link
Author

I found another use case, when you want to limit the key quantity of a embedded object, very useful.

@marshall007
Copy link
Contributor

@thelinuxlich what do you mean? Can you give an example where that's useful?

@thelinuxlich
Copy link
Author

@marshall007 when you let the user save N fields inside a embedded object but you want to limit the max quantity of fields. An example from my code(limiiting to 30 fields):

r.table("attributes").get(item.id).replace(row => {
    return r.branch(row.eq(null),
        item, {
            id: item.id,
            client_id: item.client_id,
            visitor_id: item.visitor_id,
            fields: r.branch(row("fields").keys().setUnion(r(item.fields).keys()).count().gt(30),
                row("fields").merge(r(item.fields).pluck(row("fields").keys().setIntersection(r(item.fields).keys()))),
                row("fields").merge(item.fields)
            )
        }
    );
}, {
    durability: "soft"
})

@nighelles nighelles self-assigned this Mar 7, 2016
@nighelles
Copy link

This was in review #3523.

@nighelles
Copy link

This is in next.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

5 participants