SQL Dog is a tool that analyzes MySQL query logs and triggers warnings when specified conditions (such as WHERE clauses or NOT NULL constraints) are missing from queries. It's designed to enhance database security and performance.
- Overview
- Design Philosophy and Architecture
- Installation
- Configuration
- Usage
- Features
- Technical Design
- Developer Information
- Troubleshooting
- Roadmap
SQL Dog helps with:
- Security: Detecting queries missing required WHERE conditions
- Performance: Identifying unoptimized queries that might cause full table scans
- Quality Control: Ensuring proper use of NOT NULL constraints
- Auditing: Analyzing database access patterns
It's a powerful tool for preventing bugs and issues in high-load production environments before they occur.
SQL Dog isn't just a query log analyzer—it acts as a watchdog for your database access, protecting both security and performance aspects. Below is a detailed explanation of the project's design philosophy.
Problems Being Addressed: In many development environments, database access patterns degrade over time, leading to issues such as:
- Queries missing essential WHERE clauses, causing full table scans
- Queries retrieving deleted data by forgetting to check logical deletion flags (e.g., deleted_at)
- Queries lacking proper permission conditions (tenant ID, user ID), creating security vulnerabilities
The overall program execution flow:
- Load Configuration: Read database connection information and validation rules from YAML files
- Retrieve Query Logs: Get executed queries from MySQL's general_log table
- Parse Queries: Convert each query into an abstract syntax tree (AST) and extract structured information
- Validate Rules: Compare extracted information with validation rules and detect violations
- Generate Reports: Format and output validation results
+------------------+ +----------------+ +---------------+
| Load Configuration | --> | Retrieve Logs | --> | Parse Queries |
+------------------+ +----------------+ +---------------+
|
v
+---------------+ +---------------+
| Output Reports | <-- | Validate Rules |
+---------------+ +---------------+
- PingCAP's SQL Parser: Selected as a parser capable of accurately analyzing complex MySQL syntax
- GORM: Chosen as a simple yet powerful ORM to simplify database access
- go-yaml: Selected for parsing configuration files, considering readability and extensibility
- testify: Adopted to write more concise and expressive test code
For example, in a multi-tenant application, you can set security rules like:
tables:
- name: users
mustSelectColumns:
- tenant_id # Tenant ID condition is required
stmtTypePatterns:
- select
- update
- delete
With this rule, the following query would trigger a warning:
-- Warning: no filtering by tenant_id
SELECT * FROM users WHERE name = 'John';
While this query would be allowed:
-- OK: filtered by tenant_id
SELECT * FROM users WHERE tenant_id = 123 AND name = 'John';
SQL Dog is designed with the following philosophy:
- Defensive Programming: Detect issues early to prevent production failures
- Configuration-Driven Approach: Add and modify rules flexibly without changing code
- Domain-Driven Design: View the technical domain of SQL queries from the business domain perspective of security and performance
By using this tool, you can maintain database access quality and prevent security and performance issues.
- Go 1.18 or higher
- MySQL 5.7 or higher
# Clone the repository
git clone https://github.com/tkc/sql-dog.git
cd sql-dog
# Install dependencies
go mod download
Enable query logging in MySQL and configure it to record to the general_log table:
SET GLOBAL general_log = 'ON';
SET GLOBAL log_output = 'TABLE';
# Optional: Configure slow query log
SET GLOBAL slow_query_log = 'ON';
SET GLOBAL long_query_time = 0;
-
Copy the sample configuration file:
cp config.sample.yaml config.yaml
-
Edit
config.yaml
to configure your connection settings:username: "root" password: "your_password" host: "localhost" port: 3306 rootDatabase: "mysql" serviceDatabase: "your_database_name"
-
Copy the sample validation rules file:
cp linter.sample.yaml linter.yaml
-
Edit
linter.yaml
to set up validation rules:# Queries to exclude from validation ignores: - DELETE FROM temp_table # Tables and rules to validate tables: - name: users # Required column conditions for SELECT queries mustSelectColumns: - deleted_at - tenant_id # SQL statement types to target stmtTypePatterns: - select - update - delete # Columns requiring NOT NULL constraints notNullColumns: - deleted_at
# Run query analysis and display report
go run ./cmd/lint/main.go
# Or use the compiled binary
./sql-dog-lint
# Clear records from the general_log table
go run ./cmd/clean/main.go
# Or use the compiled binary
./sql-dog-clean
- WHERE Clause Checking: Verifies that queries to specific tables include the required WHERE conditions
- NOT NULL Constraint Checking: Confirms that target tables have necessary NOT NULL constraints set
- Multi-Table Support: Configure different validation rules for multiple tables
- Exclusion Rules: Exempt specific queries from validation
# Local build (outputs to ./bin/)
make build
# Install to $GOPATH/bin
make install
# Run all tests
make test
# Run tests with race detection
make test-race
# Run tests with coverage reporting
make test-cover
# Format all Go code
make fmt
# Run Go linter
make lint
-
MySQL Connection Error
- Verify connection information in
config.yaml
- Check if MySQL server is running
- Verify connection information in
-
Empty general_log Table
- Verify MySQL logging is correctly enabled
- Check if target queries have been executed
-
Validation Rules Not Working
- Verify
linter.yaml
syntax is correct - Check that table and column names are accurately entered
- Verify
- Support for more query log formats (HTTP requests, text logs, etc.)
- Dashboard UI
- Real-time monitoring
- Automatic correction suggestions
This project is released under the MIT License.