I'm trying to update multiple documents in RethinkDB, based on some precalculated values in a Hash. i.e.
Given a table stats with primary key slug with data like
[{slug: 'foo', stats: {}}, {slug:'bar', stats:{}}]
and given a Hash with values like
updated_stats = {
'foo' => {a: 1, b: 2},
'bar' => {a: 3, b: 4}
}
I can do this
updated_stats.each{|k,v|
r.table('stats').get(k).update{|s|
{ :stats => v }
}
}
So, why can't I do the following?
r.table('stats').get_all(*updated_stats.keys).update{|s|
{ :stats => updated_stats[s["slug"]] }
}
the rql shows nil as the value of updated_stats[s["slug"]]. Would really appreciate any help on this. Thanks.
For anyone looking for how to bulk update records, it's actually pretty easy but not at all intuitive.
You actually have to perform an insert while specifying that if there's any conflicts, to update those records. You will obviously need to provide the Id of each record to be updated.
Using the following data set:
|-------------|--------------|
| id | title |
|-------------|--------------|
| 1 | fun |
|-------------|--------------|
| 2 | in |
|-------------|--------------|
| 3 | the |
|-------------|--------------|
| 4 | sun |
|-------------|--------------|
Here's an example (javascript):
const new_data = [
{id: 1, title: 'dancing'},
{id: 4, title: 'rain'},
];
r.db('your_db').table('your_table').insert(new_data, {conflict: 'update'});
The results would be:
|-------------|--------------|
| id | title |
|-------------|--------------|
| 1 | dancing |
|-------------|--------------|
| 2 | in |
|-------------|--------------|
| 3 | the |
|-------------|--------------|
| 4 | rain |
|-------------|--------------|
One caveat you should be aware of, though, is that if you represent something in the new_data array that doesn't currently exist in the table, it will be added/upserted.
Cheers!
It's a tricky problem.
Here's the solution first.
r.table('stats').get_all(*updated_stats.keys).update{|s|
{ :stats => r.expr(updated_stats).get_field(s["slug"]) }
}.run()
Then updated_stats is a ruby hash so when you use the brackets, it's the usual bracket operator, and since updated_stats doesn't have the key s["slug"], it returns nil.
So you have to wrap updated_stats in r.expr().
Then brackets in ruby are used for nth, get_field, slice etc. And when given a variable, it cannot guess which one it should use.
So you have to explicitly say you want to use get_field.
We will add a bracket term, which should fix this problem -- see https://github.com/rethinkdb/rethinkdb/issues/1179
Sorry you ran into this!
Related
Beeing pretty new to Power Query, I find myself faced with this problem I wish to solve.
I have a TableA with these columns. Example:
Key | Sprint | Index
-------------------------
A | PI1-I1 | 1
A | PI1-I2 | 2
B | PI1-I3 | 1
C | PI1-I1 | 1
I want to end up with a set looking like this:
Key | Sprint | Index | HasSpillOver
-------------------------
A | PI1-I1 | 1 | Yes
A | PI2-I2 | 2 | No
B | PI1-I3 | 1 | No
C | PI1-I1 | 1 | No
I thought I could maybe nestedjoin TableA on itself and then compare indicies and strip them away and then count rows in the table, like outlined below.
TableA=Key, Sprint, Index
// TableA Nested joined on itself (Key, Sprint, Index, Nested)
TableB=NestedJoin(#"TableA", "Key", #"TableA", "Key", "Nested", JoinKind.Inner)
TableC= Table.TransformColumns(#"TableB", {"Nested", (x)=>Table.SelectRows(x, each [Index] <x[Index])} )
.. and then do the count, however this throws an error:
Can not apply operator < on types List and Number.
Any suggestions how to approach this problem? Possibly (probably) in a different way.
You did not define very well what "spillover" means but this should get you most of the way
Mine assumes adding another index. You could use what you have if it is relevant
Then the code counts the number of rows where the (2nd) index is higher, and the [Key] field matches. You could add code so that the Sprint field matches as well if relevant
let Source = Excel.CurrentWorkbook(){[Name="Table1"]}[Content],
#"Added Index" = Table.AddIndexColumn(Source, "Index.1", 0, 1),
#"Added Custom" = Table.AddColumn(#"Added Index" ,"Count",(i)=>Table.RowCount(Table.SelectRows(#"Added Index" , each [Key]=i[Key] and [Index.1]>i[Index.1])))
in #"Added Custom"
Here's my scenario:
I have a Event model and a Stage model, a event can have multiple stages and a stage could be assigned to multiple events. So Many-to-many. The thing is, a stage has a sort_order, and that sort_order could be different in each event. That's why I added the sort_order into the pivot table instead in, for example, the stage table.
table: events_stages
| event_id | stage_id | sort_order |
------------------------------------
| 1 | 1 | 1 |
| 1 | 2 | 2 |
| 1 | 5 | 3 |
The thing is when I'm going to relate the Stage with the events its in,
I'm doing something like in the StageController:
sending a post with events: [1,2,3] and sort_order: [1,1,2]
$relatedEvents = array();
foreach ($request->events as $key => $event)
{
$relatedEvents[] = array(
'event_id' => $relatedEventId,
'sort_order' => $request->sort_order[$key]
);
}
$stage->events()->sync(
$relatedEvents
);
but rely simply in the order of the post, doesn't seem like a really good idea.
Does anyone have a nicer solution?
Thanks!
Sometimes is better to create another model (and use it as a pivot) rather than use pivot table itself. You have more control. I'm not sure what exactly you want to achieve.
I have two databases: one is old and deprecated; the other one is new, working. Both of them have a table called brands.
In the deprecated database, the brands table is something like the following:
id | name
1 | Playstation 1
2 | Playstation 2
3 | Playstation 3
4 | Playstation 4
5 | Xbox
6 | Xbox 360
7 | Xbox One
In the new one, this is the brands table:
id | name
1 | Xbox
2 | Xbox 360
3 | Xbox One
4 | Playstation 1
5 | Playstation 2
6 | Playstation 3
7 | Playstation 4
In practice, the scenario is more complex, but the example I gave represents well. So, there's also a products table:
id | name | brand_id | created_at | updated_at
I want to import products from the old database to the new one, but the brands aren't matching by id as you saw. Then, I want to do something like this:
brand_id 1 on old_database == brand_id 4 on new_database
To be more specific, is kind of a dictionary without ifs.
This is what I've done:
if query.brand == 1
brand_id == 4
elsif query.brand == 2
brand_id = 5
end
But this isn't what I really want. Yes, it works, but I want to do something simpler. I think hashes are exactly what I'm looking for. Any suggestions?
You could declare a hash like this:
brand_map = {1 => 4, 2 => 5} # add other entries as needed
and then lookup the new id like this:
brand_id = brand_map[1]
=> 4
Yes, it seems that a hash is what you want. For example,
id_map = { 1=>4, 2=>5, ... } # old id => new id
then for a record id, name, write it to the new database as id_map(id), name.
I'd like to compare a Cucumber::Ast::Table of (at least) expected values with an array containing my actual values, but I want to ignore additional rows. For this, I thought I could use the diff! method with :surplus_row => false.
This works as expected (Cucumber reports success):
table (Cucumber::Ast::Table):
|id|name |
|1 |one |
|2 |two |
#actual:
|id|name |
|1 |one |
|2 |two |
|3 |three|
But this does not (I get Cucumber::Ast::Table::Different ):
table (Cucumber::Ast::Table):
|id|name |
|2 |two |
#actual:
|id|name |
|1 |one |
|2 |two |
|3 |three|
So it seems Cucumber is reporting a false positive if my #actual contains only "inner" rows. Is this a bug in Cucumber? Or am I making some stupid mistake?
CODE
table.feature:
Feature: Comparing Cucumber tables
Scenario: Comparing with a table with additional rows
Given I have a table with three rows and two columns
When I compare this table with an additional row and the same columns
Then I should get at least these rows
|id|name |
|2 |two |
table_steps.rb:
Given /^I have a table with three rows and two columns$/ do
#actual = [ { "id" => "1", "name" => "one" },
{ "id" => "2", "name" => "two"},
{ "id" => "3", "name" => "three" } ]
end
When /^I compare this table with an additional row and the same columns$/ do
# no-op
end
Then /^I should get at least these rows$/ do |table|
table.diff!(#actual, { :surplus_row => false } )
end
Cucumber version 1.2.1
Turns out it was a bug in the old cucumber version I was using. Upgrading from 1.2.1 to 1.3.10 fixed the issue.
See Cucumber Github Issue for details regarding the bug.
Is it possible to sort based on the "weight" and then DESC on attr in the same Query?
For example, if I search for this text "test is fine" and I have this in the index
+------------+---------+
| Field | Type |
+------------+---------+
| id | integer |
| text | field |
| importance | uint |
+------------+---------+
importance is attr here
with these values,
1, "test", 3
2, "test is fine", 1
3, "test", 8
then if I search for "test is fine" I need the result to be sorted first based on the relevance of the keywords(weight) then based on "importance" attr, so the id output for the search will be
ID result = 2, 3, 1
I'm using this but the result is being sorted based on the attr 'importance' wih no regards to the weight
$cl->SetSortMode( SPH_SORT_ATTR_DESC, 'importance' );
You've sort of answered your own question. Yes its SPH_SORT_EXTENDED you want!
$cl->setSortMode(SPH_SORT_EXTENDED, "#relevance DESC, importance DESC");