How to generate a RethinkDB changefeed for all tables in a database

835 views Asked by At

I'm testing an API which inserts or deletes data in multiple tables of a RethinkDB database. In order to monitor what is happening to the database while using the API, I would like to print the changes in all its tables.

Here is some 'pseudo-code' of what I'm trying to achieve:

import rethinkdb as r

# Prior to running this script, run "rethinkdb --port-offset 1" at the command line
conn = r.connect('localhost', 28016)
if 'test' in r.db_list().run(conn):
    r.db_drop('test').run(conn)
r.db_create('test').run(conn)

r.table_create('table1').run(conn)
r.table_create('table2').run(conn)

feed = r.table('table1' and 'table2').changes().run(conn)
for document in feed:
    print document

Prior to running this script, I would run rethinkdb --port-offset 1 to initialize the RethinkDB database.

Once this script is running, I'd like to insert data into either table1 or table2 (using, for example, the web UI at localhost:8081) and see the changes printed in the terminal running the script. This appears not to work, however, because r.table('table1' and 'table2') is probably not a valid ReQL query.

How can I monitor changes in both tables?

2

There are 2 answers

0
Etienne Laurin On BEST ANSWER

You can follow multiple changefeeds in a single query using r.union:

r.union(
  r.table('table1').changes(),
  r.table('table2').changes()
).run(conn)
0
Kurt Peek On

I ended up running the changefeeds for each table in a separate thread:

import rethinkdb as r
import threading

# Prior to running this script, run "rethinkdb --port-offset 1" at the command line
conn = r.connect('localhost', 28016)

def clear_test_database():
    '''Clear the contents of the "test" database by dropping and re-creating it.'''
    if 'test' in r.db_list().run(conn):
        r.db_drop('test').run(conn)
    r.db_create('test').run(conn)

clear_test_database()

def monitor_changes(table_name, conn):
    feed = r.table(table_name).changes().run(conn)
    for document in feed:
        print document

tables = ['table1', 'table2']

for table in tables:
    conn = r.connect('localhost', 28016)
    r.table_create(table).run(conn)
    thread = threading.Thread(target=monitor_changes, args=(table, conn))
    thread.start()

Note that I re-define the conn connection object within the for-loop as these objects are not thread-safe.

To test the method, I opened the web UI at localhost:8081 and used the following insert command:

enter image description here

In the Sublime runner I see the changes being added every time I press the "Run" button:

enter image description here

This works both when I choose table1 or table2 in the insert command.