WhereSpecification
A built-in specification for basic WHERE clause conditions. This is the most commonly used specification for simple equality and comparison operations.
Namespace
php
DangerWayne\Specification\Specifications\Common\WhereSpecification
Constructor
php
public function __construct(
string $field,
mixed $operator = null,
mixed $value = null
)
Parameters
$field
(string) - The database column or field name$operator
(mixed) - The comparison operator (optional, defaults to '=')$value
(mixed) - The value to compare against (optional if operator is value)
Operator Signatures
The constructor supports two signatures:
php
// Two parameters: field and value (assumes '=' operator)
new WhereSpecification('status', 'active');
// Three parameters: field, operator, and value
new WhereSpecification('age', '>=', 18);
Supported Operators
=
- Equal!=
or<>
- Not equal>
- Greater than>=
- Greater than or equal<
- Less than<=
- Less than or equallike
- SQL LIKE operatornot like
- SQL NOT LIKE operator
Usage Examples
Basic Equality
php
use DangerWayne\Specification\Specifications\Common\WhereSpecification;
// Check for active status
$activeSpec = new WhereSpecification('status', 'active');
// Apply to query
$activeUsers = User::whereSpecification($activeSpec)->get();
// Use with in-memory collection
$users = User::all();
$activeUsers = $users->filter(function($user) use ($activeSpec) {
return $activeSpec->isSatisfiedBy($user);
});
Comparison Operators
php
// Age greater than or equal to 18
$adultSpec = new WhereSpecification('age', '>=', 18);
// Price less than 100
$affordableSpec = new WhereSpecification('price', '<', 100);
// Not equal
$notDeletedSpec = new WhereSpecification('status', '!=', 'deleted');
LIKE Operator
php
// Search for names starting with 'John'
$nameSpec = new WhereSpecification('name', 'like', 'John%');
// Search for emails containing 'gmail'
$emailSpec = new WhereSpecification('email', 'like', '%gmail%');
// Not like
$notGmailSpec = new WhereSpecification('email', 'not like', '%gmail%');
Combining with Other Specifications
AND Combinations
php
$activeSpec = new WhereSpecification('status', 'active');
$verifiedSpec = new WhereSpecification('email_verified_at', '!=', null);
// Active AND verified users
$activeVerifiedSpec = $activeSpec->and($verifiedSpec);
$users = User::whereSpecification($activeVerifiedSpec)->get();
OR Combinations
php
$adminSpec = new WhereSpecification('role', 'admin');
$moderatorSpec = new WhereSpecification('role', 'moderator');
// Admin OR moderator
$staffSpec = $adminSpec->or($moderatorSpec);
$staffUsers = User::whereSpecification($staffSpec)->get();
Complex Combinations
php
$activeSpec = new WhereSpecification('status', 'active');
$premiumSpec = new WhereSpecification('subscription', 'premium');
$oldAccountSpec = new WhereSpecification('created_at', '<', now()->subYear());
// (Active AND Premium) OR Old Account
$complexSpec = $activeSpec->and($premiumSpec)->or($oldAccountSpec);
Real-World Examples
E-commerce Product Filtering
php
// Products on sale
$onSaleSpec = new WhereSpecification('sale_price', '!=', null);
// Products in stock
$inStockSpec = new WhereSpecification('stock_quantity', '>', 0);
// Featured products
$featuredSpec = new WhereSpecification('is_featured', true);
// Combine: Featured products on sale and in stock
$hotDealsSpec = $featuredSpec
->and($onSaleSpec)
->and($inStockSpec);
$hotDeals = Product::whereSpecification($hotDealsSpec)->get();
User Account Management
php
// Active accounts
$activeSpec = new WhereSpecification('status', 'active');
// Email verified
$verifiedSpec = new WhereSpecification('email_verified_at', '!=', null);
// Recently active (logged in within 30 days)
$recentSpec = new WhereSpecification('last_login_at', '>=', now()->subDays(30));
// Active, verified, and recently logged in users
$engagedUsersSpec = $activeSpec
->and($verifiedSpec)
->and($recentSpec);
$engagedUsers = User::whereSpecification($engagedUsersSpec)->get();
Content Moderation
php
// Published content
$publishedSpec = new WhereSpecification('status', 'published');
// Safe content (not flagged)
$safeSpec = new WhereSpecification('is_flagged', false);
// Recent content (last 7 days)
$recentSpec = new WhereSpecification('created_at', '>=', now()->subDays(7));
// Published, safe, recent content
$displayableSpec = $publishedSpec
->and($safeSpec)
->and($recentSpec);
$content = Post::whereSpecification($displayableSpec)->get();
Implementation Details
isSatisfiedBy() Method
The isSatisfiedBy()
method evaluates the candidate's field value:
php
public function isSatisfiedBy(mixed $candidate): bool
{
$value = data_get($candidate, $this->field);
return match($this->operator) {
'=' => $value == $this->value,
'!=' => $value != $this->value,
'>' => $value > $this->value,
'>=' => $value >= $this->value,
'<' => $value < $this->value,
'<=' => $value <= $this->value,
'like' => str_contains($value, str_replace('%', '', $this->value)),
'not like' => !str_contains($value, str_replace('%', '', $this->value)),
default => false,
};
}
toQuery() Method
The toQuery()
method applies the condition to the Eloquent builder:
php
public function toQuery(Builder $query): Builder
{
return $query->where($this->field, $this->operator, $this->value);
}
Performance Considerations
- Index Usage: Ensure database columns used in WhereSpecification have appropriate indexes
- LIKE Performance: Leading wildcards (
%value
) prevent index usage - Type Coercion: Be aware of type comparisons in
isSatisfiedBy()
- Null Handling: Use
WhereNullSpecification
for NULL checks instead
Common Patterns
Nullable Fields
php
// Don't use WhereSpecification for NULL checks
// Bad
$notNullSpec = new WhereSpecification('field', '!=', null);
// Good - use WhereNullSpecification
$notNullSpec = new WhereNullSpecification('field', false);
Date Comparisons
php
// Recent records
$recentSpec = new WhereSpecification('created_at', '>=', now()->subDays(30));
// Date range (combine with WhereBetweenSpecification for better performance)
$startSpec = new WhereSpecification('date', '>=', $startDate);
$endSpec = new WhereSpecification('date', '<=', $endDate);
$dateRangeSpec = $startSpec->and($endSpec);
Boolean Fields
php
// Active flag
$activeSpec = new WhereSpecification('is_active', true);
// Soft deletes
$notDeletedSpec = new WhereSpecification('deleted_at', null);
Testing
php
use Tests\TestCase;
use App\Models\User;
use DangerWayne\Specification\Specifications\Common\WhereSpecification;
class WhereSpecificationTest extends TestCase
{
public function test_it_filters_by_status()
{
User::factory()->create(['status' => 'active']);
User::factory()->create(['status' => 'inactive']);
$spec = new WhereSpecification('status', 'active');
$users = User::whereSpecification($spec)->get();
$this->assertCount(1, $users);
$this->assertEquals('active', $users->first()->status);
}
public function test_it_handles_comparison_operators()
{
User::factory()->create(['age' => 17]);
User::factory()->create(['age' => 18]);
User::factory()->create(['age' => 25]);
$spec = new WhereSpecification('age', '>=', 18);
$adults = User::whereSpecification($spec)->get();
$this->assertCount(2, $adults);
}
}
See Also
- WhereInSpecification - For IN clause conditions
- WhereBetweenSpecification - For BETWEEN conditions
- WhereNullSpecification - For NULL/NOT NULL checks
- WhereHasSpecification - For relationship conditions