2019-09-11 19:25:26 +00:00
|
|
|
<?php
|
|
|
|
/** @license MIT
|
|
|
|
* Copyright 2017 J. King, Dustin Wilson et al.
|
|
|
|
* See LICENSE and AUTHORS files for details */
|
|
|
|
|
|
|
|
declare(strict_types=1);
|
|
|
|
namespace JKingWeb\Arsse\TestCase\Database;
|
|
|
|
|
|
|
|
use JKingWeb\Arsse\Database;
|
|
|
|
|
|
|
|
/** @covers \JKingWeb\Arsse\Database */
|
|
|
|
class TestDatabase extends \JKingWeb\Arsse\Test\AbstractTest {
|
2019-09-12 15:14:30 +00:00
|
|
|
protected $db = null;
|
2020-03-01 20:16:50 +00:00
|
|
|
|
2019-10-16 18:42:43 +00:00
|
|
|
public function setUp(): void {
|
2021-02-27 20:24:02 +00:00
|
|
|
parent::setUp();
|
2019-09-11 19:25:26 +00:00
|
|
|
self::setConf();
|
2019-09-12 15:14:30 +00:00
|
|
|
try {
|
2021-02-27 20:24:02 +00:00
|
|
|
$this->db = new Database;
|
2019-09-12 15:14:30 +00:00
|
|
|
} catch (\JKingWeb\Arsse\Db\Exception $e) {
|
|
|
|
$this->markTestSkipped("SQLite 3 database driver not available");
|
|
|
|
}
|
2019-09-11 19:25:26 +00:00
|
|
|
}
|
|
|
|
|
2019-10-16 18:42:43 +00:00
|
|
|
public function tearDown(): void {
|
2019-09-12 15:14:30 +00:00
|
|
|
$this->db = null;
|
2021-02-27 20:24:02 +00:00
|
|
|
parent::tearDown();
|
|
|
|
}
|
|
|
|
|
|
|
|
protected function invoke(string $method, ...$arg) {
|
|
|
|
$m = new \ReflectionMethod($this->db, $method);
|
|
|
|
$m->setAccessible(true);
|
|
|
|
return $m->invoke($this->db, ...$arg);
|
2019-09-11 19:25:26 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/** @dataProvider provideInClauses */
|
2020-01-20 18:52:48 +00:00
|
|
|
public function testGenerateInClause(string $clause, array $values, array $inV, string $inT): void {
|
2019-09-11 19:25:26 +00:00
|
|
|
$types = array_fill(0, sizeof($values), $inT);
|
|
|
|
$exp = [$clause, $types, $values];
|
2021-02-27 20:24:02 +00:00
|
|
|
$this->assertSame($exp, $this->invoke("generateIn", $inV, $inT));
|
2019-09-11 19:25:26 +00:00
|
|
|
}
|
|
|
|
|
2019-10-16 18:42:43 +00:00
|
|
|
public function provideInClauses(): iterable {
|
2020-03-01 23:32:01 +00:00
|
|
|
$l = (new \ReflectionClassConstant(Database::class, "LIMIT_SET_SIZE"))->getValue() + 1;
|
2019-09-11 19:25:26 +00:00
|
|
|
$strings = array_fill(0, $l, "");
|
|
|
|
$ints = range(1, $l);
|
2020-03-01 23:32:01 +00:00
|
|
|
$longString = str_repeat("0", (new \ReflectionClassConstant(Database::class, "LIMIT_SET_STRING_LENGTH"))->getValue() + 1);
|
2019-09-11 19:25:26 +00:00
|
|
|
$params = implode(",", array_fill(0, $l, "?"));
|
|
|
|
$intList = implode(",", $ints);
|
|
|
|
$stringList = implode(",", array_fill(0, $l, "''"));
|
|
|
|
return [
|
|
|
|
["null", [], [], "str"],
|
|
|
|
["?", [1], [1], "int"],
|
|
|
|
["?", ["1"], ["1"], "int"],
|
|
|
|
["?,?", [null, null], [null, null], "str"],
|
|
|
|
["null", [], array_fill(0, $l, null), "str"],
|
|
|
|
["$intList", [], $ints, "int"],
|
2020-03-01 20:16:50 +00:00
|
|
|
["$intList,".($l + 1), [], array_merge($ints, [$l + 1]), "int"],
|
2019-09-11 19:25:26 +00:00
|
|
|
["$intList,0", [], array_merge($ints, ["OOK"]), "int"],
|
|
|
|
["$intList", [], array_merge($ints, [null]), "int"],
|
|
|
|
["$stringList,''", [], array_merge($strings, [""]), "str"],
|
|
|
|
["$stringList", [], array_merge($strings, [null]), "str"],
|
|
|
|
["$stringList,?", [$longString], array_merge($strings, [$longString]), "str"],
|
|
|
|
["$stringList,'A''s'", [], array_merge($strings, ["A's"]), "str"],
|
2019-09-12 13:53:43 +00:00
|
|
|
["$stringList,?", ["???"], array_merge($strings, ["???"]), "str"],
|
2019-09-11 19:25:26 +00:00
|
|
|
["$params", $ints, $ints, "bool"],
|
|
|
|
];
|
|
|
|
}
|
2019-09-12 13:41:01 +00:00
|
|
|
|
|
|
|
/** @dataProvider provideSearchClauses */
|
2020-01-20 18:52:48 +00:00
|
|
|
public function testGenerateSearchClause(string $clause, array $values, array $inV, array $inC, bool $inAny): void {
|
2019-09-12 13:41:01 +00:00
|
|
|
// this is not an exhaustive test; integration tests already cover the ins and outs of the functionality
|
|
|
|
$types = array_fill(0, sizeof($values), "str");
|
|
|
|
$exp = [$clause, $types, $values];
|
2021-02-27 20:24:02 +00:00
|
|
|
$this->assertSame($exp, $this->invoke("generateSearch", $inV, $inC, $inAny));
|
2019-09-12 13:41:01 +00:00
|
|
|
}
|
|
|
|
|
2019-10-16 18:42:43 +00:00
|
|
|
public function provideSearchClauses(): iterable {
|
2020-03-01 23:32:01 +00:00
|
|
|
$setSize = (new \ReflectionClassConstant(Database::class, "LIMIT_SET_SIZE"))->getValue();
|
|
|
|
$terms = array_fill(0, $setSize + 1, "a");
|
|
|
|
$clause = array_fill(0, $setSize + 1, "test like '%a%' escape '^'");
|
|
|
|
$longString = str_repeat("0", (new \ReflectionClassConstant(Database::class, "LIMIT_SET_STRING_LENGTH"))->getValue() + 1);
|
2019-09-12 13:41:01 +00:00
|
|
|
return [
|
|
|
|
["test like ? escape '^'", ["%a%"], ["a"], ["test"], true],
|
|
|
|
["(col1 like ? escape '^' or col2 like ? escape '^')", ["%a%", "%a%"], ["a"], ["col1", "col2"], true],
|
|
|
|
["(".implode(" or ", $clause).")", [], $terms, ["test"], true],
|
|
|
|
["(".implode(" and ", $clause).")", [], $terms, ["test"], false],
|
|
|
|
["(".implode(" or ", $clause)." or test like ? escape '^')", ["%$longString%"], array_merge($terms, [$longString]), ["test"], true],
|
2019-09-12 13:53:43 +00:00
|
|
|
["(".implode(" or ", $clause)." or test like ? escape '^')", ["%Eh?%"], array_merge($terms, ["Eh?"]), ["test"], true],
|
|
|
|
["(".implode(" or ", $clause)." or test like ? escape '^')", ["%?%"], array_merge($terms, ["?"]), ["test"], true],
|
2019-09-12 13:41:01 +00:00
|
|
|
];
|
|
|
|
}
|
2019-09-11 19:25:26 +00:00
|
|
|
}
|