def _create_clean_database():
    root_engine = get_sqlalchemy_engine(config["root_database"],
                                        isolation_level="AUTOCOMMIT")

    try:
        root_engine.execute("""
            CREATE TABLE IF NOT EXISTS pytest_mock_resource_db(
                id serial
            );
            """)
    except (sqlalchemy.exc.IntegrityError, sqlalchemy.exc.ProgrammingError):
        # A race condition may occur during table creation if:
        #  - another process has already created the table
        #  - the current process begins creating the table
        #  - the other process commits the table creation
        #  - the current process tries to commit the table creation
        pass

    result = root_engine.execute(
        "INSERT INTO pytest_mock_resource_db VALUES (DEFAULT) RETURNING id")
    id_ = tuple(result)[0][0]
    database_name = "pytest_mock_resource_db_{}".format(id_)

    root_engine.execute('CREATE DATABASE "{}"'.format(database_name))
    root_engine.execute(
        'GRANT ALL PRIVILEGES ON DATABASE "{}" TO CURRENT_USER'.format(
            database_name))

    return database_name
Beispiel #2
0
def test_create_clean_database_createdb_template(pmr_postgres_config,
                                                 createdb_template_pg):
    """Assert `createdb_template` is included in emitted CREATE DATABASE statement."""
    root_engine = get_sqlalchemy_engine(pmr_postgres_config,
                                        pmr_postgres_config.root_database,
                                        isolation_level="AUTOCOMMIT")

    statement = ""

    def before_execute(conn, clauseelement, multiparams, params,
                       execution_options):
        # Search for our create database statement, so we can assert against it.
        if "CREATE DATABASE" in clauseelement:
            nonlocal statement
            statement = clauseelement
        return clauseelement, multiparams, params

    # Use the event system to hook into the statements being executed by sqlalchemy.
    with root_engine.connect().execution_options(
            isolation_level="AUTOCOMMIT") as conn:
        event.listen(conn, "before_execute", before_execute)
        _create_clean_database(conn, createdb_template="template0")
        event.remove(conn, "before_execute", before_execute)

    assert "template0" in statement
def produce_clean_database(config, createdb_template="template1"):
    root_engine = get_sqlalchemy_engine(config,
                                        config.root_database,
                                        isolation_level="AUTOCOMMIT")
    with root_engine.connect() as conn:
        database_name = _create_clean_database(
            conn, createdb_template=createdb_template)

    return database_name
    def _(_postgres_container):
        database_name = _create_clean_database()
        engine = get_sqlalchemy_engine(database_name)

        assign_fixture_credentials(
            engine,
            drivername="postgresql+psycopg2",
            host=get_docker_host(),
            port=config["port"],
            database=database_name,
            username="******",
            password="******",
        )

        engine_manager = EngineManager(engine,
                                       ordered_actions,
                                       tables=tables,
                                       default_schema="public")
        for engine in engine_manager.manage(session=session):
            yield engine
def create_engine_manager(pmr_postgres_config,
                          ordered_actions,
                          tables,
                          createdb_template="template1"):
    database_name = produce_clean_database(pmr_postgres_config,
                                           createdb_template=createdb_template)

    engine = get_sqlalchemy_engine(pmr_postgres_config, database_name)
    assign_fixture_credentials(
        engine,
        drivername="postgresql+psycopg2",
        host=pmr_postgres_config.host,
        port=pmr_postgres_config.port,
        database=database_name,
        username=pmr_postgres_config.username,
        password=pmr_postgres_config.password,
    )
    return EngineManager(engine,
                         ordered_actions,
                         tables=tables,
                         default_schema="public")