• Jobs
  • About Us
  • professionals
    • Home
    • Jobs
    • Courses and challenges
  • business
    • Home
    • Post vacancy
    • Our process
    • Pricing
    • Assessments
    • Payroll
    • Blog
    • Sales
    • Salary Calculator

0

321
Views
Automatización de la creación de bases de datos para pruebas

Para pruebas más rápidas, es mejor usar un sqlite basado en memoria, pero de vez en cuando es necesario usar MySQL para pruebas que coincidan más con la producción. Para evitar una discusión seca/pregunta abstracta, el siguiente código inserta un par de palabras y confirma que están en la base de datos, para ambos tipos de bases de datos SQL que acabamos de mencionar.

 from flask import Flask from flask_sqlalchemy import SQLAlchemy import unittest db = SQLAlchemy() TEST_DATABASE_URL_MEMORY = 'sqlite:///:memory:' TEST_DATABASE_URL_MYSQL = 'mysql+pymysql://root:@127.0.0.1:3306/somewords' def create_app(db_url): app = Flask(__name__) app.config['SQLALCHEMY_DATABASE_URI'] = db_url app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = False db.init_app(app) return app class Word(db.Model): __tablename__ = 'words' id = db.Column(db.Integer, primary_key=True, autoincrement=True) word = db.Column(db.String(32), index=True) class TestInsertion(unittest.TestCase): def manual_set_up(self, db_url): self.app = create_app(db_url) self.app_context = self.app.app_context() self.app_context.push() db.drop_all() db.create_all() def insert(self): words = ['hello', 'world'] for word in words: w = Word(word=word) db.session.add(w) db.session.commit() for word in words: assert Word.query.filter_by(word=word).first() is not None def test_dbs(self): for db_url in [TEST_DATABASE_URL_MEMORY, TEST_DATABASE_URL_MYSQL]: self.manual_set_up(db_url) self.insert()

El primero (sqlite) pasa. El segundo falla:

 E sqlalchemy.exc.InternalError: (pymysql.err.InternalError) (1049, "Unknown database 'somewords'")

Podemos, cada vez que ejecutamos las pruebas, crear la base de datos

 > mysql -u root -p Welcome to the MySQL monitor. Commands end with ; or \g. mysql> create database somewords; Query OK, 1 row affected (0.02 sec) mysql> quit;

pero esto excluye las pruebas automatizadas, por lo que supongo que me estoy perdiendo algo básico.

¿Cómo se puede ejecutar una prueba como la anterior, automatizando la creación de la base de datos?

Actualizar

Los ejemplos de prueba para 1.0 , 1.1 y el tutorial ( flask/examples/tutorial/tests/conftest.py ) usan tempfile.mkstemp() , que parece una buena manera de hacerlo. No es necesario preocuparse por establecer el nombre y crear la base de datos, ni siquiera preocuparse por el nombre de la base de datos (aleatorio y descartable). ¿Cómo/dónde se realiza la parte de creación de la base de datos?

 import tempfile db_fd, db_path = tempfile.mkstemp()
over 3 years ago · Santiago Trujillo
2 answers
Answer question

0

La creación y eliminación de bases de datos no parece ser compatible directamente con sqlalchemy, pero es compatible con sqlalchemy-utils: https://sqlalchemy-utils.readthedocs.io/en/latest/_modules/sqlalchemy_utils/functions/database.html# crear_base_de_datos .

Esto requerirá que ya tenga un servidor mysql ejecutándose, por lo que no le permitirá controlar la ubicación del archivo con tempfile.mkstemp().

Otro enfoque sería ejecutar el comando mysql como parte de la prueba automatizada.

over 3 years ago · Santiago Trujillo Report

0

Con algunas modificaciones en manual_set_up y test_dbs pude ejecutar el código.

Para la base de datos mysql, elimino el nombre de la base de datos de db_url . Y db.drop_all() también falla porque la base de datos no existe, así que introduzco try/except y paso la excepción aquí. Luego, antes db.create_all() , creo un motor sqlachemy sin pasar por db_url que no tiene el nombre de base de datos db.create_engine(db_url) .

 # your imports ... import sqlalchemy.exc #... TEST_DATABASE_URL_MYSQL = 'mysql+pymysql://root:@127.0.0.1:3306/' def manual_set_up(self, db_url, db_kind, db_name=None): if db_kind == "mysql": self.app = create_app(db_url + db_name) else: self.app = create_app(db_url) self.app_context = self.app.app_context() self.app_context.push() try: db.drop_all() except sqlalchemy.exc.InternalError as e: if "unknown database" in str(e.args[0]).lower(): pass try: db.create_all() except sqlalchemy.exc.InternalError as e: if "unknown database" in str(e.args[0]).lower(): db.create_engine(db_url, {}).execute(f"CREATE DATABASE IF NOT EXISTS {db_name};") db.create_all() def test_dbs(self): for args in [(TEST_DATABASE_URL_MEMORY, "sqlite"), (TEST_DATABASE_URL_MYSQL, "mysql", "somewords")]: self.manual_set_up(*args) self.insert()
over 3 years ago · Santiago Trujillo Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Our process Sales
Legal
Terms and conditions Privacy policy
© 2025 PeakU Inc. All Rights Reserved.

Andres GPT

Recommend me some offers
I have an error