419 lines
18 KiB
PHP
419 lines
18 KiB
PHP
|
<?php
|
||
|
/**
|
||
|
* @author Daniel J. Summers <daniel@bitbadger.solutions>
|
||
|
* @license MIT
|
||
|
*/
|
||
|
|
||
|
declare(strict_types=1);
|
||
|
|
||
|
use BitBadger\PDODocument\{Configuration, Field, Mode, Op};
|
||
|
|
||
|
pest()->group('unit');
|
||
|
|
||
|
describe('->appendParameter()', function () {
|
||
|
afterEach(function () { Configuration::overrideMode(null); });
|
||
|
test('appends no parameter for exists', function () {
|
||
|
expect(Field::exists('exists')->appendParameter([]))->toBeEmpty();
|
||
|
});
|
||
|
test('appends no parameter for notExists', function () {
|
||
|
expect(Field::notExists('absent')->appendParameter([]))->toBeEmpty();
|
||
|
});
|
||
|
test('appends two parameters for between', function () {
|
||
|
expect(Field::between('exists', 5, 9, '@num')->appendParameter([]))
|
||
|
->toHaveLength(2)
|
||
|
->toEqual(['@nummin' => 5, '@nummax' => 9]);
|
||
|
});
|
||
|
test('appends a parameter for each value for in', function () {
|
||
|
expect(Field::in('it', ['test', 'unit', 'great'], ':val')->appendParameter([]))
|
||
|
->toHaveLength(3)
|
||
|
->toEqual([':val_0' => 'test', ':val_1' => 'unit', ':val_2' => 'great']);
|
||
|
});
|
||
|
test('appends a parameter for each value for inArray [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::inArray('it', 'table', [2, 8, 64], ':bit')->appendParameter([]))
|
||
|
->toHaveLength(3)
|
||
|
->toEqual([':bit_0' => '2', ':bit_1' => '8', ':bit_2' => '64']);
|
||
|
})->group('postgresql');
|
||
|
test('appends a parameter for each value for inArray [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::inArray('it', 'table', [2, 8, 64], ':bit')->appendParameter([]))
|
||
|
->toHaveLength(3)
|
||
|
->toEqual([':bit_0' => 2, ':bit_1' => 8, ':bit_2' => 64]);
|
||
|
})->group('sqlite');
|
||
|
test('appends a parameter for other operators', function () {
|
||
|
expect(Field::equal('the_field', 33, ':test')->appendParameter([]))
|
||
|
->toHaveLength(1)
|
||
|
->toEqual([':test' => 33]);
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('->path()', function () {
|
||
|
afterEach(function () { Configuration::overrideMode(null); });
|
||
|
test('returns simple SQL path [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::equal('it', 'that'))->path()->toBe("data->>'it'");
|
||
|
})->group('postgresql');
|
||
|
test('returns simple SQL path [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::equal('top', 'that'))->path()->toBe("data->>'top'");
|
||
|
})->group('sqlite');
|
||
|
test('returns nested SQL path [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::equal('parts.to.the.path', ''))->path()->toBe("data#>>'{parts,to,the,path}'");
|
||
|
})->group('postgresql');
|
||
|
test('returns nested SQL path [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::equal('one.two.three', ''))->path()->toBe("data->'one'->'two'->>'three'");
|
||
|
})->group('sqlite');
|
||
|
test('returns simple JSON path [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::equal('it', 'that'))->path(true)->toBe("data->'it'");
|
||
|
})->group('postgresql');
|
||
|
test('returns simple JSON path [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::equal('top', 'that'))->path(true)->toBe("data->'top'");
|
||
|
})->group('sqlite');
|
||
|
test('returns nested JSON path [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::equal('parts.to.the.path', ''))->path(true)->toBe("data#>'{parts,to,the,path}'");
|
||
|
})->group('postgresql');
|
||
|
test('returns nested JSON path [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::equal('one.two.three', ''))->path(true)->toBe("data->'one'->'two'->'three'");
|
||
|
})->group('sqlite');
|
||
|
});
|
||
|
|
||
|
describe('->toWhere()', function () {
|
||
|
afterEach(function () { Configuration::overrideMode(null); });
|
||
|
test('generates IS NOT NULL for exists w/o qualifier [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::exists('that_field'))->toWhere()->toBe("data->>'that_field' IS NOT NULL");
|
||
|
})->group('postgresql');
|
||
|
test('generates IS NOT NULL for exists w/o qualifier [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::exists('that_field'))->toWhere()->toBe("data->>'that_field' IS NOT NULL");
|
||
|
})->group('sqlite');
|
||
|
test('generates IS NULL for notExists w/o qualifier [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::notExists('a_field'))->toWhere()->toBe("data->>'a_field' IS NULL");
|
||
|
})->group('postgresql');
|
||
|
test('generates IS NULL for notExists w/o qualifier [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::notExists('a_field'))->toWhere()->toBe("data->>'a_field' IS NULL");
|
||
|
})->group('sqlite');
|
||
|
test('generates BETWEEN for between w/o qualifier [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::between('age', 13, 17, '@age'))->toWhere()->toBe("data->>'age' BETWEEN @agemin AND @agemax");
|
||
|
})->group('sqlite');
|
||
|
test('generates BETWEEN for between w/o qualifier, numeric range [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::between('age', 13, 17, '@age'))->toWhere()
|
||
|
->toBe("(data->>'age')::numeric BETWEEN @agemin AND @agemax");
|
||
|
})->group('postgresql');
|
||
|
test('generates BETWEEN for between w/o qualifier, non-numeric range [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::between('city', 'Atlanta', 'Chicago', ':city'))->toWhere()
|
||
|
->toBe("data->>'city' BETWEEN :citymin AND :citymax");
|
||
|
})->group('postgresql');
|
||
|
test('generates BETWEEN for between w/ qualifier [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
$field = Field::between('age', 13, 17, '@age');
|
||
|
$field->qualifier = 'me';
|
||
|
expect($field)->toWhere()->toBe("me.data->>'age' BETWEEN @agemin AND @agemax");
|
||
|
})->group('sqlite');
|
||
|
test('generates BETWEEN for between w/ qualifier, numeric range [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
$field = Field::between('age', 13, 17, '@age');
|
||
|
$field->qualifier = 'me';
|
||
|
expect($field)->toWhere()->toBe("(me.data->>'age')::numeric BETWEEN @agemin AND @agemax");
|
||
|
})->group('postgresql');
|
||
|
test('generates BETWEEN for between w/ qualifier, non-numeric range [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
$field = Field::between('city', 'Atlanta', 'Chicago', ':city');
|
||
|
$field->qualifier = 'me';
|
||
|
expect($field)->toWhere()->toBe("me.data->>'city' BETWEEN :citymin AND :citymax");
|
||
|
})->group('postgresql');
|
||
|
test('generates IN for in, non-numeric values [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::in('test', ['Atlanta', 'Chicago'], ':city'))->toWhere()
|
||
|
->toBe("data->>'test' IN (:city_0, :city_1)");
|
||
|
})->group('postgresql');
|
||
|
test('generates IN for in, numeric values [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::in('even', [2, 4, 6], ':nbr'))->toWhere()
|
||
|
->toBe("(data->>'even')::numeric IN (:nbr_0, :nbr_1, :nbr_2)");
|
||
|
})->group('postgresql');
|
||
|
test('generates IN for in [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::in('test', ['Atlanta', 'Chicago'], ':city'))->toWhere()
|
||
|
->toBe("data->>'test' IN (:city_0, :city_1)");
|
||
|
})->group('sqlite');
|
||
|
test('generates clause for inArray [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::inArray('even', 'tbl', [2, 4, 6, 8], ':it'))->toWhere()
|
||
|
->toBe("data->'even' ??| ARRAY[:it_0, :it_1, :it_2, :it_3]");
|
||
|
})->group('postgresql');
|
||
|
test('generates clause for inArray [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::inArray('test', 'tbl', ['Atlanta', 'Chicago'], ':city'))->toWhere()
|
||
|
->toBe("EXISTS (SELECT 1 FROM json_each(tbl.data, '\$.test') WHERE value IN (:city_0, :city_1))");
|
||
|
})->group('sqlite');
|
||
|
test('generates clause for other operators w/o qualifier [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
expect(Field::equal('some_field', '', ':value'))->toWhere()->toBe("data->>'some_field' = :value");
|
||
|
})->group('postgresql');
|
||
|
test('generates clause for other operators w/o qualifier [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
expect(Field::equal('some_field', '', ':value'))->toWhere()->toBe("data->>'some_field' = :value");
|
||
|
})->group('sqlite');
|
||
|
test('generates no-parameter clause w/ qualifier [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
$field = Field::exists('no_field');
|
||
|
$field->qualifier = 'test';
|
||
|
expect($field)->toWhere()->toBe("test.data->>'no_field' IS NOT NULL");
|
||
|
})->group('postgresql');
|
||
|
test('generates no-parameter clause w/ qualifier [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
$field = Field::exists('no_field');
|
||
|
$field->qualifier = 'test';
|
||
|
expect($field)->toWhere()->toBe("test.data->>'no_field' IS NOT NULL");
|
||
|
})->group('sqlite');
|
||
|
test('generates parameter clause w/ qualifier [PostgreSQL]', function () {
|
||
|
Configuration::overrideMode(Mode::PgSQL);
|
||
|
$field = Field::lessOrEqual('le_field', 18, ':it');
|
||
|
$field->qualifier = 'q';
|
||
|
expect($field)->toWhere()->toBe("(q.data->>'le_field')::numeric <= :it");
|
||
|
})->group('postgresql');
|
||
|
test('generates parameter clause w/ qualifier [SQLite]', function () {
|
||
|
Configuration::overrideMode(Mode::SQLite);
|
||
|
$field = Field::lessOrEqual('le_field', 18, ':it');
|
||
|
$field->qualifier = 'q';
|
||
|
expect($field)->toWhere()->toBe("q.data->>'le_field' <= :it");
|
||
|
})->group('sqlite');
|
||
|
});
|
||
|
|
||
|
describe('::equal()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::equal('my_test', 9);
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('my_test')
|
||
|
->op->toBe(Op::Equal)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toBe(9);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::equal('another_test', 'turkey', ':test');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('another_test')
|
||
|
->op->toBe(Op::Equal)
|
||
|
->paramName->toBe(':test')
|
||
|
->and($field->value)->toBe('turkey');
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::greater()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::greater('your_test', 4);
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('your_test')
|
||
|
->op->toBe(Op::Greater)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toBe(4);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::greater('more_test', 'chicken', ':value');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('more_test')
|
||
|
->op->toBe(Op::Greater)
|
||
|
->paramName->toBe(':value')
|
||
|
->and($field->value)->toBe('chicken');
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::greaterOrEqual()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::greaterOrEqual('their_test', 6);
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('their_test')
|
||
|
->op->toBe(Op::GreaterOrEqual)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toBe(6);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::greaterOrEqual('greater_test', 'poultry', ':cluck');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('greater_test')
|
||
|
->op->toBe(Op::GreaterOrEqual)
|
||
|
->paramName->toBe(':cluck')
|
||
|
->and($field->value)->toBe('poultry');
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::less()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::less('z', 32);
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('z')
|
||
|
->op->toBe(Op::Less)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toBe(32);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::less('additional_test', 'fowl', ':boo');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('additional_test')
|
||
|
->op->toBe(Op::Less)
|
||
|
->paramName->toBe(':boo')
|
||
|
->and($field->value)->toBe('fowl');
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::lessOrEqual()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::lessOrEqual('g', 87);
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('g')
|
||
|
->op->toBe(Op::LessOrEqual)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toBe(87);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::lessOrEqual('lesser_test', 'hen', ':woo');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('lesser_test')
|
||
|
->op->toBe(Op::LessOrEqual)
|
||
|
->paramName->toBe(':woo')
|
||
|
->and($field->value)->toBe('hen');
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::notEqual()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::notEqual('j', 65);
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('j')
|
||
|
->op->toBe(Op::NotEqual)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toBe(65);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::notEqual('unequal_test', 'egg', ':zoo');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('unequal_test')
|
||
|
->op->toBe(Op::NotEqual)
|
||
|
->paramName->toBe(':zoo')
|
||
|
->and($field->value)->toBe('egg');
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::between()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::between('k', 'alpha', 'zed');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('k')
|
||
|
->op->toBe(Op::Between)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toEqual(['alpha', 'zed']);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::between('between_test', 18, 49, ':count');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('between_test')
|
||
|
->op->toBe(Op::Between)
|
||
|
->paramName->toBe(':count')
|
||
|
->and($field->value)->toEqual([18, 49]);
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::in()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::in('test', [1, 2, 3]);
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('test')
|
||
|
->op->toBe(Op::In)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toEqual([1, 2, 3]);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::in('unit', ['a', 'b'], ':inParam');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('unit')
|
||
|
->op->toBe(Op::In)
|
||
|
->paramName->toBe(':inParam')
|
||
|
->and($field->value)->toEqual(['a', 'b']);
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::inArray()', function () {
|
||
|
test('creates Field w/o parameter', function () {
|
||
|
$field = Field::inArray('test', 'tbl', [1, 2, 3]);
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('test')
|
||
|
->op->toBe(Op::InArray)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toEqual(['table' => 'tbl', 'values' => [1, 2, 3]]);
|
||
|
});
|
||
|
test('creates Field w/ parameter', function () {
|
||
|
$field = Field::inArray('unit', 'tab', ['a', 'b'], ':inAParam');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('unit')
|
||
|
->op->toBe(Op::InArray)
|
||
|
->paramName->toBe(':inAParam')
|
||
|
->and($field->value)->toEqual(['table' => 'tab', 'values' => ['a', 'b']]);
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::exists()', function () {
|
||
|
test('creates Field', function () {
|
||
|
$field = Field::exists('be_there');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('be_there')
|
||
|
->op->toBe(Op::Exists)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toBeEmpty();
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::notExists()', function () {
|
||
|
test('creates Field', function () {
|
||
|
$field = Field::notExists('be_absent');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('be_absent')
|
||
|
->op->toBe(Op::NotExists)
|
||
|
->paramName->toBeEmpty()
|
||
|
->and($field->value)->toBeEmpty();
|
||
|
});
|
||
|
});
|
||
|
|
||
|
describe('::named()', function () {
|
||
|
test('creates Field', function () {
|
||
|
$field = Field::named('the_field');
|
||
|
expect($field)
|
||
|
->not->toBeNull()
|
||
|
->fieldName->toBe('the_field')
|
||
|
->op->toBe(Op::Equal)
|
||
|
->value->toBeEmpty()
|
||
|
->and($field->value)->toBeEmpty();
|
||
|
});
|
||
|
});
|