VOOZH about

URL: https://deepwiki.com/hypervel/validation/6-database-integration

⇱ Database Integration | hypervel/validation | DeepWiki


Loading...
Menu

Database Integration

The database integration system provides presence verification capabilities for validation rules that need to query a database. This enables the exists and unique validation rules to verify attribute values against database tables. The system is built on an interface-based architecture that abstracts database queries behind the PresenceVerifierInterface, with a concrete implementation provided by DatabasePresenceVerifier.

For information about the exists and unique rule objects, see Built-in Rule Objects. For details on all validation rules including database rules, see Built-in Validation Rules.

System Architecture

The database integration system consists of three main components: an interface contract, a concrete implementation, and integration points within the validation engine.


Sources: src/PresenceVerifierInterface.php1-18 src/DatabasePresenceVerifier.php1-103 src/Concerns/ValidatesAttributes.php805-904

PresenceVerifierInterface

The PresenceVerifierInterface defines the contract for database presence verification. It provides two methods for counting records in a database collection (table).

MethodPurposeParametersReturn Type
getCount()Count records matching a single value$collection, $column, $value, $excludeId, $idColumn, $extraint
getMultiCount()Count distinct records matching multiple values$collection, $column, $values, $extraint

The interface uses generic terminology (collection instead of table) to allow for different storage backends, though the primary implementation targets relational databases.

Sources: src/PresenceVerifierInterface.php7-18

DatabasePresenceVerifier Implementation

The DatabasePresenceVerifier class implements the PresenceVerifierInterface using Hyperf's database query builder. It manages database connections and constructs queries with optional conditions.


Key Implementation Details

Connection Resolution

The verifier stores a ConnectionResolverInterface instance and maintains an optional connection name. The table() method resolves the appropriate database connection and returns a query builder with write PDO enabled.

src/DatabasePresenceVerifier.php91-94

Count Operations

The getCount() method performs the following operations:

  1. Creates a base query with a WHERE clause for the specified column and value
  2. Optionally excludes a specific ID (useful for unique validation during updates)
  3. Applies extra conditions via addConditions()
  4. Returns the count

src/DatabasePresenceVerifier.php31-40

The getMultiCount() method handles array values:

  1. Creates a base query with a WHERE IN clause
  2. Applies extra conditions
  3. Uses distinct() to count unique values
  4. Returns the distinct count

src/DatabasePresenceVerifier.php45-50

Sources: src/DatabasePresenceVerifier.php11-103

Conditional Query Building

The addConditions() and addWhere() methods provide flexible query condition handling. Extra conditions can be simple key-value pairs or closures for complex queries.

Condition Types

Condition FormatInterpretationExample
['key' => 'value']Equality check['status' => 'active']WHERE status = 'active'
['key' => 'NULL']Null check['deleted_at' => 'NULL']WHERE deleted_at IS NULL
['key' => 'NOT_NULL']Not null check['email' => 'NOT_NULL']WHERE email IS NOT NULL
['key' => '!value']Inequality check['role' => '!admin']WHERE role != 'admin'
['key' => Closure]Custom query logicClosure receives query builder

Closure Conditions

When a condition value is a Closure, the query builder is passed to the closure, allowing complex nested queries:

src/DatabasePresenceVerifier.php58-61

String Conditions

String values are processed by addWhere(), which interprets special prefixes and values:

src/DatabasePresenceVerifier.php73-86

Sources: src/DatabasePresenceVerifier.php55-86

Database Validation Rules

The validation engine integrates with the presence verifier through two primary validation methods in the ValidatesAttributes trait: validateExists() and validateUnique().

Exists Rule Flow


Parameter Parsing

The validateExists() method parses the first parameter to extract connection and table information:

src/Concerns/ValidatesAttributes.php813

The parseTable() method handles several formats:

  • "table" → Uses default connection
  • "connection.table" → Uses specified connection
  • "App\\Models\\User" → Extracts table and connection from Eloquent model

src/Concerns/ValidatesAttributes.php955-973

Query Column Resolution

If the second parameter is provided, it specifies the database column to check. Otherwise, guessColumnForQuery() infers the column from the attribute name:

src/Concerns/ValidatesAttributes.php978-997

Extra Conditions

Parameters after the second position are parsed as extra conditions in key-value pairs:

src/Concerns/ValidatesAttributes.php1002-1013

Sources: src/Concerns/ValidatesAttributes.php809-855

Unique Rule Flow

The validateUnique() method verifies that a value is unique in the database, with optional exclusion of a specific record (useful during updates).


ID Exclusion

The unique rule supports excluding a specific record from the uniqueness check. This is configured via parameters 2 and 3:

  • Parameter 2: The ID value to exclude (or a placeholder like [user_id] to reference another field)
  • Parameter 3: The ID column name (defaults to 'id')

src/Concerns/ValidatesAttributes.php877-883

The prepareUniqueId() method handles special values:

  • Placeholders like [field_name] are resolved from validation data
  • String 'null' is converted to actual null
  • Numeric strings are converted to integers

src/Concerns/ValidatesAttributes.php921-936

Query Execution

The final query is executed through the presence verifier's getCount() method, which returns 0 if the value is unique (no other records found):

src/Concerns/ValidatesAttributes.php896-903

Sources: src/Concerns/ValidatesAttributes.php864-904

Rule Object Integration

The Exists and Unique rule objects can provide additional query callbacks that are merged into the validation query. These callbacks allow programmatic modification of the underlying database query.

When the validation engine detects that currentRule is an instance of Exists or Unique, it extracts query callbacks and merges them with other extra conditions:

Exists Integration: src/Concerns/ValidatesAttributes.php848-850

Unique Integration: src/Concerns/ValidatesAttributes.php892-894

This design allows rule objects to encapsulate complex query logic while maintaining separation between the rule definition and the validation execution.

Sources: src/Concerns/ValidatesAttributes.php848-850 src/Concerns/ValidatesAttributes.php892-894

Connection Management

The database presence verifier supports multi-connection scenarios where different validation rules may target different databases.

Setting the Connection

The setConnection() method allows the validator to specify which database connection should be used:

src/DatabasePresenceVerifier.php99-102

This connection name is stored in the $connection property and used when building queries:

src/DatabasePresenceVerifier.php93

Connection Resolution Flow


The system resolves connections in the following order:

  1. Explicit connection specified in rule parameter (e.g., 'connection.table')
  2. Connection from Eloquent model (when table parameter is a model class name)
  3. Default connection from ConnectionResolverInterface

Sources: src/DatabasePresenceVerifier.php16 src/DatabasePresenceVerifier.php91-94 src/DatabasePresenceVerifier.php99-102

Write PDO Usage

The table() method explicitly calls useWritePdo() on the query builder:

src/DatabasePresenceVerifier.php93

This ensures that validation queries always use the write connection, preventing issues where:

  • Database replication lag might cause reads from replicas to not reflect recent writes
  • Validation during creation or update operations might incorrectly fail or pass due to stale data on read replicas

By forcing write PDO usage, the validation system guarantees consistency with the most recent database state.

Sources: src/DatabasePresenceVerifier.php93

Integration with Validator

The validator provides access to the presence verifier through the getPresenceVerifier() method. This method is called by validation rules that need database access:

src/Concerns/ValidatesAttributes.php842 src/Concerns/ValidatesAttributes.php888

The presence verifier instance is typically injected into the validator during construction or resolved from the dependency injection container. The validator's factory is responsible for ensuring the presence verifier is available when database validation rules are used.

For more details on validator construction and dependency injection, see Creating Validators and Dependency Injection Integration.

Sources: src/Concerns/ValidatesAttributes.php842 src/Concerns/ValidatesAttributes.php888