Initial commit

This commit is contained in:
Zhongwei Li
2025-11-30 08:23:07 +08:00
commit 8b69ed05af
12 changed files with 812 additions and 0 deletions

View File

@@ -0,0 +1,15 @@
{
"name": "database-test-manager",
"description": "Database testing utilities with test data setup, transaction rollback, and schema validation",
"version": "1.0.0",
"author": {
"name": "Claude Code Plugin Hub",
"email": "[email protected]"
},
"skills": [
"./skills"
],
"commands": [
"./commands"
]
}

3
README.md Normal file
View File

@@ -0,0 +1,3 @@
# database-test-manager
Database testing utilities with test data setup, transaction rollback, and schema validation

280
commands/db-test.md Normal file
View File

@@ -0,0 +1,280 @@
---
description: Database testing with test data setup, transaction rollback, and schema validation
shortcut: dbt
---
# Database Test Manager
Comprehensive database testing utilities including test data generation, transaction management, schema validation, migration testing, and database cleanup.
## What You Do
1. **Test Data Management**
- Generate realistic test data with factories
- Create database fixtures and seeds
- Set up test database state
2. **Transaction Management**
- Wrap tests in transactions with automatic rollback
- Implement database cleanup strategies
- Handle nested transactions
3. **Schema Validation**
- Verify database schema matches models
- Test migrations up and down
- Validate constraints and indexes
4. **Database Testing Patterns**
- Test database queries and performance
- Verify data integrity constraints
- Test stored procedures and triggers
## Usage Pattern
When invoked, you should:
1. Analyze database schema and models
2. Generate test data factories
3. Set up database testing infrastructure
4. Create transaction wrappers for tests
5. Implement database assertions
6. Provide cleanup and teardown strategies
## Output Format
```markdown
## Database Test Suite
### Database: [Type]
**ORM:** [Prisma / TypeORM / SQLAlchemy / ActiveRecord]
**Test Framework:** [Jest / Pytest / RSpec]
### Test Data Factories
\`\`\`javascript
// factories/userFactory.js
import { faker } from '@faker-js/faker';
export const userFactory = {
build: (overrides = {}) => ({
id: faker.string.uuid(),
email: faker.internet.email(),
name: faker.person.fullName(),
createdAt: new Date(),
...overrides
}),
create: async (overrides = {}) => {
const data = userFactory.build(overrides);
return await prisma.user.create({ data });
},
createMany: async (count, overrides = {}) => {
const users = Array.from({ length: count }, () =>
userFactory.build(overrides)
);
return await prisma.user.createMany({ data: users });
}
};
\`\`\`
### Transaction Wrapper
\`\`\`javascript
// testHelpers/dbHelper.js
export const withTransaction = (testFn) => {
return async () => {
return await prisma.$transaction(async (tx) => {
try {
await testFn(tx);
} finally {
// Transaction will rollback automatically
throw new Error('ROLLBACK');
}
}).catch(err => {
if (err.message !== 'ROLLBACK') throw err;
});
};
};
// Usage in tests
describe('User Service', () => {
it('should create user', withTransaction(async (tx) => {
const user = await userFactory.create();
expect(user.email).toBeDefined();
// Rolls back automatically after test
}));
});
\`\`\`
### Database Assertions
\`\`\`javascript
// Custom matchers
expect.extend({
async toExistInDatabase(tableName, conditions) {
const record = await prisma[tableName].findFirst({
where: conditions
});
return {
pass: record !== null,
message: () =>
`Expected ${tableName} with ${JSON.stringify(conditions)} ` +
`to ${record ? '' : 'not '}exist in database`
};
},
async toHaveCount(tableName, expectedCount) {
const count = await prisma[tableName].count();
return {
pass: count === expectedCount,
message: () =>
`Expected ${tableName} to have ${expectedCount} records, ` +
`but found ${count}`
};
}
});
// Usage
await expect('user').toExistInDatabase({ email: '[email protected]' });
await expect('user').toHaveCount(5);
\`\`\`
### Migration Testing
\`\`\`javascript
describe('Database Migrations', () => {
it('should run migrations up and down', async () => {
// Run all migrations
await runMigrations('up');
// Verify schema
const tables = await getTables();
expect(tables).toContain('users');
expect(tables).toContain('posts');
// Rollback migrations
await runMigrations('down');
// Verify tables removed
const tablesAfter = await getTables();
expect(tablesAfter).not.toContain('users');
});
it('should enforce constraints', async () => {
const user = await userFactory.create();
// Test foreign key constraint
await expect(
prisma.post.create({
data: {
title: 'Test',
userId: 'non-existent-id'
}
})
).rejects.toThrow('Foreign key constraint');
// Test unique constraint
await expect(
userFactory.create({ email: user.email })
).rejects.toThrow('Unique constraint');
});
});
\`\`\`
### Query Performance Testing
\`\`\`javascript
describe('Query Performance', () => {
beforeAll(async () => {
// Seed large dataset
await userFactory.createMany(10000);
});
it('should query efficiently with indexes', async () => {
const start = performance.now();
await prisma.user.findMany({
where: { email: { contains: '@example.com' } }
});
const duration = performance.now() - start;
expect(duration).toBeLessThan(100); // 100ms threshold
});
it('should use proper indexes', async () => {
const explain = await prisma.$queryRaw`
EXPLAIN ANALYZE
SELECT * FROM users WHERE email LIKE '%@example.com%'
`;
expect(explain).toContain('Index Scan');
expect(explain).not.toContain('Seq Scan'); // No full table scan
});
});
\`\`\`
### Database Cleanup
\`\`\`javascript
// testSetup.js
beforeEach(async () => {
// Clear all tables in reverse dependency order
await prisma.comment.deleteMany();
await prisma.post.deleteMany();
await prisma.user.deleteMany();
});
afterAll(async () => {
await prisma.$disconnect();
});
\`\`\`
### Test Configuration
\`\`\`javascript
// jest.config.js
module.exports = {
testEnvironment: 'node',
setupFilesAfterEnv: ['./tests/setup.js'],
globalSetup: './tests/globalSetup.js',
globalTeardown: './tests/globalTeardown.js'
};
// globalSetup.js
module.exports = async () => {
// Create test database
execSync('createdb myapp_test');
// Run migrations
process.env.DATABASE_URL = 'postgresql://localhost/myapp_test';
execSync('npx prisma migrate deploy');
};
\`\`\`
### Next Steps
- [ ] Implement test data factories
- [ ] Set up transaction rollback
- [ ] Add database assertions
- [ ] Test migrations
- [ ] Configure test database
```
## Supported Databases
- PostgreSQL
- MySQL
- SQLite
- MongoDB
- SQL Server
## ORMs/Query Builders
- Prisma
- TypeORM
- Sequelize
- SQLAlchemy
- ActiveRecord

77
plugin.lock.json Normal file
View File

@@ -0,0 +1,77 @@
{
"$schema": "internal://schemas/plugin.lock.v1.json",
"pluginId": "gh:jeremylongshore/claude-code-plugins-plus:plugins/testing/database-test-manager",
"normalized": {
"repo": null,
"ref": "refs/tags/v20251128.0",
"commit": "f82fa24f9af4dc169df7227783fe1e4b3cbc2b63",
"treeHash": "41da4b62be907f59333851daee5e52814cd3247ed040d5adbc940f91a7b03f17",
"generatedAt": "2025-11-28T10:18:22.057278Z",
"toolVersion": "publish_plugins.py@0.2.0"
},
"origin": {
"remote": "git@github.com:zhongweili/42plugin-data.git",
"branch": "master",
"commit": "aa1497ed0949fd50e99e70d6324a29c5b34f9390",
"repoRoot": "/Users/zhongweili/projects/openmind/42plugin-data"
},
"manifest": {
"name": "database-test-manager",
"description": "Database testing utilities with test data setup, transaction rollback, and schema validation",
"version": "1.0.0"
},
"content": {
"files": [
{
"path": "README.md",
"sha256": "f79c7f3e943e3c5aab692100735641bf8f7a9f3d9e975c253accf589cc11d73f"
},
{
"path": ".claude-plugin/plugin.json",
"sha256": "264de649eaa2abe9c828f4a395863678cd79d0cd5d21883b1ce5592ebedda242"
},
{
"path": "commands/db-test.md",
"sha256": "fc763d3f4cf2aa21ebb203c88fe5f186d746bb818e9330044e4cd5d7876e66cd"
},
{
"path": "skills/database-test-manager/SKILL.md",
"sha256": "ee138446e7eee07c8d2a8b9e2fa4551baf31a3e1498bf531e887279031aaf0d5"
},
{
"path": "skills/database-test-manager/references/README.md",
"sha256": "0540671e41f17b66fd8cc4b6ecd64b7caaef13e0de946a7a0af71f7dea4cf03a"
},
{
"path": "skills/database-test-manager/scripts/README.md",
"sha256": "82a56d791b48aa2e9559202fac3ea3974b07b732fee053a10d3ac5575cc3c828"
},
{
"path": "skills/database-test-manager/assets/test_data_schema_template.json",
"sha256": "75a8285221c94d4929d48d3523cc7d83c39248126332585497ae7cae11671514"
},
{
"path": "skills/database-test-manager/assets/README.md",
"sha256": "97811dac10315510e629eb6c0a0fe24a7272d9e8dd0fd80d80fc24d700384904"
},
{
"path": "skills/database-test-manager/assets/example_migration_script.sql",
"sha256": "77f00460f308a7c956b63c4b9667718dba746bc4b90b294127d85757ab8c9cc3"
},
{
"path": "skills/database-test-manager/assets/database_schema_definition.json",
"sha256": "5f12063e263f57edca5cbd6cfaf519915560c77937cc2379c91ff9a5cf156f50"
},
{
"path": "skills/database-test-manager/assets/docker-compose.yml",
"sha256": "d5ab51c3e28fa639221a149166820c591c5d93bf63579ade858da058a6ebe180"
}
],
"dirSha256": "41da4b62be907f59333851daee5e52814cd3247ed040d5adbc940f91a7b03f17"
},
"security": {
"scannedAt": null,
"scannerVersion": null,
"flags": []
}
}

View File

@@ -0,0 +1,52 @@
---
name: managing-database-testing
description: |
This skill manages database testing by generating test data, wrapping tests in transactions, and validating database schemas. It is used to create robust and reliable database interactions. Claude uses this skill when the user requests database testing utilities, including test data generation, transaction management, schema validation, or migration testing. Trigger this skill by mentioning "database testing," "test data factories," "transaction rollback," "schema validation," or using the `/db-test` or `/dbt` commands.
allowed-tools: Read, Write, Edit, Grep, Glob, Bash
version: 1.0.0
---
## Overview
This skill empowers Claude to create and manage comprehensive database testing workflows. It facilitates the generation of realistic test data, ensures transactional integrity with automatic rollbacks, and validates database schema integrity.
## How It Works
1. **Test Data Generation**: Generates realistic test data using factories and fixtures, populating the database with relevant information for testing.
2. **Transaction Wrapping**: Wraps database tests within transactions, ensuring that any changes made during the test are automatically rolled back, maintaining a clean testing environment.
3. **Schema Validation**: Validates the database schema against expected structures and constraints, identifying potential issues with migrations or data integrity.
## When to Use This Skill
This skill activates when you need to:
- Generate test data for database interactions.
- Implement transaction management for database tests.
- Validate database schema and migrations.
## Examples
### Example 1: Generating Test Data
User request: "Generate test data factories for my PostgreSQL database using Faker to populate users and products tables."
The skill will:
1. Create Python code utilizing Faker and a database library (e.g., SQLAlchemy) to generate realistic user and product data.
2. Provide instructions on how to execute the generated code to seed the database.
### Example 2: Implementing Transaction Rollback
User request: "Wrap my database integration tests in transactions with automatic rollback to ensure a clean state after each test."
The skill will:
1. Generate code that utilizes database transaction management features to wrap test functions.
2. Implement automatic rollback mechanisms to revert any changes made during the test execution.
## Best Practices
- **Data Realism**: Utilize Faker or similar libraries to generate realistic test data that accurately reflects production data.
- **Transaction Isolation**: Ensure proper transaction isolation levels to prevent interference between concurrent tests.
- **Schema Validation**: Regularly validate database schema against expected structures to identify migration issues early.
## Integration
This skill seamlessly integrates with other code generation and execution tools within Claude Code. It can be used in conjunction with file management and code editing skills to create, modify, and execute database testing scripts.

View File

@@ -0,0 +1,8 @@
# Assets
Bundled resources for database-test-manager skill
- [ ] test_data_schema_template.json: Template for defining test data schemas.
- [ ] database_schema_definition.json: Example database schema definition for validation.
- [ ] example_migration_script.sql: Example SQL migration script for testing.
- [ ] docker-compose.yml: Docker Compose file for setting up test databases.

View File

@@ -0,0 +1,142 @@
{
"_comment": "Example database schema definition for validation. This can be used as a template.",
"schema_name": "public",
"tables": [
{
"table_name": "users",
"_comment": "Table for storing user information",
"columns": [
{
"column_name": "id",
"data_type": "SERIAL",
"is_nullable": false,
"is_primary_key": true,
"is_unique": true,
"_comment": "Unique identifier for the user"
},
{
"column_name": "username",
"data_type": "VARCHAR(50)",
"is_nullable": false,
"is_unique": true,
"_comment": "Unique username for login"
},
{
"column_name": "email",
"data_type": "VARCHAR(255)",
"is_nullable": false,
"is_unique": true,
"_comment": "Email address of the user"
},
{
"column_name": "password_hash",
"data_type": "VARCHAR(255)",
"is_nullable": false,
"_comment": "Hashed password for security"
},
{
"column_name": "created_at",
"data_type": "TIMESTAMP",
"is_nullable": false,
"default_value": "NOW()",
"_comment": "Timestamp of user creation"
}
],
"constraints": [
{
"constraint_name": "unique_username",
"constraint_type": "UNIQUE",
"columns": ["username"],
"_comment": "Ensures usernames are unique"
},
{
"constraint_name": "unique_email",
"constraint_type": "UNIQUE",
"columns": ["email"],
"_comment": "Ensures email addresses are unique"
}
]
},
{
"table_name": "products",
"_comment": "Table for storing product information",
"columns": [
{
"column_name": "id",
"data_type": "SERIAL",
"is_nullable": false,
"is_primary_key": true,
"is_unique": true,
"_comment": "Unique identifier for the product"
},
{
"column_name": "name",
"data_type": "VARCHAR(100)",
"is_nullable": false,
"_comment": "Name of the product"
},
{
"column_name": "description",
"data_type": "TEXT",
"is_nullable": true,
"_comment": "Detailed description of the product"
},
{
"column_name": "price",
"data_type": "NUMERIC(10, 2)",
"is_nullable": false,
"_comment": "Price of the product"
},
{
"column_name": "created_at",
"data_type": "TIMESTAMP",
"is_nullable": false,
"default_value": "NOW()",
"_comment": "Timestamp of product creation"
}
]
},
{
"table_name": "orders",
"_comment": "Table for storing order information",
"columns": [
{
"column_name": "id",
"data_type": "SERIAL",
"is_nullable": false,
"is_primary_key": true,
"is_unique": true,
"_comment": "Unique identifier for the order"
},
{
"column_name": "user_id",
"data_type": "INTEGER",
"is_nullable": false,
"_comment": "Foreign key referencing the users table"
},
{
"column_name": "order_date",
"data_type": "TIMESTAMP",
"is_nullable": false,
"default_value": "NOW()",
"_comment": "Date and time the order was placed"
},
{
"column_name": "total_amount",
"data_type": "NUMERIC(10, 2)",
"is_nullable": false,
"_comment": "Total amount of the order"
}
],
"foreign_keys": [
{
"constraint_name": "fk_user_id",
"columns": ["user_id"],
"referenced_table": "users",
"referenced_columns": ["id"],
"_comment": "Foreign key relationship to the users table"
}
]
}
]
}

View File

@@ -0,0 +1,75 @@
version: "3.9"
services:
# PostgreSQL Database Service
postgres:
image: postgres:14 # Use PostgreSQL version 14
container_name: test-db-postgres
environment:
POSTGRES_USER: test_user # Database username
POSTGRES_PASSWORD: test_password # Database password
POSTGRES_DB: test_database # Default database name
ports:
- "5432:5432" # Expose port 5432 for external access
volumes:
- postgres_data:/var/lib/postgresql/data # Persist data in a volume
healthcheck:
test: ["CMD-SHELL", "pg_isready -U test_user -d test_database"] # Check if the database is ready
interval: 10s
timeout: 5s
retries: 5
restart: unless-stopped # Restart policy
# MySQL Database Service
mysql:
image: mysql:8.0 # Use MySQL version 8.0
container_name: test-db-mysql
environment:
MYSQL_ROOT_PASSWORD: root_password # Root password for MySQL
MYSQL_USER: test_user # Database username
MYSQL_PASSWORD: test_password # Database password
MYSQL_DATABASE: test_database # Default database name
ports:
- "3306:3306" # Expose port 3306 for external access
volumes:
- mysql_data:/var/lib/mysql # Persist data in a volume
healthcheck:
test: ["CMD-SHELL", "mysqladmin ping -h localhost -u root -proot_password"] # Check if the database is ready
interval: 10s
timeout: 5s
retries: 5
restart: unless-stopped # Restart policy
# MongoDB Database Service
mongo:
image: mongo:latest # Use the latest MongoDB image
container_name: test-db-mongo
environment:
MONGO_INITDB_ROOT_USERNAME: root # Root username
MONGO_INITDB_ROOT_PASSWORD: root_password # Root password
ports:
- "27017:27017" # Expose port 27017 for external access
volumes:
- mongo_data:/data/db # Persist data in a volume
healthcheck:
test: ["CMD", "mongosh", "--eval", "db.runCommand('ping').ok"] # Check if the database is ready
interval: 10s
timeout: 5s
retries: 5
restart: unless-stopped # Restart policy
# Redis Service (Example for caching or other use cases)
redis:
image: redis:latest # Use the latest Redis image
container_name: test-redis
ports:
- "6379:6379" # Expose port 6379 for external access
volumes:
- redis_data:/data # Persist data in a volume
restart: unless-stopped # Restart policy
volumes:
postgres_data: # Volume for PostgreSQL data
mysql_data: # Volume for MySQL data
mongo_data: # Volume for MongoDB data
redis_data: # Volume for Redis data

View File

@@ -0,0 +1,39 @@
-- Example SQL migration script for database-test-manager plugin tests.
-- This script demonstrates basic table creation and data insertion.
-- Table creation: Replace 'your_table_name' with your actual table name.
CREATE TABLE IF NOT EXISTS your_table_name (
id INT PRIMARY KEY AUTO_INCREMENT,
name VARCHAR(255) NOT NULL,
email VARCHAR(255) UNIQUE,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
-- Data insertion: Replace with your initial data. Use Faker for more realistic data during testing.
INSERT INTO your_table_name (name, email) VALUES
('John Doe', 'john.doe@example.com'),
('Jane Smith', 'jane.smith@example.com');
-- Add an index (optional): Useful for optimizing queries.
CREATE INDEX idx_name ON your_table_name (name);
-- Add a constraint (optional): Enforces data integrity. Example: email must be in valid format
-- ALTER TABLE your_table_name ADD CONSTRAINT chk_email CHECK (email LIKE '%@%.%');
-- INSERT additional test data (example for parameterized testing):
-- INSERT INTO your_table_name (name, email) VALUES ('${test_name}', '${test_email}'); -- Placeholder for test parameters
-- Add a new column (example migration):
-- ALTER TABLE your_table_name ADD COLUMN phone_number VARCHAR(20);
-- Drop a column (example migration):
-- ALTER TABLE your_table_name DROP COLUMN phone_number;
-- Rename a column (example migration):
-- ALTER TABLE your_table_name RENAME COLUMN old_column_name TO new_column_name;
-- Modify a column (example migration):
-- ALTER TABLE your_table_name MODIFY COLUMN name VARCHAR(100);
-- Example of a more complex query (useful for testing query performance):
-- SELECT * FROM your_table_name WHERE name LIKE '%John%' ORDER BY created_at DESC LIMIT 10;

View File

@@ -0,0 +1,104 @@
{
"_comment": "Template for defining test data schemas. Use this as a starting point for creating your test data definitions.",
"schema_name": "your_schema_name",
"_comment": "The name of the database schema this data applies to. Often 'public'.",
"tables": [
{
"table_name": "users",
"_comment": "The name of the table.",
"columns": [
{
"column_name": "id",
"data_type": "INTEGER",
"primary_key": true,
"auto_increment": true,
"_comment": "Example of an integer primary key with auto-increment."
},
{
"column_name": "username",
"data_type": "VARCHAR(255)",
"nullable": false,
"unique": true,
"faker": "user_name",
"_comment": "Example using Faker to generate usernames."
},
{
"column_name": "email",
"data_type": "VARCHAR(255)",
"nullable": false,
"unique": true,
"faker": "email",
"_comment": "Example using Faker to generate email addresses."
},
{
"column_name": "created_at",
"data_type": "TIMESTAMP",
"default": "CURRENT_TIMESTAMP",
"_comment": "Example of a timestamp column with a default value."
}
],
"rows": [
{
"username": "existing_user",
"email": "existing@example.com",
"_comment": "Optionally specify exact values for specific rows. Faker will be used if not specified"
}
]
},
{
"table_name": "products",
"_comment": "Example of another table.",
"columns": [
{
"column_name": "id",
"data_type": "INTEGER",
"primary_key": true,
"auto_increment": true
},
{
"column_name": "name",
"data_type": "VARCHAR(255)",
"nullable": false,
"faker": "product_name",
"_comment": "Using a custom Faker provider. Requires the provider to be installed."
},
{
"column_name": "price",
"data_type": "DECIMAL(10, 2)",
"nullable": false,
"faker": "pyfloat:left_digits=3,right_digits=2,positive=True",
"_comment": "Example of using pyfloat for generating prices. Can use faker.pyfloat arguments."
},
{
"column_name": "description",
"data_type": "TEXT",
"faker": "paragraph",
"_comment": "Example of using faker to generate a paragraph of text."
},
{
"column_name": "user_id",
"data_type": "INTEGER",
"nullable": false,
"foreign_key": "users.id",
"_comment": "Example of a foreign key relationship. Requires the 'users' table to exist and have an 'id' column."
}
],
"rows": [
{
"name": "Specific Product",
"price": 99.99,
"description": "A very specific product description.",
"user_id": 1
}
]
}
],
"options": {
"number_of_rows_per_table": 5,
"_comment": "Default number of rows to create for each table if no 'rows' key is specified. Defaults to 1 if not specified.",
"rollback_transaction": true,
"_comment": "Whether to rollback the transaction after the data is inserted. Defaults to true.",
"truncate_tables": false,
"_comment": "Whether to truncate the tables before inserting data. Defaults to false."
}
}

View File

@@ -0,0 +1,9 @@
# References
Bundled resources for database-test-manager skill
- [ ] faker_providers.md: Documentation on creating custom Faker providers for generating specific types of test data.
- [ ] transaction_management_strategies.md: Detailed explanation of different transaction management strategies and their implications.
- [ ] schema_validation_techniques.md: Overview of various schema validation techniques and tools.
- [ ] database_api_documentation.md: API documentation for interacting with different database systems (PostgreSQL, MySQL, SQLite, MongoDB).
- [ ] database_testing_best_practices.md: Best practices for database testing, including data seeding, isolation, and cleanup.

View File

@@ -0,0 +1,8 @@
# Scripts
Bundled resources for database-test-manager skill
- [ ] generate_test_data.py: Generates test data using Faker library based on user-defined schemas.
- [ ] wrap_in_transaction.py: Wraps database operations within a transaction, providing automatic rollback functionality.
- [ ] validate_schema.py: Validates database schema against a predefined schema definition.
- [ ] run_migration_tests.py: Executes database migration tests and verifies the integrity of the database after migrations.