Skip to content

Commit

Permalink
[11.x] Support named in-memory SQLite connections (#53635)
Browse files Browse the repository at this point in the history
* [11.x] Support named in-memory SQLite connections

* code style

* apply change to SQLiteBuilder & SqliteSchemaState

* add connector test

* foramtting

---------

Co-authored-by: Taylor Otwell <taylor@laravel.com>
  • Loading branch information
stancl and taylorotwell authored Nov 25, 2024
1 parent a041617 commit a2bcf35
Show file tree
Hide file tree
Showing 4 changed files with 31 additions and 5 deletions.
9 changes: 6 additions & 3 deletions src/Illuminate/Database/Connectors/SQLiteConnector.php
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,12 @@ public function connect(array $config)

// SQLite supports "in-memory" databases that only last as long as the owning
// connection does. These are useful for tests or for short lifetime store
// querying. In-memory databases may only have a single open connection.
if ($config['database'] === ':memory:') {
return $this->createConnection('sqlite::memory:', $config, $options);
// querying. In-memory databases shall be anonymous (:memory:) or named.
if ($config['database'] === ':memory:' ||
str_contains($config['database'], '?mode=memory') ||
str_contains($config['database'], '&mode=memory')
) {
return $this->createConnection('sqlite:'.$config['database'], $config, $options);
}

$path = realpath($config['database']);
Expand Down
7 changes: 6 additions & 1 deletion src/Illuminate/Database/Schema/SQLiteBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,12 @@ public function getColumns($table)
*/
public function dropAllTables()
{
if ($this->connection->getDatabaseName() !== ':memory:') {
$database = $this->connection->getDatabaseName();

if ($database !== ':memory:' &&
! str_contains($database, '?mode=memory') &&
! str_contains($database, '&mode=memory')
) {
return $this->refreshDatabaseFile();
}

Expand Down
7 changes: 6 additions & 1 deletion src/Illuminate/Database/Schema/SqliteSchemaState.php
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,12 @@ protected function appendMigrationData(string $path)
*/
public function load($path)
{
if ($this->connection->getDatabaseName() === ':memory:') {
$database = $this->connection->getDatabaseName();

if ($database === ':memory:' ||
str_contains($database, '?mode=memory') ||
str_contains($database, '&mode=memory')
) {
$this->connection->getPdo()->exec($this->files->get($path));

return;
Expand Down
13 changes: 13 additions & 0 deletions tests/Database/DatabaseConnectorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -270,6 +270,19 @@ public function testSQLiteMemoryDatabasesMayBeConnectedTo()
$this->assertSame($result, $connection);
}

public function testSQLiteNamedMemoryDatabasesMayBeConnectedTo()
{
$dsn = 'sqlite:file:mydb?mode=memory&cache=shared';
$config = ['database' => 'file:mydb?mode=memory&cache=shared'];
$connector = $this->getMockBuilder(SQLiteConnector::class)->onlyMethods(['createConnection', 'getOptions'])->getMock();
$connection = m::mock(stdClass::class);
$connector->expects($this->once())->method('getOptions')->with($this->equalTo($config))->willReturn(['options']);
$connector->expects($this->once())->method('createConnection')->with($this->equalTo($dsn), $this->equalTo($config), $this->equalTo(['options']))->willReturn($connection);
$result = $connector->connect($config);

$this->assertSame($result, $connection);
}

public function testSQLiteFileDatabasesMayBeConnectedTo()
{
$dsn = 'sqlite:'.__DIR__;
Expand Down

0 comments on commit a2bcf35

Please sign in to comment.