Как сгенерировать тестовые данные для вашего проекта базы данных с помощью Python
Если вам нужны тестовые данные для базы данных вашего проекта, вы можете получить набор данных из Kaggle или воспользоваться генератором данных. В первом случае, если вам нужно обработать данные перед вставкой их в базу данных, вы можете использовать Pandas, широко используемую библиотеку Python для анализа данных. Эта библиотека поддерживает различные форматы, включая CSV и JSON, а также предоставляет метод вставки данных в базу данных SQL.
Если вы выберете вместо этого генератор данных, вы можете найти его для MySQL в одном из репозиториев нашей учетной записи Percona Lab на GitHub. Используете ли вы другие технологии баз данных? Вы можете следовать руководствам, где объяснено, как создать свой собственный генератор данных для MySQL (он может работать для PostgreSQL) и MongoDB.
Если вы создаете свой собственный генератор данных, вы должны следовать этому процессу:
- Генерация поддельных данных с помощью Faker
- Хранение сгенерированных данных во фрейме данных Pandas
- Установление соединения с вашей базой данных
- Вставка содержимого DataFrame в базу данных
Зависимости
Убедитесь, что все зависимости установлены перед созданием скрипта Python, который будет генерировать данные для вашего проекта.
Вы можете создать requirements.txt
файл со следующим содержимым:
pandas
tqdm
faker
Или, если вы используете Anaconda, создайте файл environment.yml
:
name: percona
dependencies:
- python=3.10
- pandas
- tqdm
- faker
Вы можете изменить версию Python, поскольку было доказано, что этот скрипт работает с этими версиями Python: 3.7, 3.8, 3.9, 3.10 и 3.11.
В зависимости от используемой вами технологии базы данных вы должны добавить соответствующий пакет в свой requirements.txt
или файл environment.yml
:
- MySQL →
PyMySQL
- PostgreSQL →
psycopg2
- MongoDB →
pymongo
Запустите следующую команду, если вы используете pip
:
pip install -r requirements.txt
Или выполните следующую инструкцию для настройки среды проекта при использовании Anaconda:
conda env create -f environment.yml
База данных
Теперь, когда у вас установлены зависимости, вы должны создать базу данных с именем company
для MySQL или PostgreSQL.
Войдите в MySQL:
$ mysql -u root -p
Замените root
на ваше имя пользователя, если необходимо, и замените localhost
на IP-адрес или URL-адрес вашего экземпляра сервера MySQL, если необходимо.
Или войдите в PostgreSQL:
$ sudo su postgres
$ psql
и создайте базу данных company
:
create database company;
Вам не нужно предварительно создавать базу данных MongoDB.
Создание кадра данных Pandas
Перед созданием скрипта важно знать, что нам необходимо реализовать многопроцессорную обработку для оптимизации времени выполнения скрипта.
Многопроцессорность - это способ использовать преимущества процессорных ядер, доступных на компьютере, на котором запущен скрипт. В Python использование одного процессора вызвано глобальной блокировкой интерпретатора, которая позволяет только одному потоку выполнять интерпретатор Python в любой момент времени. При многопроцессорной обработке вся рабочая нагрузка распределяется на каждое доступное ядро процессора.
Теперь давайте начнем создавать наш собственный генератор данных. Во-первых, необходимо создать каталог modules
, а внутри каталога мы создадим модуль с именем dataframe.py.
Этот модуль позже будет импортирован в наш основной скрипт, и именно здесь мы определяем метод, который будет генерировать данные.
Вам необходимо импортировать необходимые библиотеки и методы:
from multiprocessing import cpu_count
import pandas as pd
from tqdm import tqdm
from faker import Faker
pandas
. Данные, сгенерированные с помощью Faker, будут сохранены в фрейме данных Pandas перед импортом в базу данных.tqdm()
. Этот метод необходим для добавления индикатора выполнения, показывающего ход создания DataFrame.Faker()
. Это генератор из библиотеки faker.cpu_count()
. Это метод из модуля многопроцессорной обработки, который вернет количество доступных ядер.
Затем будет создан и инициализирован генератор подделок путем вызова метода Faker()
. Это необходимо для генерации данных путем доступа к свойствам в библиотеке Faker.
И мы определяем количество доступных ядер процессора, вызывая метод cpu_count()
и присваивая это значение num_cores variable
.
fake = Faker()
num_cores = cpu_count() - 1
num_cores
— это переменная, в которой хранится значение, возвращаемое после вызова метода cpu_count()
. Используем все ядра минус одно, чтобы не зависал компьютер.
def create_dataframe(arg):
x = int(60000/num_cores)
data = pd.DataFrame()
for i in tqdm(range(x), desc='Creating DataFrame'):
data.loc[i, 'first_name'] = fake.first_name()
data.loc[i, 'last_name'] = fake.last_name()
data.loc[i, 'job'] = fake.job()
data.loc[i, 'company'] = fake.company()
data.loc[i, 'address'] = fake.address()
data.loc[i, 'city'] = fake.city()
data.loc[i, 'country'] = fake.country()
data.loc[i, 'email'] = fake.email()
return data
Затем мы определяем функцию create_dataframe()
, где:
x
— это переменная, которая будет определять количество итераций циклаfor
, в котором создается DataFrame.data
— это пустой DataFrame, который позже будет заполнен данными, сгенерированными с помощью Faker.- Атрибут Pandas DataFrame.loc обеспечивает доступ к группе строк и столбцов по их меткам. На каждой итерации в DataFrame добавляется строка данных, и этот атрибут позволяет присваивать значения каждому столбцу.
DataFrame, созданный после вызова этой функции, будет иметь следующие столбцы:
# Column Non-Null Count Dtype
--- ------ -------------- -----
0 first_name 60000 non-null object
1 last_name 60000 non-null object
2 job 60000 non-null object
3 company 60000 non-null object
4 address 60000 non-null object
5 country 60000 non-null object
6 city 60000 non-null object
7 email 60000 non-null object
Примечание. Скрипт генерирует 60 тысяч записей, но его можно адаптировать к вашему проекту, вы можете изменить это значение в переменной x
.
Подключение к базе данных
MySQL и PostgreSQL
Перед вставкой данных, ранее сгенерированных с помощью Faker, нам необходимо установить соединение с базой данных, и для этого будет использоваться библиотека SQLAlchemy.
SQLAlchemy — это набор инструментов Python SQL и Object Relational Mapper, который дает разработчикам приложений всю мощь и гибкость SQL.
from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
engine = create_engine("mysql+pymysql://user:password@localhost/company")
Session = sessionmaker(bind=engine)
Из SQLAlchemy мы импортируем методы create_engine()
и sessionmaker()
. Первый предназначен для подключения к базе данных, а второй — для создания привязки сеанса к объекту движка.
Не забудьте заменить user
, password
и localhost
своими данными аутентификации. Сохраните этот код в каталоге modules
и назовите его base.py
.
Для PostgreSQL замените:
engine = create_engine("mysql+pymysql://user:password@localhost/company")
С:
engine = create_engine("postgresql+psycopg2://user:password@localhost:5432/company")
Определение схемы базы данных
Для MySQL и PostgreSQL схема базы данных может быть определена с помощью Schema Definition Language, предоставляемого SQLAlchemy, но, поскольку мы создаем только одну таблицу и импортируем DataFrame, вызывая метод Pandas to_sql(), в этом нет необходимости.
При вызове метода Pandas to_sql()
мы определяем схему следующим образом:
from sqlalchemy.types import *
schema = {
"first_name": String(50),
"last_name": String(50),
"job": String(100),
"company": String(100),
"address": String(200),
"city": String(100),
"country" String(100),
"email": String(50)
}
Затем мы передаем переменную schema
в качестве параметра этому методу.
Сохраните этот код в каталоге modules
под именем schema.py
.
MongoDB
Прежде чем вставлять данные, ранее сгенерированные с помощью Faker, нам необходимо установить соединение с базой данных, и для этого будет использоваться библиотека PyMongo.
from pymongo import MongoClient
uri = "mongodb://user:password@localhost:27017/"
client = MongoClient(uri)
Из PyMongo мы импортируем метод MongoClient()
.
Не забудьте заменить user
, password
, localhost
и port
(27017) данными аутентификации. Сохраните этот код в каталоге модулей и назовите его base.py
.
Создание ваших данных
MySQL и PostgreSQL
Все необходимые модули теперь готовы к импорту в основной скрипт, теперь пришло время создать скрипт sql.py
. Сначала импортируйте необходимые библиотеки:
from multiprocessing import Pool
from multiprocessing import cpu_count
import pandas as pd
Для многопроцессорной обработки требуются Pool()
и cpu_count()
. Класс Python Multiprocessing Pool позволяет создавать пулы процессов и управлять ими в Python.
Затем импортируйте ранее созданные модули:
from modules.dataframe import create_dataframe
from modules.schema import schema
from modules.base import Session, engine
Теперь мы создаем многопроцессорный пул, настроенный на использование всех доступных ядер CPU минус одно. Каждое ядро вызовет функцию create_dataframe()
и создаст DataFrame с 4 тысячами записей. После завершения каждого вызова функции все созданные кадры данных будут объединены в один.
if __name__ == "__main__":
num_cores = cpu_count() - 1
with Pool() as pool:
data = pd.concat(pool.map(create_dataframe, range(num_cores)))
data.to_sql(name='employees', con=engine, if_exists = 'append', index=False, dtype=schema)
И, наконец, мы вставим DataFrame в базу данных MySQL, вызвав метод to_sql()
. Все данные будут храниться в таблице с именем сотрудников.
Таблица employees
создается без первичного ключа, поэтому мы выполняем следующую инструкцию SQL, чтобы добавить столбец id
, который установлен в качестве первичного ключа таблицы.
with engine.connect() as conn:
conn.execute("ALTER TABLE employees ADD id INT NOT NULL AUTO_INCREMENT PRIMARY KEY FIRST;")
Для PostgreSQL замените эту строку:
conn.execute("ALTER TABLE employees ADD id INT NOT NULL AUTO_INCREMENT PRIMARY KEY FIRST;")
С:
conn.execute("ALTER TABLE employees ADD COLUMN id SERIAL PRIMARY KEY;")
MongoDB
Все необходимые модули теперь готовы к импорту в основной скрипт, теперь пришло время создать скрипт mongodb.py
. Сначала импортируйте необходимые библиотеки:
from multiprocessing import Pool
from multiprocessing import cpu_count
import pandas as pd
Для многопроцессорной обработки требуются Pool()
и cpu_count()
. Класс Python Multiprocessing Pool позволяет создавать пулы процессов и управлять ими в Python.
Затем импортируйте ранее созданные модули:
from modules.dataframe import create_dataframe
from modules.base import client
Теперь мы создаем многопроцессорный пул, настроенный на использование всех доступных ядер CPU минус одно. Каждое ядро вызовет функцию create_dataframe()
и создаст DataFrame с 4 тысячами записей. После завершения каждого вызова функции все созданные кадры данных будут объединены в один.
if __name__ == "__main__":
num_cores = cpu_count() - 1
with Pool() as pool:
data = pd.concat(pool.map(create_dataframe, range(num_cores)))
data_dict = data.to_dict('records')
db = client["company"]
collection = db["employees"]
collection.insert_many(data_dict)
После входа на сервер MongoDB мы указываем базу данных и коллекцию, в которой будут храниться данные.
И, наконец, мы вставим DataFrame в MongoDB, вызвав метод insert_many()
. Все данные будут храниться в коллекции с именем employees
.
Запуск скрипта
Запустите следующую инструкцию, чтобы заполнить таблицу:
$ python sql.py
Или:
$ python mongodb.py
Время выполнения зависит от ядер CPU, доступных на вашем компьютере. Я запускаю этот скрипт на Intel i7 1260P с 16 ядрами, но использую 15.
Запросите свои данные
После завершения скрипта вы можете проверить данные в базе данных.
MySQL и PostgreSQL
Подключиться к базе данных company
.
MySQL:
use company;
PostgreSQL:
\c company
Затем получите количество записей.
select count(*) from employees;
Функция count()
возвращает количество записей в таблице employees
.
+----------+
| count(*) |
+----------+
| 60000 |
+----------+
1 row in set (0.22 sec)
MongoDB
use company
db.employees.count()
Функция count()
возвращает количество записей в таблице employees
.
60000
Или вы можете отобразить записи в таблице employees
:
db.employees.find().pretty()
Код, показанный в этом сообщении блога, можно найти в учетной записи GitHub в репозитории генератора данных.