Refactor webpush store tests and add coverage
- Add SetSubscriptionUpdatedAt to Store interface, remove DB() accessor - Rename store files to store_sqlite.go and store_postgres.go - Use camelCase for test function names - Add tests for upsert field updates and multi-user removal - Use transaction in setupNewPostgresDB - Use lowercase "excluded." in PostgreSQL upsert query
This commit is contained in:
@@ -19,7 +19,6 @@ import (
|
|||||||
"github.com/stretchr/testify/require"
|
"github.com/stretchr/testify/require"
|
||||||
"heckel.io/ntfy/v2/user"
|
"heckel.io/ntfy/v2/user"
|
||||||
"heckel.io/ntfy/v2/util"
|
"heckel.io/ntfy/v2/util"
|
||||||
wpush "heckel.io/ntfy/v2/webpush"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
@@ -241,7 +240,7 @@ func TestServer_WebPush_Expiry(t *testing.T) {
|
|||||||
addSubscription(t, s, endpoint, "test-topic")
|
addSubscription(t, s, endpoint, "test-topic")
|
||||||
requireSubscriptionCount(t, s, "test-topic", 1)
|
requireSubscriptionCount(t, s, "test-topic", 1)
|
||||||
|
|
||||||
require.Nil(t, s.webPush.(*wpush.SQLiteStore).SetSubscriptionUpdatedAt(endpoint, time.Now().Add(-55*24*time.Hour).Unix()))
|
require.Nil(t, s.webPush.SetSubscriptionUpdatedAt(endpoint, time.Now().Add(-55*24*time.Hour).Unix()))
|
||||||
|
|
||||||
s.pruneAndNotifyWebPushSubscriptions()
|
s.pruneAndNotifyWebPushSubscriptions()
|
||||||
requireSubscriptionCount(t, s, "test-topic", 1)
|
requireSubscriptionCount(t, s, "test-topic", 1)
|
||||||
@@ -250,7 +249,7 @@ func TestServer_WebPush_Expiry(t *testing.T) {
|
|||||||
return received.Load()
|
return received.Load()
|
||||||
})
|
})
|
||||||
|
|
||||||
require.Nil(t, s.webPush.(*wpush.SQLiteStore).SetSubscriptionUpdatedAt(endpoint, time.Now().Add(-60*24*time.Hour).Unix()))
|
require.Nil(t, s.webPush.SetSubscriptionUpdatedAt(endpoint, time.Now().Add(-60*24*time.Hour).Unix()))
|
||||||
|
|
||||||
s.pruneAndNotifyWebPushSubscriptions()
|
s.pruneAndNotifyWebPushSubscriptions()
|
||||||
waitFor(t, func() bool {
|
waitFor(t, func() bool {
|
||||||
|
|||||||
@@ -1,83 +0,0 @@
|
|||||||
package webpush_test
|
|
||||||
|
|
||||||
import (
|
|
||||||
"database/sql"
|
|
||||||
"fmt"
|
|
||||||
"net/url"
|
|
||||||
"os"
|
|
||||||
"testing"
|
|
||||||
|
|
||||||
"github.com/stretchr/testify/require"
|
|
||||||
"heckel.io/ntfy/v2/util"
|
|
||||||
"heckel.io/ntfy/v2/webpush"
|
|
||||||
)
|
|
||||||
|
|
||||||
func newTestPostgresStore(t *testing.T) *webpush.PostgresStore {
|
|
||||||
dsn := os.Getenv("NTFY_TEST_DATABASE_URL")
|
|
||||||
if dsn == "" {
|
|
||||||
t.Skip("NTFY_TEST_DATABASE_URL not set, skipping PostgreSQL tests")
|
|
||||||
}
|
|
||||||
// Create a unique schema for this test
|
|
||||||
schema := fmt.Sprintf("test_%s", util.RandomString(10))
|
|
||||||
setupDB, err := sql.Open("pgx", dsn)
|
|
||||||
require.Nil(t, err)
|
|
||||||
_, err = setupDB.Exec(fmt.Sprintf("CREATE SCHEMA %s", schema))
|
|
||||||
require.Nil(t, err)
|
|
||||||
require.Nil(t, setupDB.Close())
|
|
||||||
// Open store with search_path set to the new schema
|
|
||||||
u, err := url.Parse(dsn)
|
|
||||||
require.Nil(t, err)
|
|
||||||
q := u.Query()
|
|
||||||
q.Set("search_path", schema)
|
|
||||||
u.RawQuery = q.Encode()
|
|
||||||
store, err := webpush.NewPostgresStore(u.String())
|
|
||||||
require.Nil(t, err)
|
|
||||||
t.Cleanup(func() {
|
|
||||||
store.Close()
|
|
||||||
cleanDB, err := sql.Open("pgx", dsn)
|
|
||||||
if err == nil {
|
|
||||||
cleanDB.Exec(fmt.Sprintf("DROP SCHEMA %s CASCADE", schema))
|
|
||||||
cleanDB.Close()
|
|
||||||
}
|
|
||||||
})
|
|
||||||
return store
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_UpsertSubscription_SubscriptionsForTopic(t *testing.T) {
|
|
||||||
testStoreUpsertSubscription_SubscriptionsForTopic(t, newTestPostgresStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_UpsertSubscription_SubscriberIPLimitReached(t *testing.T) {
|
|
||||||
testStoreUpsertSubscription_SubscriberIPLimitReached(t, newTestPostgresStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_UpsertSubscription_UpdateTopics(t *testing.T) {
|
|
||||||
testStoreUpsertSubscription_UpdateTopics(t, newTestPostgresStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_RemoveSubscriptionsByEndpoint(t *testing.T) {
|
|
||||||
testStoreRemoveSubscriptionsByEndpoint(t, newTestPostgresStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_RemoveSubscriptionsByUserID(t *testing.T) {
|
|
||||||
testStoreRemoveSubscriptionsByUserID(t, newTestPostgresStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_RemoveSubscriptionsByUserID_Empty(t *testing.T) {
|
|
||||||
testStoreRemoveSubscriptionsByUserID_Empty(t, newTestPostgresStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_MarkExpiryWarningSent(t *testing.T) {
|
|
||||||
store := newTestPostgresStore(t)
|
|
||||||
testStoreMarkExpiryWarningSent(t, store, store.SetSubscriptionUpdatedAt)
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_SubscriptionsExpiring(t *testing.T) {
|
|
||||||
store := newTestPostgresStore(t)
|
|
||||||
testStoreSubscriptionsExpiring(t, store, store.SetSubscriptionUpdatedAt)
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPostgresStore_RemoveExpiredSubscriptions(t *testing.T) {
|
|
||||||
store := newTestPostgresStore(t)
|
|
||||||
testStoreRemoveExpiredSubscriptions(t, store, store.SetSubscriptionUpdatedAt)
|
|
||||||
}
|
|
||||||
@@ -1,55 +0,0 @@
|
|||||||
package webpush_test
|
|
||||||
|
|
||||||
import (
|
|
||||||
"path/filepath"
|
|
||||||
"testing"
|
|
||||||
|
|
||||||
"github.com/stretchr/testify/require"
|
|
||||||
"heckel.io/ntfy/v2/webpush"
|
|
||||||
)
|
|
||||||
|
|
||||||
func newTestSQLiteStore(t *testing.T) *webpush.SQLiteStore {
|
|
||||||
store, err := webpush.NewSQLiteStore(filepath.Join(t.TempDir(), "webpush.db"), "")
|
|
||||||
require.Nil(t, err)
|
|
||||||
t.Cleanup(func() { store.Close() })
|
|
||||||
return store
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_UpsertSubscription_SubscriptionsForTopic(t *testing.T) {
|
|
||||||
testStoreUpsertSubscription_SubscriptionsForTopic(t, newTestSQLiteStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_UpsertSubscription_SubscriberIPLimitReached(t *testing.T) {
|
|
||||||
testStoreUpsertSubscription_SubscriberIPLimitReached(t, newTestSQLiteStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_UpsertSubscription_UpdateTopics(t *testing.T) {
|
|
||||||
testStoreUpsertSubscription_UpdateTopics(t, newTestSQLiteStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_RemoveSubscriptionsByEndpoint(t *testing.T) {
|
|
||||||
testStoreRemoveSubscriptionsByEndpoint(t, newTestSQLiteStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_RemoveSubscriptionsByUserID(t *testing.T) {
|
|
||||||
testStoreRemoveSubscriptionsByUserID(t, newTestSQLiteStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_RemoveSubscriptionsByUserID_Empty(t *testing.T) {
|
|
||||||
testStoreRemoveSubscriptionsByUserID_Empty(t, newTestSQLiteStore(t))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_MarkExpiryWarningSent(t *testing.T) {
|
|
||||||
store := newTestSQLiteStore(t)
|
|
||||||
testStoreMarkExpiryWarningSent(t, store, store.SetSubscriptionUpdatedAt)
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_SubscriptionsExpiring(t *testing.T) {
|
|
||||||
store := newTestSQLiteStore(t)
|
|
||||||
testStoreSubscriptionsExpiring(t, store, store.SetSubscriptionUpdatedAt)
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSQLiteStore_RemoveExpiredSubscriptions(t *testing.T) {
|
|
||||||
store := newTestSQLiteStore(t)
|
|
||||||
testStoreRemoveExpiredSubscriptions(t, store, store.SetSubscriptionUpdatedAt)
|
|
||||||
}
|
|
||||||
@@ -29,6 +29,7 @@ type Store interface {
|
|||||||
RemoveSubscriptionsByEndpoint(endpoint string) error
|
RemoveSubscriptionsByEndpoint(endpoint string) error
|
||||||
RemoveSubscriptionsByUserID(userID string) error
|
RemoveSubscriptionsByUserID(userID string) error
|
||||||
RemoveExpiredSubscriptions(expireAfter time.Duration) error
|
RemoveExpiredSubscriptions(expireAfter time.Duration) error
|
||||||
|
SetSubscriptionUpdatedAt(endpoint string, updatedAt int64) error
|
||||||
Close() error
|
Close() error
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -53,7 +53,7 @@ const (
|
|||||||
INSERT INTO webpush_subscription (id, endpoint, key_auth, key_p256dh, user_id, subscriber_ip, updated_at, warned_at)
|
INSERT INTO webpush_subscription (id, endpoint, key_auth, key_p256dh, user_id, subscriber_ip, updated_at, warned_at)
|
||||||
VALUES ($1, $2, $3, $4, $5, $6, $7, $8)
|
VALUES ($1, $2, $3, $4, $5, $6, $7, $8)
|
||||||
ON CONFLICT (endpoint)
|
ON CONFLICT (endpoint)
|
||||||
DO UPDATE SET key_auth = EXCLUDED.key_auth, key_p256dh = EXCLUDED.key_p256dh, user_id = EXCLUDED.user_id, subscriber_ip = EXCLUDED.subscriber_ip, updated_at = EXCLUDED.updated_at, warned_at = EXCLUDED.warned_at
|
DO UPDATE SET key_auth = excluded.key_auth, key_p256dh = excluded.key_p256dh, user_id = excluded.user_id, subscriber_ip = excluded.subscriber_ip, updated_at = excluded.updated_at, warned_at = excluded.warned_at
|
||||||
`
|
`
|
||||||
pgUpdateSubscriptionWarningSentQuery = `UPDATE webpush_subscription SET warned_at = $1 WHERE id = $2`
|
pgUpdateSubscriptionWarningSentQuery = `UPDATE webpush_subscription SET warned_at = $1 WHERE id = $2`
|
||||||
pgDeleteSubscriptionByEndpointQuery = `DELETE FROM webpush_subscription WHERE endpoint = $1`
|
pgDeleteSubscriptionByEndpointQuery = `DELETE FROM webpush_subscription WHERE endpoint = $1`
|
||||||
@@ -95,7 +95,7 @@ func NewPostgresStore(dsn string) (*PostgresStore, error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func setupPostgresDB(db *sql.DB) error {
|
func setupPostgresDB(db *sql.DB) error {
|
||||||
// If 'wp_schema_version' table does not exist, this must be a new database
|
// If 'webpush_schema_version' table does not exist, this must be a new database
|
||||||
rows, err := db.Query(pgSelectSchemaVersionQuery)
|
rows, err := db.Query(pgSelectSchemaVersionQuery)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return setupNewPostgresDB(db)
|
return setupNewPostgresDB(db)
|
||||||
@@ -104,13 +104,18 @@ func setupPostgresDB(db *sql.DB) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func setupNewPostgresDB(db *sql.DB) error {
|
func setupNewPostgresDB(db *sql.DB) error {
|
||||||
if _, err := db.Exec(pgCreateTablesQuery); err != nil {
|
tx, err := db.Begin()
|
||||||
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if _, err := db.Exec(pgInsertSchemaVersion, pgCurrentSchemaVersion); err != nil {
|
defer tx.Rollback()
|
||||||
|
if _, err := tx.Exec(pgCreateTablesQuery); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
return nil
|
if _, err := tx.Exec(pgInsertSchemaVersion, pgCurrentSchemaVersion); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tx.Commit()
|
||||||
}
|
}
|
||||||
|
|
||||||
// UpsertSubscription adds or updates Web Push subscriptions for the given topics and user ID.
|
// UpsertSubscription adds or updates Web Push subscriptions for the given topics and user ID.
|
||||||
91
webpush/store_postgres_test.go
Normal file
91
webpush/store_postgres_test.go
Normal file
@@ -0,0 +1,91 @@
|
|||||||
|
package webpush_test
|
||||||
|
|
||||||
|
import (
|
||||||
|
"database/sql"
|
||||||
|
"fmt"
|
||||||
|
"net/url"
|
||||||
|
"os"
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/stretchr/testify/require"
|
||||||
|
"heckel.io/ntfy/v2/util"
|
||||||
|
"heckel.io/ntfy/v2/webpush"
|
||||||
|
)
|
||||||
|
|
||||||
|
func newTestPostgresStore(t *testing.T) *webpush.PostgresStore {
|
||||||
|
dsn := os.Getenv("NTFY_TEST_DATABASE_URL")
|
||||||
|
if dsn == "" {
|
||||||
|
t.Skip("NTFY_TEST_DATABASE_URL not set, skipping PostgreSQL tests")
|
||||||
|
}
|
||||||
|
// Create a unique schema for this test
|
||||||
|
schema := fmt.Sprintf("test_%s", util.RandomString(10))
|
||||||
|
setupDB, err := sql.Open("pgx", dsn)
|
||||||
|
require.Nil(t, err)
|
||||||
|
_, err = setupDB.Exec(fmt.Sprintf("CREATE SCHEMA %s", schema))
|
||||||
|
require.Nil(t, err)
|
||||||
|
require.Nil(t, setupDB.Close())
|
||||||
|
// Open store with search_path set to the new schema
|
||||||
|
u, err := url.Parse(dsn)
|
||||||
|
require.Nil(t, err)
|
||||||
|
q := u.Query()
|
||||||
|
q.Set("search_path", schema)
|
||||||
|
u.RawQuery = q.Encode()
|
||||||
|
store, err := webpush.NewPostgresStore(u.String())
|
||||||
|
require.Nil(t, err)
|
||||||
|
t.Cleanup(func() {
|
||||||
|
store.Close()
|
||||||
|
cleanDB, err := sql.Open("pgx", dsn)
|
||||||
|
if err == nil {
|
||||||
|
cleanDB.Exec(fmt.Sprintf("DROP SCHEMA %s CASCADE", schema))
|
||||||
|
cleanDB.Close()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
return store
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreUpsertSubscriptionSubscriptionsForTopic(t *testing.T) {
|
||||||
|
testStoreUpsertSubscriptionSubscriptionsForTopic(t, newTestPostgresStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreUpsertSubscriptionSubscriberIPLimitReached(t *testing.T) {
|
||||||
|
testStoreUpsertSubscriptionSubscriberIPLimitReached(t, newTestPostgresStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreUpsertSubscriptionUpdateTopics(t *testing.T) {
|
||||||
|
testStoreUpsertSubscriptionUpdateTopics(t, newTestPostgresStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreUpsertSubscriptionUpdateFields(t *testing.T) {
|
||||||
|
testStoreUpsertSubscriptionUpdateFields(t, newTestPostgresStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreRemoveByUserIDMultiple(t *testing.T) {
|
||||||
|
testStoreRemoveByUserIDMultiple(t, newTestPostgresStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreRemoveByEndpoint(t *testing.T) {
|
||||||
|
testStoreRemoveByEndpoint(t, newTestPostgresStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreRemoveByUserID(t *testing.T) {
|
||||||
|
testStoreRemoveByUserID(t, newTestPostgresStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreRemoveByUserIDEmpty(t *testing.T) {
|
||||||
|
testStoreRemoveByUserIDEmpty(t, newTestPostgresStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreExpiryWarningSent(t *testing.T) {
|
||||||
|
store := newTestPostgresStore(t)
|
||||||
|
testStoreExpiryWarningSent(t, store, store.SetSubscriptionUpdatedAt)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreExpiring(t *testing.T) {
|
||||||
|
store := newTestPostgresStore(t)
|
||||||
|
testStoreExpiring(t, store, store.SetSubscriptionUpdatedAt)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestPostgresStoreRemoveExpired(t *testing.T) {
|
||||||
|
store := newTestPostgresStore(t)
|
||||||
|
testStoreRemoveExpired(t, store, store.SetSubscriptionUpdatedAt)
|
||||||
|
}
|
||||||
63
webpush/store_sqlite_test.go
Normal file
63
webpush/store_sqlite_test.go
Normal file
@@ -0,0 +1,63 @@
|
|||||||
|
package webpush_test
|
||||||
|
|
||||||
|
import (
|
||||||
|
"path/filepath"
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/stretchr/testify/require"
|
||||||
|
"heckel.io/ntfy/v2/webpush"
|
||||||
|
)
|
||||||
|
|
||||||
|
func newTestSQLiteStore(t *testing.T) *webpush.SQLiteStore {
|
||||||
|
store, err := webpush.NewSQLiteStore(filepath.Join(t.TempDir(), "webpush.db"), "")
|
||||||
|
require.Nil(t, err)
|
||||||
|
t.Cleanup(func() { store.Close() })
|
||||||
|
return store
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreUpsertSubscriptionSubscriptionsForTopic(t *testing.T) {
|
||||||
|
testStoreUpsertSubscriptionSubscriptionsForTopic(t, newTestSQLiteStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreUpsertSubscriptionSubscriberIPLimitReached(t *testing.T) {
|
||||||
|
testStoreUpsertSubscriptionSubscriberIPLimitReached(t, newTestSQLiteStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreUpsertSubscriptionUpdateTopics(t *testing.T) {
|
||||||
|
testStoreUpsertSubscriptionUpdateTopics(t, newTestSQLiteStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreUpsertSubscriptionUpdateFields(t *testing.T) {
|
||||||
|
testStoreUpsertSubscriptionUpdateFields(t, newTestSQLiteStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreRemoveByUserIDMultiple(t *testing.T) {
|
||||||
|
testStoreRemoveByUserIDMultiple(t, newTestSQLiteStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreRemoveByEndpoint(t *testing.T) {
|
||||||
|
testStoreRemoveByEndpoint(t, newTestSQLiteStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreRemoveByUserID(t *testing.T) {
|
||||||
|
testStoreRemoveByUserID(t, newTestSQLiteStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreRemoveByUserIDEmpty(t *testing.T) {
|
||||||
|
testStoreRemoveByUserIDEmpty(t, newTestSQLiteStore(t))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreExpiryWarningSent(t *testing.T) {
|
||||||
|
store := newTestSQLiteStore(t)
|
||||||
|
testStoreExpiryWarningSent(t, store, store.SetSubscriptionUpdatedAt)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreExpiring(t *testing.T) {
|
||||||
|
store := newTestSQLiteStore(t)
|
||||||
|
testStoreExpiring(t, store, store.SetSubscriptionUpdatedAt)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestSQLiteStoreRemoveExpired(t *testing.T) {
|
||||||
|
store := newTestSQLiteStore(t)
|
||||||
|
testStoreRemoveExpired(t, store, store.SetSubscriptionUpdatedAt)
|
||||||
|
}
|
||||||
@@ -12,7 +12,7 @@ import (
|
|||||||
|
|
||||||
const testWebPushEndpoint = "https://updates.push.services.mozilla.com/wpush/v1/AAABBCCCDDEEEFFF"
|
const testWebPushEndpoint = "https://updates.push.services.mozilla.com/wpush/v1/AAABBCCCDDEEEFFF"
|
||||||
|
|
||||||
func testStoreUpsertSubscription_SubscriptionsForTopic(t *testing.T, store webpush.Store) {
|
func testStoreUpsertSubscriptionSubscriptionsForTopic(t *testing.T, store webpush.Store) {
|
||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"test-topic", "mytopic"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"test-topic", "mytopic"}))
|
||||||
|
|
||||||
subs, err := store.SubscriptionsForTopic("test-topic")
|
subs, err := store.SubscriptionsForTopic("test-topic")
|
||||||
@@ -29,7 +29,7 @@ func testStoreUpsertSubscription_SubscriptionsForTopic(t *testing.T, store webpu
|
|||||||
require.Equal(t, subs[0].Endpoint, subs2[0].Endpoint)
|
require.Equal(t, subs[0].Endpoint, subs2[0].Endpoint)
|
||||||
}
|
}
|
||||||
|
|
||||||
func testStoreUpsertSubscription_SubscriberIPLimitReached(t *testing.T, store webpush.Store) {
|
func testStoreUpsertSubscriptionSubscriberIPLimitReached(t *testing.T, store webpush.Store) {
|
||||||
// Insert 10 subscriptions with the same IP address
|
// Insert 10 subscriptions with the same IP address
|
||||||
for i := 0; i < 10; i++ {
|
for i := 0; i < 10; i++ {
|
||||||
endpoint := fmt.Sprintf(testWebPushEndpoint+"%d", i)
|
endpoint := fmt.Sprintf(testWebPushEndpoint+"%d", i)
|
||||||
@@ -46,7 +46,7 @@ func testStoreUpsertSubscription_SubscriberIPLimitReached(t *testing.T, store we
|
|||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"99", "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("9.9.9.9"), []string{"test-topic", "mytopic"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"99", "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("9.9.9.9"), []string{"test-topic", "mytopic"}))
|
||||||
}
|
}
|
||||||
|
|
||||||
func testStoreUpsertSubscription_UpdateTopics(t *testing.T, store webpush.Store) {
|
func testStoreUpsertSubscriptionUpdateTopics(t *testing.T, store webpush.Store) {
|
||||||
// Insert subscription with two topics, and another with one topic
|
// Insert subscription with two topics, and another with one topic
|
||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"0", "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"0", "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"1", "auth-key", "p256dh-key", "", netip.MustParseAddr("9.9.9.9"), []string{"topic1"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"1", "auth-key", "p256dh-key", "", netip.MustParseAddr("9.9.9.9"), []string{"topic1"}))
|
||||||
@@ -75,7 +75,51 @@ func testStoreUpsertSubscription_UpdateTopics(t *testing.T, store webpush.Store)
|
|||||||
require.Len(t, subs, 0)
|
require.Len(t, subs, 0)
|
||||||
}
|
}
|
||||||
|
|
||||||
func testStoreRemoveSubscriptionsByEndpoint(t *testing.T, store webpush.Store) {
|
func testStoreUpsertSubscriptionUpdateFields(t *testing.T, store webpush.Store) {
|
||||||
|
// Insert a subscription
|
||||||
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1"}))
|
||||||
|
|
||||||
|
subs, err := store.SubscriptionsForTopic("topic1")
|
||||||
|
require.Nil(t, err)
|
||||||
|
require.Len(t, subs, 1)
|
||||||
|
require.Equal(t, "auth-key", subs[0].Auth)
|
||||||
|
require.Equal(t, "p256dh-key", subs[0].P256dh)
|
||||||
|
require.Equal(t, "u_1234", subs[0].UserID)
|
||||||
|
|
||||||
|
// Re-upsert the same endpoint with different auth, p256dh, and userID
|
||||||
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "new-auth", "new-p256dh", "u_5678", netip.MustParseAddr("1.2.3.4"), []string{"topic1"}))
|
||||||
|
|
||||||
|
subs, err = store.SubscriptionsForTopic("topic1")
|
||||||
|
require.Nil(t, err)
|
||||||
|
require.Len(t, subs, 1)
|
||||||
|
require.Equal(t, testWebPushEndpoint, subs[0].Endpoint)
|
||||||
|
require.Equal(t, "new-auth", subs[0].Auth)
|
||||||
|
require.Equal(t, "new-p256dh", subs[0].P256dh)
|
||||||
|
require.Equal(t, "u_5678", subs[0].UserID)
|
||||||
|
}
|
||||||
|
|
||||||
|
func testStoreRemoveByUserIDMultiple(t *testing.T, store webpush.Store) {
|
||||||
|
// Insert two subscriptions for u_1234 and one for u_5678
|
||||||
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"0", "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1"}))
|
||||||
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"1", "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1"}))
|
||||||
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint+"2", "auth-key", "p256dh-key", "u_5678", netip.MustParseAddr("9.9.9.9"), []string{"topic1"}))
|
||||||
|
|
||||||
|
subs, err := store.SubscriptionsForTopic("topic1")
|
||||||
|
require.Nil(t, err)
|
||||||
|
require.Len(t, subs, 3)
|
||||||
|
|
||||||
|
// Remove all subscriptions for u_1234
|
||||||
|
require.Nil(t, store.RemoveSubscriptionsByUserID("u_1234"))
|
||||||
|
|
||||||
|
// Only u_5678's subscription should remain
|
||||||
|
subs, err = store.SubscriptionsForTopic("topic1")
|
||||||
|
require.Nil(t, err)
|
||||||
|
require.Len(t, subs, 1)
|
||||||
|
require.Equal(t, testWebPushEndpoint+"2", subs[0].Endpoint)
|
||||||
|
require.Equal(t, "u_5678", subs[0].UserID)
|
||||||
|
}
|
||||||
|
|
||||||
|
func testStoreRemoveByEndpoint(t *testing.T, store webpush.Store) {
|
||||||
// Insert subscription with two topics
|
// Insert subscription with two topics
|
||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
||||||
subs, err := store.SubscriptionsForTopic("topic1")
|
subs, err := store.SubscriptionsForTopic("topic1")
|
||||||
@@ -89,7 +133,7 @@ func testStoreRemoveSubscriptionsByEndpoint(t *testing.T, store webpush.Store) {
|
|||||||
require.Len(t, subs, 0)
|
require.Len(t, subs, 0)
|
||||||
}
|
}
|
||||||
|
|
||||||
func testStoreRemoveSubscriptionsByUserID(t *testing.T, store webpush.Store) {
|
func testStoreRemoveByUserID(t *testing.T, store webpush.Store) {
|
||||||
// Insert subscription with two topics
|
// Insert subscription with two topics
|
||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
||||||
subs, err := store.SubscriptionsForTopic("topic1")
|
subs, err := store.SubscriptionsForTopic("topic1")
|
||||||
@@ -103,11 +147,11 @@ func testStoreRemoveSubscriptionsByUserID(t *testing.T, store webpush.Store) {
|
|||||||
require.Len(t, subs, 0)
|
require.Len(t, subs, 0)
|
||||||
}
|
}
|
||||||
|
|
||||||
func testStoreRemoveSubscriptionsByUserID_Empty(t *testing.T, store webpush.Store) {
|
func testStoreRemoveByUserIDEmpty(t *testing.T, store webpush.Store) {
|
||||||
require.Equal(t, webpush.ErrWebPushUserIDCannotBeEmpty, store.RemoveSubscriptionsByUserID(""))
|
require.Equal(t, webpush.ErrWebPushUserIDCannotBeEmpty, store.RemoveSubscriptionsByUserID(""))
|
||||||
}
|
}
|
||||||
|
|
||||||
func testStoreMarkExpiryWarningSent(t *testing.T, store webpush.Store, setUpdatedAt func(endpoint string, updatedAt int64) error) {
|
func testStoreExpiryWarningSent(t *testing.T, store webpush.Store, setUpdatedAt func(endpoint string, updatedAt int64) error) {
|
||||||
// Insert subscription with two topics
|
// Insert subscription with two topics
|
||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
||||||
|
|
||||||
@@ -129,7 +173,7 @@ func testStoreMarkExpiryWarningSent(t *testing.T, store webpush.Store, setUpdate
|
|||||||
require.Len(t, subs, 0)
|
require.Len(t, subs, 0)
|
||||||
}
|
}
|
||||||
|
|
||||||
func testStoreSubscriptionsExpiring(t *testing.T, store webpush.Store, setUpdatedAt func(endpoint string, updatedAt int64) error) {
|
func testStoreExpiring(t *testing.T, store webpush.Store, setUpdatedAt func(endpoint string, updatedAt int64) error) {
|
||||||
// Insert subscription with two topics
|
// Insert subscription with two topics
|
||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
||||||
subs, err := store.SubscriptionsForTopic("topic1")
|
subs, err := store.SubscriptionsForTopic("topic1")
|
||||||
@@ -149,7 +193,7 @@ func testStoreSubscriptionsExpiring(t *testing.T, store webpush.Store, setUpdate
|
|||||||
require.Equal(t, testWebPushEndpoint, subs[0].Endpoint)
|
require.Equal(t, testWebPushEndpoint, subs[0].Endpoint)
|
||||||
}
|
}
|
||||||
|
|
||||||
func testStoreRemoveExpiredSubscriptions(t *testing.T, store webpush.Store, setUpdatedAt func(endpoint string, updatedAt int64) error) {
|
func testStoreRemoveExpired(t *testing.T, store webpush.Store, setUpdatedAt func(endpoint string, updatedAt int64) error) {
|
||||||
// Insert subscription with two topics
|
// Insert subscription with two topics
|
||||||
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
require.Nil(t, store.UpsertSubscription(testWebPushEndpoint, "auth-key", "p256dh-key", "u_1234", netip.MustParseAddr("1.2.3.4"), []string{"topic1", "topic2"}))
|
||||||
subs, err := store.SubscriptionsForTopic("topic1")
|
subs, err := store.SubscriptionsForTopic("topic1")
|
||||||
|
|||||||
Reference in New Issue
Block a user