Beispiel #1
0
def _populate_results_table(source_conn: ConnectionPlus,
                            target_conn: ConnectionPlus,
                            source_table_name: str,
                            target_table_name: str) -> None:
    """
    Copy over all the entries of the results table
    """
    get_data_query = f"""
                     SELECT *
                     FROM "{source_table_name}"
                     """

    source_cursor = source_conn.cursor()
    target_cursor = target_conn.cursor()

    for row in source_cursor.execute(get_data_query):
        column_names = ','.join(row.keys()[1:])  # the first key is "id"
        values = tuple(val for val in row[1:])
        value_placeholders = sql_placeholder_string(len(values))
        insert_data_query = f"""
                             INSERT INTO "{target_table_name}"
                             ({column_names})
                             values {value_placeholders}
                             """
        target_cursor.execute(insert_data_query, values)
Beispiel #2
0
def test_atomic_on_connection_plus_that_is_in_progress(in_transaction):
    sqlite_conn = sqlite3.connect(':memory:')
    conn_plus = ConnectionPlus(sqlite_conn)

    # explicitly set to True for testing purposes
    conn_plus.atomic_in_progress = True

    # implement parametrizing over connection's `in_transaction` attribute
    if in_transaction:
        conn_plus.cursor().execute('BEGIN')
    assert in_transaction is conn_plus.in_transaction

    isolation_level = conn_plus.isolation_level
    in_transaction = conn_plus.in_transaction

    with atomic(conn_plus) as atomic_conn:
        assert True is conn_plus.atomic_in_progress
        assert isolation_level == conn_plus.isolation_level
        assert in_transaction is conn_plus.in_transaction

        assert True is atomic_conn.atomic_in_progress
        assert isolation_level == atomic_conn.isolation_level
        assert in_transaction is atomic_conn.in_transaction

    assert True is conn_plus.atomic_in_progress
    assert isolation_level == conn_plus.isolation_level
    assert in_transaction is conn_plus.in_transaction

    assert True is atomic_conn.atomic_in_progress
    assert isolation_level == atomic_conn.isolation_level
    assert in_transaction is atomic_conn.in_transaction
Beispiel #3
0
def test_connection_plus():
    sqlite_conn = sqlite3.connect(':memory:')
    conn_plus = ConnectionPlus(sqlite_conn)

    assert isinstance(conn_plus, ConnectionPlus)
    assert isinstance(conn_plus, sqlite3.Connection)
    assert False is conn_plus.atomic_in_progress

    match_str = re.escape('Attempted to create `ConnectionPlus` from a '
                          '`ConnectionPlus` object which is not allowed.')
    with pytest.raises(ValueError, match=match_str):
        ConnectionPlus(conn_plus)
Beispiel #4
0
def test_atomic_on_outmost_connection_that_is_in_transaction():
    conn = ConnectionPlus(sqlite3.connect(':memory:'))

    conn.execute('BEGIN')
    assert True is conn.in_transaction

    match_str = re.escape('SQLite connection has uncommitted transactions. '
                          'Please commit those before starting an atomic '
                          'transaction.')
    with pytest.raises(RuntimeError, match=match_str):
        with atomic(conn):
            pass
Beispiel #5
0
def test_atomic():
    sqlite_conn = sqlite3.connect(':memory:')

    match_str = re.escape('atomic context manager only accepts ConnectionPlus '
                          'database connection objects.')
    with pytest.raises(ValueError, match=match_str):
        with atomic(sqlite_conn):
            pass

    conn_plus = ConnectionPlus(sqlite_conn)
    assert False is conn_plus.atomic_in_progress

    atomic_in_progress = conn_plus.atomic_in_progress
    isolation_level = conn_plus.isolation_level

    assert False is conn_plus.in_transaction

    with atomic(conn_plus) as atomic_conn:
        assert conn_plus_in_transaction(atomic_conn)
        assert conn_plus_in_transaction(conn_plus)

    assert isolation_level == conn_plus.isolation_level
    assert False is conn_plus.in_transaction
    assert atomic_in_progress is conn_plus.atomic_in_progress

    assert isolation_level == conn_plus.isolation_level
    assert False is atomic_conn.in_transaction
    assert atomic_in_progress is atomic_conn.atomic_in_progress
Beispiel #6
0
def test_make_connection_plus_from_connecton_plus():
    conn = ConnectionPlus(sqlite3.connect(':memory:'))
    conn_plus = make_connection_plus_from(conn)

    assert isinstance(conn_plus, ConnectionPlus)
    assert conn.atomic_in_progress is conn_plus.atomic_in_progress
    assert conn_plus is conn
Beispiel #7
0
def test_two_nested_atomics():
    sqlite_conn = sqlite3.connect(':memory:')
    conn_plus = ConnectionPlus(sqlite_conn)

    atomic_in_progress = conn_plus.atomic_in_progress
    isolation_level = conn_plus.isolation_level

    assert False is conn_plus.in_transaction

    with atomic(conn_plus) as atomic_conn_1:
        assert conn_plus_in_transaction(conn_plus)
        assert conn_plus_in_transaction(atomic_conn_1)

        with atomic(atomic_conn_1) as atomic_conn_2:
            assert conn_plus_in_transaction(conn_plus)
            assert conn_plus_in_transaction(atomic_conn_1)
            assert conn_plus_in_transaction(atomic_conn_2)

        assert conn_plus_in_transaction(conn_plus)
        assert conn_plus_in_transaction(atomic_conn_1)
        assert conn_plus_in_transaction(atomic_conn_2)

    assert conn_plus_is_idle(conn_plus, isolation_level)
    assert conn_plus_is_idle(atomic_conn_1, isolation_level)
    assert conn_plus_is_idle(atomic_conn_2, isolation_level)

    assert atomic_in_progress == conn_plus.atomic_in_progress
    assert atomic_in_progress == atomic_conn_1.atomic_in_progress
    assert atomic_in_progress == atomic_conn_2.atomic_in_progress
Beispiel #8
0
def path_to_dbfile(conn: ConnectionPlus) -> str:
    """
    Return the path of the database file that the conn object is connected to
    """
    cursor = conn.cursor()
    cursor.execute("PRAGMA database_list")
    row = cursor.fetchall()[0]

    return row[2]
Beispiel #9
0
def _rewrite_timestamps(target_conn: ConnectionPlus, target_run_id: int,
                        correct_run_timestamp: float,
                        correct_completed_timestamp: float) -> None:
    """
    Update the timestamp to match the original one
    """
    query = """
            UPDATE runs
            SET run_timestamp = ?
            WHERE run_id = ?
            """
    cursor = target_conn.cursor()
    cursor.execute(query, (correct_run_timestamp, target_run_id))

    query = """
            UPDATE runs
            SET completed_timestamp = ?
            WHERE run_id = ?
            """
    cursor = target_conn.cursor()
    cursor.execute(query, (correct_completed_timestamp, target_run_id))
Beispiel #10
0
def test_atomic_transaction(tmp_path):
    """Test that atomic_transaction works for ConnectionPlus"""
    dbfile = str(tmp_path / 'temp.db')

    conn = ConnectionPlus(sqlite3.connect(dbfile))

    ctrl_conn = sqlite3.connect(dbfile)

    sql_create_table = 'CREATE TABLE smth (name TEXT)'
    sql_table_exists = 'SELECT sql FROM sqlite_master WHERE TYPE = "table"'

    atomic_transaction(conn, sql_create_table)

    assert sql_create_table in ctrl_conn.execute(
        sql_table_exists).fetchall()[0]
Beispiel #11
0
def test_atomic_with_exception():
    sqlite_conn = sqlite3.connect(':memory:')
    conn_plus = ConnectionPlus(sqlite_conn)

    sqlite_conn.execute('PRAGMA user_version(25)')
    sqlite_conn.commit()

    assert 25 == sqlite_conn.execute('PRAGMA user_version').fetchall()[0][0]

    with pytest.raises(RuntimeError,
                       match="Rolling back due to unhandled exception") as e:
        with atomic(conn_plus) as atomic_conn:
            atomic_conn.execute('PRAGMA user_version(42)')
            raise Exception('intended exception')
    assert error_caused_by(e, 'intended exception')

    assert 25 == sqlite_conn.execute('PRAGMA user_version').fetchall()[0][0]