mirror of
https://github.com/octoleo/syncthing.git
synced 2024-11-09 14:50:56 +00:00
Let server side decide if restart is needed on config change
This commit is contained in:
parent
5a2328d9a5
commit
df381fd03f
File diff suppressed because one or more lines are too long
@ -16,6 +16,7 @@ import (
|
|||||||
"net"
|
"net"
|
||||||
"net/http"
|
"net/http"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
|
"reflect"
|
||||||
"runtime"
|
"runtime"
|
||||||
"sync"
|
"sync"
|
||||||
"time"
|
"time"
|
||||||
@ -210,9 +211,43 @@ func restPostConfig(req *http.Request) {
|
|||||||
newCfg.GUI.Password = string(hash)
|
newCfg.GUI.Password = string(hash)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Figure out if any changes require a restart
|
||||||
|
|
||||||
|
if len(cfg.Repositories) != len(newCfg.Repositories) {
|
||||||
|
configInSync = false
|
||||||
|
} else {
|
||||||
|
om := cfg.RepoMap()
|
||||||
|
nm := newCfg.RepoMap()
|
||||||
|
for id := range om {
|
||||||
|
if !reflect.DeepEqual(om[id], nm[id]) {
|
||||||
|
configInSync = false
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(cfg.Nodes) != len(newCfg.Nodes) {
|
||||||
|
configInSync = false
|
||||||
|
} else {
|
||||||
|
om := cfg.NodeMap()
|
||||||
|
nm := newCfg.NodeMap()
|
||||||
|
for k := range om {
|
||||||
|
if _, ok := nm[k]; !ok {
|
||||||
|
configInSync = false
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if !reflect.DeepEqual(cfg.Options, newCfg.Options) {
|
||||||
|
configInSync = false
|
||||||
|
}
|
||||||
|
|
||||||
|
// Activate and save
|
||||||
|
|
||||||
cfg = newCfg
|
cfg = newCfg
|
||||||
saveConfig()
|
saveConfig()
|
||||||
configInSync = false
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -126,6 +126,22 @@ type GUIConfiguration struct {
|
|||||||
APIKey string `xml:"apikey,omitempty"`
|
APIKey string `xml:"apikey,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (cfg *Configuration) NodeMap() map[string]NodeConfiguration {
|
||||||
|
m := make(map[string]NodeConfiguration, len(cfg.Nodes))
|
||||||
|
for _, n := range cfg.Nodes {
|
||||||
|
m[n.NodeID] = n
|
||||||
|
}
|
||||||
|
return m
|
||||||
|
}
|
||||||
|
|
||||||
|
func (cfg *Configuration) RepoMap() map[string]RepositoryConfiguration {
|
||||||
|
m := make(map[string]RepositoryConfiguration, len(cfg.Repositories))
|
||||||
|
for _, r := range cfg.Repositories {
|
||||||
|
m[r.ID] = r
|
||||||
|
}
|
||||||
|
return m
|
||||||
|
}
|
||||||
|
|
||||||
func setDefaults(data interface{}) error {
|
func setDefaults(data interface{}) error {
|
||||||
s := reflect.ValueOf(data).Elem()
|
s := reflect.ValueOf(data).Elem()
|
||||||
t := s.Type()
|
t := s.Type()
|
||||||
|
27
gui/app.js
27
gui/app.js
@ -268,6 +268,16 @@ syncthing.controller('SyncthingCtrl', function ($scope, $http) {
|
|||||||
$('#settings').modal({backdrop: 'static', keyboard: true});
|
$('#settings').modal({backdrop: 'static', keyboard: true});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
$scope.saveConfig = function() {
|
||||||
|
var cfg = JSON.stringify($scope.config);
|
||||||
|
var opts = {headers: {'Content-Type': 'application/json'}};
|
||||||
|
$http.post(urlbase + '/config', cfg, opts).success(function () {
|
||||||
|
$http.get(urlbase + '/config/sync').success(function (data) {
|
||||||
|
$scope.configInSync = data.configInSync;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
$scope.saveSettings = function () {
|
$scope.saveSettings = function () {
|
||||||
// Make sure something changed
|
// Make sure something changed
|
||||||
var changed = ! angular.equals($scope.config.Options, $scope.config.workingOptions) ||
|
var changed = ! angular.equals($scope.config.Options, $scope.config.workingOptions) ||
|
||||||
@ -281,10 +291,9 @@ syncthing.controller('SyncthingCtrl', function ($scope, $http) {
|
|||||||
// Apply new settings locally
|
// Apply new settings locally
|
||||||
$scope.config.Options = angular.copy($scope.config.workingOptions);
|
$scope.config.Options = angular.copy($scope.config.workingOptions);
|
||||||
$scope.config.GUI = angular.copy($scope.config.workingGUI);
|
$scope.config.GUI = angular.copy($scope.config.workingGUI);
|
||||||
|
|
||||||
$scope.configInSync = false;
|
|
||||||
$scope.config.Options.ListenAddress = $scope.config.Options.ListenStr.split(',').map(function (x) { return x.trim(); });
|
$scope.config.Options.ListenAddress = $scope.config.Options.ListenStr.split(',').map(function (x) { return x.trim(); });
|
||||||
$http.post(urlbase + '/config', JSON.stringify($scope.config), {headers: {'Content-Type': 'application/json'}});
|
|
||||||
|
$scope.saveConfig();
|
||||||
}
|
}
|
||||||
|
|
||||||
$('#settings').modal("hide");
|
$('#settings').modal("hide");
|
||||||
@ -358,14 +367,12 @@ syncthing.controller('SyncthingCtrl', function ($scope, $http) {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
$scope.configInSync = false;
|
$scope.saveConfig();
|
||||||
$http.post(urlbase + '/config', JSON.stringify($scope.config), {headers: {'Content-Type': 'application/json'}});
|
|
||||||
};
|
};
|
||||||
|
|
||||||
$scope.saveNode = function () {
|
$scope.saveNode = function () {
|
||||||
var nodeCfg, done, i;
|
var nodeCfg, done, i;
|
||||||
|
|
||||||
$scope.configInSync = false;
|
|
||||||
$('#editNode').modal('hide');
|
$('#editNode').modal('hide');
|
||||||
nodeCfg = $scope.currentNode;
|
nodeCfg = $scope.currentNode;
|
||||||
nodeCfg.NodeID = nodeCfg.NodeID.replace(/ /g, '').replace(/-/g, '').toUpperCase().trim();
|
nodeCfg.NodeID = nodeCfg.NodeID.replace(/ /g, '').replace(/-/g, '').toUpperCase().trim();
|
||||||
@ -387,7 +394,7 @@ syncthing.controller('SyncthingCtrl', function ($scope, $http) {
|
|||||||
$scope.nodes.sort(nodeCompare);
|
$scope.nodes.sort(nodeCompare);
|
||||||
$scope.config.Nodes = $scope.nodes;
|
$scope.config.Nodes = $scope.nodes;
|
||||||
|
|
||||||
$http.post(urlbase + '/config', JSON.stringify($scope.config), {headers: {'Content-Type': 'application/json'}});
|
$scope.saveConfig();
|
||||||
};
|
};
|
||||||
|
|
||||||
$scope.otherNodes = function () {
|
$scope.otherNodes = function () {
|
||||||
@ -462,7 +469,6 @@ syncthing.controller('SyncthingCtrl', function ($scope, $http) {
|
|||||||
$scope.saveRepo = function () {
|
$scope.saveRepo = function () {
|
||||||
var repoCfg, done, i;
|
var repoCfg, done, i;
|
||||||
|
|
||||||
$scope.configInSync = false;
|
|
||||||
$('#editRepo').modal('hide');
|
$('#editRepo').modal('hide');
|
||||||
repoCfg = $scope.currentRepo;
|
repoCfg = $scope.currentRepo;
|
||||||
repoCfg.Nodes = [];
|
repoCfg.Nodes = [];
|
||||||
@ -490,7 +496,7 @@ syncthing.controller('SyncthingCtrl', function ($scope, $http) {
|
|||||||
$scope.repos[repoCfg.ID] = repoCfg;
|
$scope.repos[repoCfg.ID] = repoCfg;
|
||||||
$scope.config.Repositories = repoList($scope.repos);
|
$scope.config.Repositories = repoList($scope.repos);
|
||||||
|
|
||||||
$http.post(urlbase + '/config', JSON.stringify($scope.config), {headers: {'Content-Type': 'application/json'}});
|
$scope.saveConfig();
|
||||||
};
|
};
|
||||||
|
|
||||||
$scope.sharesRepo = function(repoCfg) {
|
$scope.sharesRepo = function(repoCfg) {
|
||||||
@ -511,8 +517,7 @@ syncthing.controller('SyncthingCtrl', function ($scope, $http) {
|
|||||||
delete $scope.repos[$scope.currentRepo.ID];
|
delete $scope.repos[$scope.currentRepo.ID];
|
||||||
$scope.config.Repositories = repoList($scope.repos);
|
$scope.config.Repositories = repoList($scope.repos);
|
||||||
|
|
||||||
$scope.configInSync = false;
|
$scope.saveConfig();
|
||||||
$http.post(urlbase + '/config', JSON.stringify($scope.config), {headers: {'Content-Type': 'application/json'}});
|
|
||||||
};
|
};
|
||||||
|
|
||||||
$scope.setAPIKey = function (cfg) {
|
$scope.setAPIKey = function (cfg) {
|
||||||
|
Loading…
Reference in New Issue
Block a user