Skip to content

Commit

Permalink
Merge 5789aa3 into 1716c6e
Browse files Browse the repository at this point in the history
  • Loading branch information
Zlob committed Dec 9, 2019
2 parents 1716c6e + 5789aa3 commit f75ada5
Show file tree
Hide file tree
Showing 3 changed files with 175 additions and 0 deletions.
45 changes: 45 additions & 0 deletions src/PostgresConnection.php
Expand Up @@ -4,10 +4,12 @@

namespace Umbrellio\Postgres;

use DateTimeInterface;
use Doctrine\DBAL\Connection;
use Doctrine\DBAL\Events;
use Illuminate\Database\PostgresConnection as BasePostgresConnection;
use Illuminate\Support\Traits\Macroable;
use PDO;
use Umbrellio\Postgres\Extensions\AbstractExtension;
use Umbrellio\Postgres\Extensions\Exceptions\ExtensionInvalidException;
use Umbrellio\Postgres\Schema\Builder;
Expand Down Expand Up @@ -58,6 +60,49 @@ public function getDoctrineConnection(): Connection
return $doctrineConnection;
}

public function bindValues($statement, $bindings)
{
if ($this->pdo->getAttribute(PDO::ATTR_EMULATE_PREPARES)) {
foreach ($bindings as $key => $value) {
$parameter = is_string($key) ? $key : $key + 1;

switch (true) {
case is_bool($value):
$dataType = PDO::PARAM_BOOL;
break;

case $value === null:
$dataType = PDO::PARAM_NULL;
break;

default:
$dataType = PDO::PARAM_STR;
}

$statement->bindValue($parameter, $value, $dataType);
}
} else {
parent::bindValues($statement, $bindings);
}
}

public function prepareBindings(array $bindings)
{
if ($this->pdo->getAttribute(PDO::ATTR_EMULATE_PREPARES)) {
$grammar = $this->getQueryGrammar();

foreach ($bindings as $key => $value) {
if ($value instanceof DateTimeInterface) {
$bindings[$key] = $value->format($grammar->getDateFormat());
}
}

return $bindings;
}

return parent::prepareBindings($bindings);
}

protected function getDefaultSchemaGrammar()
{
return $this->withTablePrefix(new PostgresGrammar());
Expand Down
121 changes: 121 additions & 0 deletions tests/Functional/Connection/ConnectionTest.php
@@ -0,0 +1,121 @@
<?php

declare(strict_types=1);

namespace Umbrellio\Postgres\Tests\Functional\Connection;

use Illuminate\Foundation\Testing\Concerns\InteractsWithDatabase;
use Illuminate\Foundation\Testing\DatabaseTransactions;
use Illuminate\Support\Carbon;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Schema;
use Umbrellio\Postgres\Schema\Blueprint;
use Umbrellio\Postgres\Tests\FunctionalTestCase;

class ConnectionTest extends FunctionalTestCase
{
use DatabaseTransactions, InteractsWithDatabase;

protected $emulatePrepares = true;

/**
* @test
* @dataProvider boolDataProvider
*/
public function boolTrueBindingsWorks($value)
{
$table = 'test_table';
$data = ['field' => $value];
Schema::create($table, function (Blueprint $table) {
$table->increments('id');
$table->boolean('field');
});
DB::table($table)->insert($data);
$result = DB::table($table)->select($data);
$this->assertSame(1, $result->count());
}

/**
* @test
* @dataProvider intDataProvider
*/
public function intBindingsWorks($value)
{
$table = 'test_table';
$data = ['field' => $value];
Schema::create($table, function (Blueprint $table) {
$table->increments('id');
$table->integer('field');
});
DB::table($table)->insert($data);
$result = DB::table($table)->select($data);
$this->assertSame(1, $result->count());
}

/**
* @test
*/
public function stringBindingsWorks()
{
$table = 'test_table';
$data = ['field' => 'string'];
Schema::create($table, function (Blueprint $table) {
$table->increments('id');
$table->string('field');
});
DB::table($table)->insert($data);
$result = DB::table($table)->select($data);
$this->assertSame(1, $result->count());
}

/**
* @test
*/
public function nullBindingsWorks()
{
$table = 'test_table';
$data = ['field' => null];
Schema::create($table, function (Blueprint $table) {
$table->increments('id');
$table->string('field')->nullable();
});
DB::table($table)->insert($data);
$result = DB::table($table)->whereNull('field')->get();
$this->assertSame(1, $result->count());
}

/**
* @test
* @dataProvider dateDataProvider
*/
public function dateTimeBindingsWorks($value)
{
$table = 'test_table';
$data = ['field' => $value];
Schema::create($table, function (Blueprint $table) {
$table->increments('id');
$table->dateTime('field');
});
DB::table($table)->insert($data);
$result = DB::table($table)->select($data);
$this->assertSame(1, $result->count());
}

public function boolDataProvider()
{
yield 'true' => [true];
yield 'false' => [false];
}

public function intDataProvider()
{
yield 'zero' => [0];
yield 'non-zero' => [10];
}

public function dateDataProvider()
{
yield 'as string' => ['2019-01-01 13:12:22'];
yield 'as Carbon object' => [new Carbon('2019-01-01 13:12:22')];
}
}
9 changes: 9 additions & 0 deletions tests/FunctionalTestCase.php
Expand Up @@ -5,9 +5,12 @@
namespace Umbrellio\Postgres\Tests;

use Illuminate\Support\Facades\Facade;
use PDO;

abstract class FunctionalTestCase extends TestCase
{
protected $emulatePrepares = false;

protected function setUp(): void
{
parent::setUp();
Expand All @@ -33,6 +36,12 @@ protected function getEnvironmentSetUp($app): void
'prefix' => '',
'schema' => 'public',
]);

if ($this->emulatePrepares) {
$app['config']->set('database.connections.main.options', [
PDO::ATTR_EMULATE_PREPARES => true,
]);
}
}

private function getConnectionParams(): array
Expand Down

0 comments on commit f75ada5

Please sign in to comment.