support importing/exporting AriaNg settings
This commit is contained in:
parent
e6d7e7fd1a
commit
93ab9c4072
|
@ -378,6 +378,7 @@
|
||||||
<script src="scripts/directives/settingDialog.js"></script>
|
<script src="scripts/directives/settingDialog.js"></script>
|
||||||
<script src="scripts/directives/tooltip.js"></script>
|
<script src="scripts/directives/tooltip.js"></script>
|
||||||
<script src="scripts/directives/validUrls.js"></script>
|
<script src="scripts/directives/validUrls.js"></script>
|
||||||
|
<script src="scripts/directives/blobDownload.js"></script>
|
||||||
<script src="scripts/filters/dateDuration.js"></script>
|
<script src="scripts/filters/dateDuration.js"></script>
|
||||||
<script src="scripts/filters/fileOrderBy.js"></script>
|
<script src="scripts/filters/fileOrderBy.js"></script>
|
||||||
<script src="scripts/filters/longDate.js"></script>
|
<script src="scripts/filters/longDate.js"></script>
|
||||||
|
|
|
@ -26,6 +26,9 @@ Search=搜索
|
||||||
Default=默认
|
Default=默认
|
||||||
Expand=展开
|
Expand=展开
|
||||||
Collapse=折叠
|
Collapse=折叠
|
||||||
|
Open=打开
|
||||||
|
Save=保存
|
||||||
|
Import=导入
|
||||||
Remove Task=删除任务
|
Remove Task=删除任务
|
||||||
Clear Stopped Tasks=清空已结束任务
|
Clear Stopped Tasks=清空已结束任务
|
||||||
Click to view task detail=点击查看任务详情
|
Click to view task detail=点击查看任务详情
|
||||||
|
@ -157,6 +160,12 @@ Navigate to Task Detail Page=转到任务详情页面
|
||||||
RPC List Display Order=RPC 列表显示顺序
|
RPC List Display Order=RPC 列表显示顺序
|
||||||
Recently Used=最近使用
|
Recently Used=最近使用
|
||||||
RPC Alias=RPC 别名
|
RPC Alias=RPC 别名
|
||||||
|
Import / Export AriaNg Settings=导入 / 导出 AriaNg 设置
|
||||||
|
Import Settings=导入设置
|
||||||
|
Export Settings=导出设置
|
||||||
|
Confirm Import=确认导入
|
||||||
|
Are you sure you want to import all settings?=您是否要导入所有设置?
|
||||||
|
Invalid settings data format!=无效的设置数据格式!
|
||||||
Supported Placeholder=支持的占位符
|
Supported Placeholder=支持的占位符
|
||||||
AriaNg Title=AriaNg 标题
|
AriaNg Title=AriaNg 标题
|
||||||
Downloading Count=正在下载数量
|
Downloading Count=正在下载数量
|
||||||
|
|
|
@ -26,6 +26,9 @@ Search=搜尋
|
||||||
Default=預設
|
Default=預設
|
||||||
Expand=展開
|
Expand=展開
|
||||||
Collapse=摺疊
|
Collapse=摺疊
|
||||||
|
Open=打開
|
||||||
|
Save=儲存
|
||||||
|
Import=匯入
|
||||||
Remove Task=刪除工作
|
Remove Task=刪除工作
|
||||||
Clear Stopped Tasks=清除已結束工作
|
Clear Stopped Tasks=清除已結束工作
|
||||||
Click to view task detail=點選檢視工作詳情
|
Click to view task detail=點選檢視工作詳情
|
||||||
|
@ -157,6 +160,12 @@ Navigate to Task Detail Page=轉到工作詳情頁面
|
||||||
RPC List Display Order=RPC 清單顯示順序
|
RPC List Display Order=RPC 清單顯示順序
|
||||||
Recently Used=最近使用
|
Recently Used=最近使用
|
||||||
RPC Alias=RPC 別名
|
RPC Alias=RPC 別名
|
||||||
|
Import / Export AriaNg Settings=匯入 / 匯出 AriaNg 設定
|
||||||
|
Import Settings=匯入設定
|
||||||
|
Export Settings=匯出設定
|
||||||
|
Confirm Import=確認匯入
|
||||||
|
Are you sure you want to import all settings?=您是否要匯入所有設定?
|
||||||
|
Invalid settings data format!=無效的設定資料格式!
|
||||||
Supported Placeholder=支援的預留位置
|
Supported Placeholder=支援的預留位置
|
||||||
AriaNg Title=AriaNg 標題
|
AriaNg Title=AriaNg 標題
|
||||||
Downloading Count=正在下載數量
|
Downloading Count=正在下載數量
|
||||||
|
|
|
@ -37,6 +37,9 @@
|
||||||
downloadTaskRefreshInterval: 1000,
|
downloadTaskRefreshInterval: 1000,
|
||||||
rpcListDisplayOrder: 'recentlyUsed',
|
rpcListDisplayOrder: 'recentlyUsed',
|
||||||
afterCreatingNewTask: 'task-list',
|
afterCreatingNewTask: 'task-list',
|
||||||
removeOldTaskAfterRestarting: false
|
removeOldTaskAfterRestarting: false,
|
||||||
|
displayOrder: 'default:asc',
|
||||||
|
fileListDisplayOrder: 'default:asc',
|
||||||
|
peerListDisplayOrder: 'default:asc'
|
||||||
});
|
});
|
||||||
}());
|
}());
|
||||||
|
|
|
@ -30,6 +30,9 @@
|
||||||
'Default': 'Default',
|
'Default': 'Default',
|
||||||
'Expand': 'Expand',
|
'Expand': 'Expand',
|
||||||
'Collapse': 'Collapse',
|
'Collapse': 'Collapse',
|
||||||
|
'Open': 'Open',
|
||||||
|
'Save': 'Save',
|
||||||
|
'Import': 'Import',
|
||||||
'Remove Task': 'Remove Task',
|
'Remove Task': 'Remove Task',
|
||||||
'Clear Stopped Tasks': 'Clear Stopped Tasks',
|
'Clear Stopped Tasks': 'Clear Stopped Tasks',
|
||||||
'Click to view task detail': 'Click to view task detail',
|
'Click to view task detail': 'Click to view task detail',
|
||||||
|
@ -161,6 +164,12 @@
|
||||||
'RPC List Display Order': 'RPC List Display Order',
|
'RPC List Display Order': 'RPC List Display Order',
|
||||||
'Recently Used': 'Recently Used',
|
'Recently Used': 'Recently Used',
|
||||||
'RPC Alias': 'RPC Alias',
|
'RPC Alias': 'RPC Alias',
|
||||||
|
'Import / Export AriaNg Settings': 'Import / Export AriaNg Settings',
|
||||||
|
'Import Settings': 'Import Settings',
|
||||||
|
'Export Settings': 'Export Settings',
|
||||||
|
'Confirm Import': 'Confirm Import',
|
||||||
|
'Are you sure you want to import all settings?': 'Are you sure you want to import all settings?',
|
||||||
|
'Invalid settings data format!': 'Invalid settings data format!',
|
||||||
'Supported Placeholder': 'Supported Placeholder',
|
'Supported Placeholder': 'Supported Placeholder',
|
||||||
'AriaNg Title': 'AriaNg Title',
|
'AriaNg Title': 'AriaNg Title',
|
||||||
'Downloading Count': 'Downloading Count',
|
'Downloading Count': 'Downloading Count',
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
(function () {
|
(function () {
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
angular.module('ariaNg').controller('AriaNgSettingsController', ['$rootScope', '$scope', '$routeParams', '$window', '$interval', '$timeout', 'ariaNgLanguages', 'ariaNgCommonService', 'ariaNgNotificationService', 'ariaNgLocalizationService', 'ariaNgSettingService', 'ariaNgMonitorService', 'ariaNgTitleService', 'aria2SettingService', function ($rootScope, $scope, $routeParams, $window, $interval, $timeout, ariaNgLanguages, ariaNgCommonService, ariaNgNotificationService, ariaNgLocalizationService, ariaNgSettingService, ariaNgMonitorService, ariaNgTitleService, aria2SettingService) {
|
angular.module('ariaNg').controller('AriaNgSettingsController', ['$rootScope', '$scope', '$routeParams', '$window', '$interval', '$timeout', '$filter', 'ariaNgLanguages', 'ariaNgCommonService', 'ariaNgNotificationService', 'ariaNgLocalizationService', 'ariaNgLogService', 'ariaNgFileService', 'ariaNgSettingService', 'ariaNgMonitorService', 'ariaNgTitleService', 'aria2SettingService', function ($rootScope, $scope, $routeParams, $window, $interval, $timeout, $filter, ariaNgLanguages, ariaNgCommonService, ariaNgNotificationService, ariaNgLocalizationService, ariaNgLogService, ariaNgFileService, ariaNgSettingService, ariaNgMonitorService, ariaNgTitleService, aria2SettingService) {
|
||||||
var extendType = $routeParams.extendType;
|
var extendType = $routeParams.extendType;
|
||||||
var lastRefreshPageNotification = null;
|
var lastRefreshPageNotification = null;
|
||||||
|
|
||||||
|
@ -41,7 +41,10 @@
|
||||||
isInsecureProtocolDisabled: ariaNgSettingService.isInsecureProtocolDisabled(),
|
isInsecureProtocolDisabled: ariaNgSettingService.isInsecureProtocolDisabled(),
|
||||||
settings: ariaNgSettingService.getAllOptions(),
|
settings: ariaNgSettingService.getAllOptions(),
|
||||||
sessionSettings: ariaNgSettingService.getAllSessionOptions(),
|
sessionSettings: ariaNgSettingService.getAllSessionOptions(),
|
||||||
rpcSettings: ariaNgSettingService.getAllRpcSettings()
|
rpcSettings: ariaNgSettingService.getAllRpcSettings(),
|
||||||
|
isSupportBlob: ariaNgFileService.isSupportBlob(),
|
||||||
|
importSettings: null,
|
||||||
|
exportSettings: null
|
||||||
};
|
};
|
||||||
|
|
||||||
$scope.context.showDebugMode = $scope.context.sessionSettings.debugMode || extendType === 'debug';
|
$scope.context.showDebugMode = $scope.context.sessionSettings.debugMode || extendType === 'debug';
|
||||||
|
@ -161,6 +164,60 @@
|
||||||
ariaNgSettingService.setRemoveOldTaskAfterRestarting(value);
|
ariaNgSettingService.setRemoveOldTaskAfterRestarting(value);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
$scope.showImportSettingsModal = function () {
|
||||||
|
$scope.context.importSettings = null;
|
||||||
|
angular.element('#import-settings-modal').modal();
|
||||||
|
};
|
||||||
|
|
||||||
|
$('#import-settings-modal').on('hide.bs.modal', function (e) {
|
||||||
|
$scope.context.importSettings = null;
|
||||||
|
});
|
||||||
|
|
||||||
|
$scope.openAriaNgConfigFile = function () {
|
||||||
|
ariaNgFileService.openFileContent({
|
||||||
|
fileFilter: '.json',
|
||||||
|
fileType: 'text'
|
||||||
|
}, function (result) {
|
||||||
|
$scope.context.importSettings = result.content;
|
||||||
|
}, function (error) {
|
||||||
|
ariaNgLocalizationService.showError(error);
|
||||||
|
}, angular.element('#import-file-holder'));
|
||||||
|
};
|
||||||
|
|
||||||
|
$scope.importSettings = function (settings) {
|
||||||
|
var settingsObj = null;
|
||||||
|
|
||||||
|
try {
|
||||||
|
settingsObj = JSON.parse(settings);
|
||||||
|
} catch (e) {
|
||||||
|
ariaNgLogService.error('[AriaNgSettingsController.importSettings] parse settings json error', e);
|
||||||
|
ariaNgLocalizationService.showError('Invalid settings data format!');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!angular.isObject(settingsObj) || angular.isArray(settingsObj)) {
|
||||||
|
ariaNgLogService.error('[AriaNgSettingsController.importSettings] settings json is not object');
|
||||||
|
ariaNgLocalizationService.showError('Invalid settings data format!');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (settingsObj) {
|
||||||
|
ariaNgLocalizationService.confirm('Confirm Import', 'Are you sure you want to import all settings?', 'warning', function () {
|
||||||
|
ariaNgSettingService.importAllOptions(settingsObj);
|
||||||
|
$window.location.reload();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
$scope.showExportSettingsModal = function () {
|
||||||
|
$scope.context.exportSettings = $filter('json')(ariaNgSettingService.exportAllOptions());
|
||||||
|
angular.element('#export-settings-modal').modal();
|
||||||
|
};
|
||||||
|
|
||||||
|
$('#export-settings-modal').on('hide.bs.modal', function (e) {
|
||||||
|
$scope.context.exportSettings = null;
|
||||||
|
});
|
||||||
|
|
||||||
$scope.addNewRpcSetting = function () {
|
$scope.addNewRpcSetting = function () {
|
||||||
setNeedRefreshPage();
|
setNeedRefreshPage();
|
||||||
|
|
||||||
|
|
24
src/scripts/directives/blobDownload.js
Normal file
24
src/scripts/directives/blobDownload.js
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
(function () {
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
angular.module('ariaNg').directive('ngBlobDownload', ['ariaNgFileService', function (ariaNgFileService) {
|
||||||
|
return {
|
||||||
|
restrict: 'A',
|
||||||
|
scope: {
|
||||||
|
ngBlobDownload: '=ngBlobDownload',
|
||||||
|
ngFileName: '@',
|
||||||
|
ngContentType: '@'
|
||||||
|
},
|
||||||
|
link: function (scope, element) {
|
||||||
|
scope.$watch('ngBlobDownload', function (value) {
|
||||||
|
if (value) {
|
||||||
|
ariaNgFileService.saveFileContent(value, element, {
|
||||||
|
fileName: scope.ngFileName,
|
||||||
|
contentType: scope.ngContentType
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}]);
|
||||||
|
}());
|
|
@ -257,6 +257,49 @@
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
},
|
},
|
||||||
|
importAllOptions: function (options) {
|
||||||
|
var finalOptions = angular.copy(ariaNgDefaultOptions);
|
||||||
|
|
||||||
|
for (var key in options) {
|
||||||
|
if (!options.hasOwnProperty(key) || !finalOptions.hasOwnProperty(key)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (angular.isObject(options[key]) || angular.isArray(options[key])) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
finalOptions[key] = options[key];
|
||||||
|
}
|
||||||
|
|
||||||
|
if (angular.isArray(options.extendRpcServers)) {
|
||||||
|
for (var i = 0; i < options.extendRpcServers.length; i++) {
|
||||||
|
var rpcSetting = options.extendRpcServers[i];
|
||||||
|
var finalRpcSetting = createNewRpcSetting();
|
||||||
|
|
||||||
|
for (var key in rpcSetting) {
|
||||||
|
if (!rpcSetting.hasOwnProperty(key) || !finalRpcSetting.hasOwnProperty(key)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (angular.isObject(rpcSetting[key]) || angular.isArray(rpcSetting[key])) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
finalRpcSetting[key] = rpcSetting[key];
|
||||||
|
}
|
||||||
|
|
||||||
|
finalOptions.extendRpcServers.push(finalRpcSetting);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setOptions(finalOptions);
|
||||||
|
},
|
||||||
|
exportAllOptions: function () {
|
||||||
|
var options = angular.extend({}, ariaNgDefaultOptions, getOptions());
|
||||||
|
|
||||||
|
return options;
|
||||||
|
},
|
||||||
getAllSessionOptions: function () {
|
getAllSessionOptions: function () {
|
||||||
return angular.copy(sessionSettings);
|
return angular.copy(sessionSettings);
|
||||||
},
|
},
|
||||||
|
|
|
@ -151,6 +151,19 @@
|
||||||
</select>
|
</select>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="row">
|
||||||
|
<div class="setting-key setting-key-without-desc col-sm-4">
|
||||||
|
<span translate>Import / Export AriaNg Settings</span>
|
||||||
|
</div>
|
||||||
|
<div class="setting-value col-sm-8">
|
||||||
|
<button class="btn btn-sm btn-default" ng-click="showImportSettingsModal()">
|
||||||
|
<span translate>Import Settings</span>
|
||||||
|
</button>
|
||||||
|
<button class="btn btn-sm btn-default" ng-click="showExportSettingsModal()">
|
||||||
|
<span translate>Export Settings</span>
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
<div class="row tip no-background no-hover">
|
<div class="row tip no-background no-hover">
|
||||||
<span class="asterisk">*</span>
|
<span class="asterisk">*</span>
|
||||||
<span translate>Changes to the settings take effect after refreshing page.</span>
|
<span translate>Changes to the settings take effect after refreshing page.</span>
|
||||||
|
@ -252,6 +265,64 @@
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div id="import-settings-modal" class="modal fade" tabindex="-1" role="dialog">
|
||||||
|
<div class="modal-dialog modal-lg" role="document">
|
||||||
|
<div class="modal-content">
|
||||||
|
<div class="modal-header">
|
||||||
|
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button>
|
||||||
|
<h4 class="modal-title">
|
||||||
|
<span translate>Import Settings</span>
|
||||||
|
<small>
|
||||||
|
<a class="pointer-cursor" title="{{'Open' | translate}}" ng-click="openAriaNgConfigFile()">
|
||||||
|
<i class="icon-primary fa fa-folder-open-o"></i>
|
||||||
|
</a>
|
||||||
|
</small>
|
||||||
|
</h4>
|
||||||
|
</div>
|
||||||
|
<div class="modal-body no-padding">
|
||||||
|
<div class="settings-table striped">
|
||||||
|
<input id="import-file-holder" type="file" style="display: none"/>
|
||||||
|
<textarea class="form-control" ng-model="context.importSettings" rows="20"></textarea>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="modal-footer">
|
||||||
|
<button type="button" class="btn btn-primary" ng-disabled="!context.importSettings || !context.importSettings.length"
|
||||||
|
ng-click="importSettings(context.importSettings)" translate>Import</button>
|
||||||
|
<button type="button" class="btn btn-default" data-dismiss="modal" translate>Cancel</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div id="export-settings-modal" class="modal fade" tabindex="-1" role="dialog">
|
||||||
|
<div class="modal-dialog modal-lg" role="document">
|
||||||
|
<div class="modal-content">
|
||||||
|
<div class="modal-header">
|
||||||
|
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button>
|
||||||
|
<h4 class="modal-title">
|
||||||
|
<span translate>Export Settings</span>
|
||||||
|
<small>
|
||||||
|
<a class="pointer-cursor" title="{{'Copy' | translate}}" text="context.exportSettings" clipboard>
|
||||||
|
<i class="icon-primary fa fa-copy"></i>
|
||||||
|
</a>
|
||||||
|
<a class="pointer-cursor" title="{{'Save' | translate}}" ng-if="context.isSupportBlob"
|
||||||
|
ng-blob-download="context.exportSettings" ng-file-name="AriaNgConfig.json" ng-content-type="application/json">
|
||||||
|
<i class="icon-primary fa fa-save"></i>
|
||||||
|
</a>
|
||||||
|
</small>
|
||||||
|
</h4>
|
||||||
|
</div>
|
||||||
|
<div class="modal-body no-padding">
|
||||||
|
<div class="settings-table striped">
|
||||||
|
<textarea class="form-control" ng-model="context.exportSettings" rows="20" readonly="readonly"></textarea>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="modal-footer">
|
||||||
|
<button type="button" class="btn btn-default" data-dismiss="modal" translate>Cancel</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</section>
|
</section>
|
||||||
<script id="setting-changed-notification.html" type="text/ng-template">
|
<script id="setting-changed-notification.html" type="text/ng-template">
|
||||||
<div class="ui-notification custom-template">
|
<div class="ui-notification custom-template">
|
||||||
|
|
Reference in a new issue