mirror of
https://github.com/lightninglabs/lightning-terminal.git
synced 2026-08-13 12:33:36 +02:00
session: fix empty config for features in sql mig
In the bbolt store, an empty config for a feature is represented as an empty array, while in for the SQL store, the same config is represented as nil. Therefore, in the scenario where a specific feature has an empty config, we override the SQL FeatureConfig for that feature to also be set to an empty array. This is needed to ensure that the deep equals check in the migration validation does not fail in this scenario.
This commit is contained in:
parent
e3a8589283
commit
3d10572280
2 changed files with 85 additions and 3 deletions
|
|
@ -198,6 +198,7 @@ func migrateSessionsToSQLAndValidate(ctx context.Context,
|
|||
overrideSessionTimeZone(migratedSession)
|
||||
overrideMacaroonRecipe(kvSession, migratedSession)
|
||||
overrideRemovedAccount(kvSession, migratedSession)
|
||||
overrideFeatureConfig(kvSession, migratedSession)
|
||||
|
||||
if !reflect.DeepEqual(kvSession, migratedSession) {
|
||||
diff := difflib.UnifiedDiff{
|
||||
|
|
@ -530,3 +531,29 @@ func overrideRemovedAccount(kvSession *Session, migratedSession *Session) {
|
|||
},
|
||||
)
|
||||
}
|
||||
|
||||
// overrideFeatureConfig overrides a specific feature's config for the SQL
|
||||
// session in a certain scenario:
|
||||
//
|
||||
// In the bbolt store, an empty config for a feature is represented as an empty
|
||||
// array, while in for the SQL store, the same config is represented as nil.
|
||||
// Therefore, in the scenario where a specific feature has an empty config, we
|
||||
// override the SQL FeatureConfig for that feature to also be set to an empty
|
||||
// array. This is needed to ensure that the deep equals check in the migration
|
||||
// validation does not fail in this scenario.
|
||||
func overrideFeatureConfig(kvSession *Session, mSession *Session) {
|
||||
// If FeatureConfig is not set for both sessions, we return early.
|
||||
if kvSession.FeatureConfig == nil || mSession.FeatureConfig == nil {
|
||||
return
|
||||
}
|
||||
|
||||
migratedConf := *mSession.FeatureConfig
|
||||
for featureName, config := range *kvSession.FeatureConfig {
|
||||
// If the config is empty for the bbolt feature, and nil for the
|
||||
// SQL version, we override the SQL version to match the bbolt
|
||||
// version.
|
||||
if len(config) == 0 && migratedConf[featureName] == nil {
|
||||
migratedConf[featureName] = make([]byte, 0)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -81,6 +81,10 @@ func TestSessionsStoreMigration(t *testing.T) {
|
|||
// session doesn't.
|
||||
overrideRemovedAccount(kvSession, sqlSession)
|
||||
|
||||
// Finally, we also need to override specific feature's
|
||||
// config if they are empty.
|
||||
overrideFeatureConfig(kvSession, sqlSession)
|
||||
|
||||
assertEqualSessions(t, kvSession, sqlSession)
|
||||
}
|
||||
|
||||
|
|
@ -200,6 +204,48 @@ func TestSessionsStoreMigration(t *testing.T) {
|
|||
return getBoltStoreSessions(t, store)
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "one session with a feature config with empty",
|
||||
populateDB: func(t *testing.T, store *BoltStore,
|
||||
_ accounts.Store) []*Session {
|
||||
|
||||
// Set a feature config, which has an empty
|
||||
// entry for a specific feature.
|
||||
featureConfig := map[string][]byte{
|
||||
"AutoFees": {},
|
||||
}
|
||||
|
||||
_, err := store.NewSession(
|
||||
ctx, "test", TypeMacaroonAdmin,
|
||||
time.Unix(1000, 0), "",
|
||||
WithFeatureConfig(featureConfig),
|
||||
)
|
||||
require.NoError(t, err)
|
||||
|
||||
return getBoltStoreSessions(t, store)
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "one session with a feature config with nil",
|
||||
populateDB: func(t *testing.T, store *BoltStore,
|
||||
_ accounts.Store) []*Session {
|
||||
|
||||
// Set a feature config, which has a nil entry
|
||||
// for a specific feature.
|
||||
featureConfig := map[string][]byte{
|
||||
"AutoFees": nil,
|
||||
}
|
||||
|
||||
_, err := store.NewSession(
|
||||
ctx, "test", TypeMacaroonAdmin,
|
||||
time.Unix(1000, 0), "",
|
||||
WithFeatureConfig(featureConfig),
|
||||
)
|
||||
require.NoError(t, err)
|
||||
|
||||
return getBoltStoreSessions(t, store)
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "one session with dev server",
|
||||
populateDB: func(t *testing.T, store *BoltStore,
|
||||
|
|
@ -801,9 +847,18 @@ func randomPrivacyFlags() PrivacyFlags {
|
|||
func randomFeatureConfig() FeaturesConfig {
|
||||
featureConfig := make(FeaturesConfig)
|
||||
for i := range rand.Intn(10) {
|
||||
featureName := fmt.Sprintf("feature%d", i)
|
||||
featureValue := []byte{byte(rand.Int31())}
|
||||
featureConfig[featureName] = featureValue
|
||||
var (
|
||||
featureName = fmt.Sprintf("feature%d", i)
|
||||
configValue []byte
|
||||
)
|
||||
|
||||
// For the vast majority of the features, we set a value for the
|
||||
// feature's config. But in 1/5 of the cases, we set an empty
|
||||
// config.
|
||||
if rand.Intn(5) != 0 {
|
||||
configValue = []byte{byte(rand.Int31())}
|
||||
}
|
||||
featureConfig[featureName] = configValue
|
||||
}
|
||||
|
||||
return featureConfig
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue