Add special profile upgrade system

This commit is contained in:
Daniel
2021-05-05 13:01:58 +02:00
parent 94756d9f38
commit 6245bca6d9
2 changed files with 88 additions and 1 deletions

View File

@@ -51,6 +51,12 @@ func GetProfile(source profileSource, id, linkedPath string) ( //nolint:gocognit
// Get from database.
profile, err = getProfile(scopedID)
// Check if the request is for a special profile that may need a reset.
if err == nil && specialProfileNeedsReset(profile) {
// Trigger creation of special profile.
err = database.ErrNotFound
}
// If we cannot find a profile, check if the request is for a special
// profile we can create.
if errors.Is(err, database.ErrNotFound) {

View File

@@ -1,5 +1,14 @@
package profile
import (
"fmt"
"time"
"github.com/safing/portbase/notifications"
"github.com/safing/portbase/log"
)
const (
// UnidentifiedProfileID is the profile ID used for unidentified processes.
UnidentifiedProfileID = "_unidentified"
@@ -76,7 +85,19 @@ func getSpecialProfile(profileID, linkedPath string) *Profile {
return New(SourceLocal, SystemProfileID, linkedPath, nil)
case SystemResolverProfileID:
return New(SourceLocal, SystemResolverProfileID, linkedPath, nil)
return New(
SourceLocal,
SystemResolverProfileID,
linkedPath,
map[string]interface{}{
CfgOptionServiceEndpointsKey: []string{
"+ Localhost", // Allow everything from localhost.
"+ LAN UDP/5353", // Allow inbound mDNS requests and multicast replies.
"+ LAN UDP/5355", // Allow inbound LLMNR requests and multicast replies.
"+ LAN UDP/1900", // Allow inbound SSDP requests and multicast replies.
},
},
)
case PortmasterProfileID:
profile := New(SourceLocal, PortmasterProfileID, linkedPath, nil)
@@ -117,3 +138,63 @@ func getSpecialProfile(profileID, linkedPath string) *Profile {
return nil
}
}
// specialProfileNeedsReset is used as a workaround until we can properly use
// profile layering in a way that it is also correctly handled by the UI. We
// check if the special profile has not been changed by the user and if not,
// check if the profile is outdated and can be upgraded.
func specialProfileNeedsReset(profile *Profile) bool {
switch {
case profile.Source != SourceLocal:
// Special profiles live in the local scope only.
return false
case profile.LastEdited > 0:
// Profile was edited - don't override user settings.
return false
}
switch profile.ID {
case SystemResolverProfileID:
return canBeUpgraded(profile, "10.5.2021")
default:
// Not a special profile or no upgrade available yet.
return false
}
}
func canBeUpgraded(profile *Profile, upgradeDate string) bool {
// Parse upgrade date.
upgradeTime, err := time.Parse("2.1.2006", upgradeDate)
if err != nil {
log.Warningf("profile: failed to parse date %q: %s", upgradeDate, err)
return false
}
// Check if the upgrade is applicable.
if profile.Meta().Created < upgradeTime.Unix() {
log.Infof("profile: upgrading special profile %s", profile.ScopedID())
notifications.NotifyInfo(
"profiles:upgraded-special-profile-"+profile.ID,
profile.Name+" Settings Upgraded",
// TODO: Remove disclaimer.
fmt.Sprintf(
"The %s settings were automatically upgraded. The current app settings have been replaced, as the Portmaster did not detect any changes made by you. Please note that settings upgrades before June 2021 might not detect previous changes correctly and you might want to review the new settings.",
profile.Name,
),
notifications.Action{
ID: "ack",
Text: "OK",
},
notifications.Action{
Text: "Open Settings",
Type: notifications.ActionTypeOpenProfile,
Payload: profile.ScopedID(),
},
)
return true
}
return false
}