176 lines
5.3 KiB
Go
176 lines
5.3 KiB
Go
package useCases
|
|
|
|
import (
|
|
"RenewCMS/internal/domain/update"
|
|
"strings"
|
|
"time"
|
|
)
|
|
|
|
type ManageBrowserUpdatesDependencies struct {
|
|
Probe update.MachineProbe
|
|
Locator update.ServiceLocator
|
|
Units update.UnitWriter
|
|
Manager update.UnitManager
|
|
Status update.HelperStatusWriter
|
|
Now func() time.Time
|
|
}
|
|
|
|
type EnableBrowserUpdatesUseCase struct {
|
|
dependencies ManageBrowserUpdatesDependencies
|
|
}
|
|
|
|
type DisableBrowserUpdatesUseCase struct {
|
|
dependencies ManageBrowserUpdatesDependencies
|
|
}
|
|
|
|
func NewEnableBrowserUpdatesUseCase(dependencies ManageBrowserUpdatesDependencies) *EnableBrowserUpdatesUseCase {
|
|
return &EnableBrowserUpdatesUseCase{dependencies: dependencies}
|
|
}
|
|
|
|
func NewDisableBrowserUpdatesUseCase(dependencies ManageBrowserUpdatesDependencies) *DisableBrowserUpdatesUseCase {
|
|
return &DisableBrowserUpdatesUseCase{dependencies: dependencies}
|
|
}
|
|
|
|
func (e *EnableBrowserUpdatesUseCase) Enable(options update.InstallOptions) (string, error) {
|
|
d := e.dependencies
|
|
if err := update.CheckInstallEnvironment(d.Probe); err != nil {
|
|
return "", err
|
|
}
|
|
resolved, err := e.resolve(options)
|
|
if err != nil {
|
|
return "", err
|
|
}
|
|
if err := e.install(resolved); err != nil {
|
|
e.undo()
|
|
return "", err
|
|
}
|
|
status := update.HelperStatus{
|
|
Version: update.HelperStatusVersion,
|
|
Service: resolved.Service,
|
|
Binary: resolved.Binary,
|
|
DataDir: resolved.DataDir,
|
|
InstalledAt: d.Now().UTC(),
|
|
}
|
|
if err := d.Status.Write(resolved.DataDir, status); err != nil {
|
|
e.undo()
|
|
return "", err
|
|
}
|
|
return enabledMessage(resolved), nil
|
|
}
|
|
|
|
func (e *EnableBrowserUpdatesUseCase) resolve(options update.InstallOptions) (update.InstallOptions, error) {
|
|
service := firstNonEmpty(options.Service, update.DefaultService)
|
|
description, found := e.dependencies.Locator.Locate(service)
|
|
resolved := update.InstallOptions{
|
|
Service: service,
|
|
Binary: firstNonEmpty(options.Binary, description.BinaryPath),
|
|
DataDir: firstNonEmpty(options.DataDir, description.DataDir),
|
|
}
|
|
if resolved.Binary == "" || (resolved.DataDir == "" && !found) {
|
|
return resolved, update.ErrServiceNotFound
|
|
}
|
|
if resolved.DataDir == "" {
|
|
return resolved, update.ErrDataDirNotFound
|
|
}
|
|
resolved.Port = e.port(options.Port, description)
|
|
return resolved, update.ValidatePort(resolved.Port)
|
|
}
|
|
|
|
func (e *EnableBrowserUpdatesUseCase) port(flag string, description update.ServiceDescription) string {
|
|
if flag != "" {
|
|
return flag
|
|
}
|
|
if port, found := e.dependencies.Locator.PortFromEnvironmentFile(description.EnvironmentFile); found {
|
|
return port
|
|
}
|
|
return update.DefaultPort
|
|
}
|
|
|
|
func (e *EnableBrowserUpdatesUseCase) install(options update.InstallOptions) error {
|
|
d := e.dependencies
|
|
layout := update.HelperLayout{DataDir: options.DataDir, BinaryPath: options.Binary}
|
|
if err := d.Units.Write(update.ServiceUnitName, update.RenderServiceUnit(options)); err != nil {
|
|
return err
|
|
}
|
|
if err := d.Units.Write(update.PathUnitName, update.RenderPathUnit(layout)); err != nil {
|
|
return err
|
|
}
|
|
if err := d.Manager.DaemonReload(); err != nil {
|
|
return err
|
|
}
|
|
return d.Manager.EnableNow(update.PathUnitName)
|
|
}
|
|
|
|
func (e *EnableBrowserUpdatesUseCase) undo() {
|
|
d := e.dependencies
|
|
_ = d.Manager.DisableNow(update.PathUnitName)
|
|
_, _ = d.Units.Remove(update.ServiceUnitName)
|
|
_, _ = d.Units.Remove(update.PathUnitName)
|
|
_ = d.Manager.DaemonReload()
|
|
}
|
|
|
|
func enabledMessage(options update.InstallOptions) string {
|
|
lines := []string{
|
|
"Browser updates are enabled for " + options.Service + ".",
|
|
"Installed " + update.PathUnitName + " and " + update.ServiceUnitName + " (port " + options.Port + ") and wrote " + update.HelperStatusFileName + " in " + options.DataDir + ".",
|
|
"To undo it, run: renewcms disable-browser-updates",
|
|
}
|
|
return strings.Join(lines, "\n")
|
|
}
|
|
|
|
func (u *DisableBrowserUpdatesUseCase) Disable(options update.InstallOptions) (string, error) {
|
|
d := u.dependencies
|
|
if d.Probe.OS() != update.OSLinux || !d.Probe.SystemdRunning() {
|
|
return notEnabledMessage, nil
|
|
}
|
|
if err := update.CheckInstallEnvironment(d.Probe); err != nil {
|
|
return "", err
|
|
}
|
|
dataDir := firstNonEmpty(options.DataDir, u.locatedDataDir(options.Service))
|
|
|
|
_ = d.Manager.DisableNow(update.PathUnitName)
|
|
removed := u.removeUnits()
|
|
if dataDir == "" {
|
|
return "", update.ErrDataDirNotFound
|
|
}
|
|
statusRemoved, err := d.Status.Remove(dataDir)
|
|
if err != nil {
|
|
return "", err
|
|
}
|
|
if !removed && !statusRemoved {
|
|
return notEnabledMessage, nil
|
|
}
|
|
if err := d.Manager.DaemonReload(); err != nil {
|
|
return "", err
|
|
}
|
|
return disabledMessage, nil
|
|
}
|
|
|
|
func (u *DisableBrowserUpdatesUseCase) locatedDataDir(service string) string {
|
|
description, _ := u.dependencies.Locator.Locate(firstNonEmpty(service, update.DefaultService))
|
|
return description.DataDir
|
|
}
|
|
|
|
func (u *DisableBrowserUpdatesUseCase) removeUnits() bool {
|
|
removedAny := false
|
|
for _, name := range []string{update.PathUnitName, update.ServiceUnitName} {
|
|
removed, err := u.dependencies.Units.Remove(name)
|
|
removedAny = removedAny || (removed && err == nil)
|
|
}
|
|
return removedAny
|
|
}
|
|
|
|
const (
|
|
notEnabledMessage = "Browser updates were not enabled, nothing to remove."
|
|
disabledMessage = "Browser updates are disabled. The restart request, the result, the staged files and the backups were left in place."
|
|
)
|
|
|
|
func firstNonEmpty(values ...string) string {
|
|
for _, value := range values {
|
|
if value != "" {
|
|
return value
|
|
}
|
|
}
|
|
return ""
|
|
}
|