-
Notifications
You must be signed in to change notification settings - Fork 6
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add support for creating namespaced databases (#294)
### TL;DR Added support for namespaced databases with automatic creation and migration capabilities. ### What changed? - Introduced `NewNamespacedDB` function to create and manage isolated database instances - Refactored database connection logic into smaller, focused functions - Added `createNamespace` function to handle database creation - Implemented `waitUntilDBReady` for connection readiness checks - Added unit tests to verify namespaced database functionality - Made test database DSN constants public for reuse ### How to test? 1. Run the new unit test `TestNamespacedDB` 2. Verify that a new database is created with the specified namespace 3. Confirm that the created database is properly initialized with migrations 4. Check that the database name matches the provided namespace ### Why make this change? This change enables better isolation between different database instances, allowing for separate namespaces per instance. This is particularly useful for testing scenarios and multi-tenant applications where data separation is crucial. ## Ticket #225 <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit - **New Features** - Introduced a function to check database readiness and a function to create a namespaced database. - Enhanced database configuration handling with a new parsing function. - **Bug Fixes** - Improved error handling during namespace creation. - **Tests** - Added tests to validate the creation and querying of namespaced databases, including support for multiple instances with the same name and error handling for invalid inputs. - **Documentation** - Updated visibility of constants for better accessibility in the test utilities. <!-- end of auto-generated comment: release notes by coderabbit.ai -->
- Loading branch information
Showing
3 changed files
with
216 additions
and
16 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
package db | ||
|
||
import ( | ||
"context" | ||
"testing" | ||
"time" | ||
|
||
"github.com/stretchr/testify/require" | ||
"github.com/xmtp/xmtpd/pkg/testutils" | ||
) | ||
|
||
func TestNamespacedDB(t *testing.T) { | ||
startingDsn := testutils.LocalTestDBDSNPrefix + "/foo" + testutils.LocalTestDBDSNSuffix | ||
newDBName := "xmtp_" + testutils.RandomString(24) | ||
// Create namespaced DB | ||
namespacedDB, err := NewNamespacedDB( | ||
context.Background(), | ||
startingDsn, | ||
newDBName, | ||
time.Second, | ||
time.Second, | ||
) | ||
t.Cleanup(func() { namespacedDB.Close() }) | ||
require.NoError(t, err) | ||
|
||
result, err := namespacedDB.Query("SELECT current_database();") | ||
require.NoError(t, err) | ||
defer result.Close() | ||
|
||
require.True(t, result.Next()) | ||
var dbName string | ||
err = result.Scan(&dbName) | ||
require.NoError(t, err) | ||
require.Equal(t, newDBName, dbName) | ||
} | ||
|
||
func TestNamespaceRepeat(t *testing.T) { | ||
startingDsn := testutils.LocalTestDBDSNPrefix + "/foo" + testutils.LocalTestDBDSNSuffix | ||
newDBName := "xmtp_" + testutils.RandomString(24) | ||
// Create namespaced DB | ||
db1, err := NewNamespacedDB( | ||
context.Background(), | ||
startingDsn, | ||
newDBName, | ||
time.Second, | ||
time.Second, | ||
) | ||
require.NoError(t, err) | ||
require.NotNil(t, db1) | ||
t.Cleanup(func() { db1.Close() }) | ||
|
||
// Create again with the same name | ||
db2, err := NewNamespacedDB( | ||
context.Background(), | ||
startingDsn, | ||
newDBName, | ||
time.Second, | ||
time.Second, | ||
) | ||
require.NoError(t, err) | ||
require.NotNil(t, db2) | ||
t.Cleanup(func() { db2.Close() }) | ||
} | ||
|
||
func TestNamespacedDBInvalidName(t *testing.T) { | ||
_, err := NewNamespacedDB( | ||
context.Background(), | ||
testutils.LocalTestDBDSNPrefix+"/foo"+testutils.LocalTestDBDSNSuffix, | ||
"invalid/name", | ||
time.Second, | ||
time.Second, | ||
) | ||
require.Error(t, err) | ||
} | ||
|
||
func TestNamespacedDBInvalidDSN(t *testing.T) { | ||
_, err := NewNamespacedDB( | ||
context.Background(), | ||
"invalid-dsn", | ||
"dbname", | ||
time.Second, | ||
time.Second, | ||
) | ||
require.Error(t, err) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters