500 lines
28 KiB
HTML
500 lines
28 KiB
HTML
<!-- Modal change avatar -->
|
|
<div class="modal fade" id="avatarChangeModal" tabindex="-1" role="dialog">
|
|
<div class="modal-dialog">
|
|
<div class="modal-content">
|
|
<div class="modal-header">
|
|
<h4 class="modal-title">Change your Cloudron Avatar</h4>
|
|
</div>
|
|
<div class="modal-body settings-avatar-selector">
|
|
<img id="previewAvatar" width="128" height="128" ng-src="{{avatarChange.avatar.data || avatarChange.avatar.url || client.avatar}}"/>
|
|
<input type="file" id="avatarFileInput" style="display: none" accept="image/png"/>
|
|
|
|
<br/>
|
|
<br/>
|
|
|
|
<div class="grid">
|
|
<div class="item" ng-repeat="avatar in avatarChange.availableAvatars" style="background-image: url('{{avatar.data || avatar.url}}');" ng-click="avatarChange.setPreviewAvatar(avatar)"></div>
|
|
<div class="item add" ng-click="avatarChange.showCustomAvatarSelector()"></div>
|
|
</div>
|
|
</div>
|
|
<div class="modal-footer">
|
|
<button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button>
|
|
<button type="button" class="btn btn-success" ng-click="avatarChange.doChangeAvatar()" ng-disabled="avatarChange.busy"><i class="fa fa-circle-o-notch fa-spin" ng-show="avatarChange.busy"></i> Change</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Modal change cloudron name -->
|
|
<div class="modal fade" id="cloudronNameChangeModal" tabindex="-1" role="dialog">
|
|
<div class="modal-dialog">
|
|
<div class="modal-content">
|
|
<div class="modal-header">
|
|
<h4 class="modal-title">Change Cloudron Name</h4>
|
|
</div>
|
|
<div class="modal-body">
|
|
<form name="cloudronNameChangeForm" role="form" novalidate ng-submit="cloudronNameChange.submit()" autocomplete="off">
|
|
<div class="form-group" ng-class="{ 'has-error': (cloudronNameChangeForm.name.$dirty && cloudronNameChangeForm.name.$invalid) }">
|
|
<label class="control-label">Name</label>
|
|
<div class="control-label" ng-show="(!cloudronNameChangeForm.name.$dirty && cloudronNameChange.error.name) || (cloudronNameChangeForm.name.$dirty && cloudronNameChangeForm.name.$invalid)">
|
|
<small ng-show="cloudronNameChangeForm.name.$error.required">A name is required</small>
|
|
<small ng-show="cloudronNameChangeForm.name.$error.maxlength">The name is too long</small>
|
|
<small ng-show="!cloudronNameChangeForm.name.$dirty && cloudronNameChange.error.name">{{ cloudronNameChange.error.name }}</small>
|
|
</div>
|
|
<input type="text" class="form-control" ng-model="cloudronNameChange.name" name="name" id="inputCloudronName" ng-maxlength="30" required autofocus>
|
|
</div>
|
|
<input class="ng-hide" type="submit" ng-disabled="cloudronNameChangeForm.$invalid"/>
|
|
</form>
|
|
</div>
|
|
<div class="modal-footer">
|
|
<button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button>
|
|
<button type="button" class="btn btn-success" ng-click="cloudronNameChange.submit()" ng-disabled="cloudronNameChangeForm.$invalid || cloudronNameChange.busy"><i class="fa fa-circle-o-notch fa-spin" ng-show="cloudronNameChange.busy"></i> Change</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Modal backup failed -->
|
|
<div class="modal fade" id="createBackupFailedModal" tabindex="-1" role="dialog">
|
|
<div class="modal-dialog">
|
|
<div class="modal-content">
|
|
<div class="modal-header">
|
|
<h4 class="modal-title">Unable to create backup</h4>
|
|
</div>
|
|
<div class="modal-body">
|
|
{{ createBackup.errorMessage }}
|
|
</div>
|
|
<div class="modal-footer">
|
|
<button type="button" class="btn btn-success" data-dismiss="modal">OK</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Modal plan change -->
|
|
<div class="modal fade" id="planChangeModal" tabindex="-1" role="dialog">
|
|
<div class="modal-dialog">
|
|
<div class="modal-content">
|
|
<div class="modal-header">
|
|
<button type="button" class="close" data-dismiss="modal">×</button>
|
|
<h4 class="modal-title">Cloudron Change Plan</h4>
|
|
</div>
|
|
<div class="modal-body">
|
|
This will change your plan from <b>{{ currentPlan.name }}</b> to <b>{{ planChange.requestedPlan.name }}</b>.
|
|
<br/>
|
|
<br/>
|
|
Your apps and data will be migrated to the new Cloudron and will take around 15 minutes.
|
|
<br/>
|
|
<br/>
|
|
<br/>
|
|
<form name="planChangeForm" role="form" novalidate ng-submit="planChange.doChangePlan(planChangeForm)" autocomplete="off">
|
|
<fieldset>
|
|
<input type="password" style="display: none;">
|
|
<div class="form-group" ng-class="{ 'has-error': (!planChangeForm.password.$dirty && planChange.error.password) || (planChangeForm.password.$dirty && planChangeForm.password.$invalid) }">
|
|
<label class="control-label">Give your password to verify that you are performing that action</label>
|
|
<div class="control-label" ng-show="(!planChangeForm.password.$dirty && planChange.error.password) || (planChangeForm.password.$dirty && planChangeForm.password.$invalid)">
|
|
<small ng-show=" planChangeForm.password.$dirty && planChangeForm.password.$invalid">A password is required</small>
|
|
<small ng-show="!planChangeForm.password.$dirty && planChange.error.password">Wrong password</small>
|
|
</div>
|
|
<input type="password" class="form-control" ng-model="planChange.password" id="inputPlanChangePassword" name="password" required autofocus>
|
|
</div>
|
|
<input class="ng-hide" type="submit" ng-disabled="planChangeForm.$invalid"/>
|
|
</fieldset>
|
|
</form>
|
|
</div>
|
|
<div class="modal-footer">
|
|
<button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button>
|
|
<button type="button" class="btn btn-success" ng-click="planChange.doChangePlan()" ng-disabled="planChange.busy"><i class="fa fa-circle-o-notch fa-spin" ng-show="planChange.busy"></i> Confirm</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- modal backup config -->
|
|
<div class="modal fade" id="configureBackupModal" tabindex="-1" role="dialog">
|
|
<div class="modal-dialog">
|
|
<div class="modal-content">
|
|
<div class="modal-header">
|
|
<h4 class="modal-title">Configure Backup Storage</h4>
|
|
</div>
|
|
<div class="modal-body">
|
|
<p>Cloudron makes a complete backup of your system every day.</p>
|
|
|
|
<form name="configureBackupForm" role="form" novalidate ng-submit="configureBackup.submit()" autocomplete="off">
|
|
<fieldset>
|
|
<p class="has-error text-center" ng-show="configureBackup.error">{{ configureBackup.error.generic }}</p>
|
|
|
|
<div class="form-group">
|
|
<label class="control-label" for="storageProviderProvider">Storage provider <sup><a ng-href="{{ config.webServerOrigin }}/documentation/backups/" class="help" target="_blank"><i class="fa fa-question-circle"></i></a></sup></label>
|
|
<select class="form-control" id="storageProviderProvider" ng-model="configureBackup.provider" ng-options="a.value as a.name for a in storageProvider" ng-change=configureBackup.clearForm()></select>
|
|
</div>
|
|
|
|
<!-- Noop -->
|
|
<div class="form-group" ng-show="configureBackup.provider === 'noop'">
|
|
<p class="has-error">
|
|
This option breaks the backup and restore functionality of Cloudron and should only be used for testing. Please make sure the server is completely backed up using alternate means.
|
|
</p>
|
|
</div>
|
|
|
|
<!-- Filesystem -->
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.backupFolder }" ng-show="configureBackup.provider === 'filesystem'">
|
|
<label class="control-label" for="inputConfigureBackupFolder">Local backup directory</label>
|
|
<input type="text" class="form-control" ng-model="configureBackup.backupFolder" id="inputConfigureBackupFolder" name="backupFolder" ng-disabled="configureBackup.busy" placeholder="Directory for backups" ng-required="configureBackup.provider === 'filesystem'">
|
|
|
|
<p class="has-error" ng-show="configureBackup.provider === 'filesystem'">
|
|
Please ensure that the backup directory is an external ext4 disk
|
|
</p>
|
|
</div>
|
|
|
|
<div class="checkbox" ng-show="configureBackup.provider === 'filesystem'">
|
|
<label>
|
|
<input type="checkbox" ng-model="configureBackup.useHardlinks" id="inputConfigureUseHardlinks">
|
|
Use hardlinks
|
|
</input>
|
|
</label>
|
|
</div>
|
|
|
|
<!-- S3/Minio/SOS/GCS -->
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.endpoint }" ng-show="configureBackup.provider === 'minio' || configureBackup.provider === 's3-v4-compat'">
|
|
<label class="control-label" for="inputConfigureBackupEndpoint">Endpoint</label>
|
|
<input type="text" class="form-control" ng-model="configureBackup.endpoint" id="inputConfigureBackupEndpoint" name="endpoint" ng-disabled="configureBackup.busy" placeholder="URL of Minio/S3 Compatible" ng-required="configureBackup.provider === 'minio' || configureBackup.provider === 's3-v4-compat'">
|
|
</div>
|
|
|
|
<div class="checkbox" ng-show="configureBackup.provider === 'minio' || configureBackup.provider === 's3-v4-compat'" >
|
|
<label>
|
|
<input type="checkbox" ng-model="configureBackup.acceptSelfSignedCerts" id="inputConfigureBackupSelfSigned">
|
|
Accept Self-signed certificate
|
|
</input>
|
|
</label>
|
|
</div>
|
|
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.bucket }" ng-show="s3like(configureBackup.provider) || configureBackup.provider === 'gcs'">
|
|
<label class="control-label" for="inputConfigureBackupBucket">Bucket name</label>
|
|
<input type="text" class="form-control" ng-model="configureBackup.bucket" id="inputConfigureBackupBucket" name="bucket" ng-disabled="configureBackup.busy" ng-required="s3like(configureBackup.provider)">
|
|
</div>
|
|
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.prefix }" ng-show="configureBackup.provider !== 'filesystem'">
|
|
<label class="control-label" for="inputConfigureBackupPrefix">Prefix</label>
|
|
<input type="text" class="form-control" ng-model="configureBackup.prefix" id="inputConfigureBackupPrefix" name="prefix" ng-disabled="configureBackup.busy" placeholder="Prefix for backup file names">
|
|
</div>
|
|
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.region }" ng-show="configureBackup.provider === 's3'">
|
|
<label class="control-label" for="inputConfigureBackupRegion">Region</label>
|
|
<select class="form-control" name="region" id="inputConfigureBackupRegion" ng-model="configureBackup.region" ng-options="a.value as a.name for a in s3Regions" ng-disabled="configureBackup.busy" ng-required="configureBackup.provider === 's3'"></select>
|
|
</div>
|
|
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.region }" ng-show="configureBackup.provider === 'digitalocean-spaces'">
|
|
<label class="control-label" for="inputConfigureBackupRegion">Region</label>
|
|
<select class="form-control" name="region" id="inputConfigureBackupRegion" ng-model="configureBackup.endpoint" ng-options="a.value as a.name for a in doSpacesRegions" ng-disabled="configureBackup.busy" ng-required="configureBackup.provider === 'digitalocean-spaces'"></select>
|
|
</div>
|
|
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.accessKeyId }" ng-show="s3like(configureBackup.provider)">
|
|
<label class="control-label" for="inputConfigureBackupAccessKeyId">Access key id</label>
|
|
<input type="text" class="form-control" ng-model="configureBackup.accessKeyId" id="inputConfigureBackupAccessKeyId" name="accessKeyId" ng-disabled="configureBackup.busy" ng-required="s3like(configureBackup.provider)">
|
|
</div>
|
|
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.secretAccessKey }" ng-show="s3like(configureBackup.provider)">
|
|
<label class="control-label" for="inputConfigureBackupSecretAccessKey">Secret access key</label>
|
|
<input type="text" class="form-control" ng-model="configureBackup.secretAccessKey" id="inputConfigureBackupSecretAccessKey" name="secretAccessKey" ng-disabled="configureBackup.busy" ng-required="s3like(configureBackup.provider)">
|
|
</div>
|
|
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.gcsKeyInput }" ng-show="configureBackup.provider === 'gcs'">
|
|
<label class="control-label" for="gcsKeyInput">Service Account Key</label>
|
|
|
|
<div class="input-group">
|
|
<input type="file" id="gcsKeyFileInput" style="display:none"/>
|
|
<input type="text" class="form-control" placeholder="Service Account Key" ng-model="configureBackup.gcsKey.keyFileName" id="gcsKeyInput" name="cert" onclick="getElementById('gcsKeyFileInput').click();" style="cursor: pointer;" ng-disabled="configureBackup.busy" ng-required="configureBackup.provider === 'gcs'">
|
|
<span class="input-group-addon">
|
|
<i class="fa fa-upload" onclick="getElementById('gcsKeyFileInput').click();"></i>
|
|
</span>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="form-group" ng-show="configureBackup.provider !== 'noop'">
|
|
<label class="control-label" for="storageFormat">Storage Format</label>
|
|
<select class="form-control" id="storageFormat" ng-change="configureBackup.key = ''" ng-model="configureBackup.format" ng-options="a.value as a.name for a in formats"></select>
|
|
</div>
|
|
|
|
<div class="form-group" ng-show="configureBackup.provider !== 'noop'">
|
|
<label class="control-label" for="storageRetention">Retention Time</label>
|
|
<select class="form-control" id="storageRetention" ng-model="configureBackup.retentionSecs" ng-options="a.value as a.name for a in retentionTimes"></select>
|
|
</div>
|
|
|
|
<div class="form-group" ng-class="{ 'has-error': configureBackup.error.key }" ng-show="configureBackup.provider !== 'noop' && configureBackup.format === 'tgz'">
|
|
<label class="control-label" for="inputConfigureBackupKey">Encryption key (optional)</label>
|
|
<input type="text" class="form-control" ng-model="configureBackup.key" id="inputConfigureBackupKey" name="prefix" ng-disabled="configureBackup.busy" placeholder="Passphrase used to encrypt the backups">
|
|
</div>
|
|
|
|
<input class="ng-hide" type="submit" ng-disabled="configureBackupForm.$invalid"/>
|
|
</fieldset>
|
|
</form>
|
|
</div>
|
|
<div class="modal-footer ">
|
|
<button type="button" class="btn btn-default" data-dismiss="modal">Cancel</button>
|
|
<button type="submit" class="btn btn-outline btn-success pull-right" ng-click="configureBackup.submit()" ng-disabled="configureBackupForm.$invalid || configureBackup.busy">
|
|
<i class="fa fa-circle-o-notch fa-spin" ng-show="configureBackup.busy"></i><span>Save</span>
|
|
</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="content">
|
|
|
|
<div class="text-left">
|
|
<h1>Settings</h1>
|
|
</div>
|
|
|
|
<div class="text-left">
|
|
<h3>About</h3>
|
|
</div>
|
|
|
|
<div class="card" style="margin-bottom: 15px;">
|
|
<div class="row">
|
|
<div class="col-xs-4" style="min-width: 150px;">
|
|
<div class="settings-avatar" ng-click="avatarChange.showChangeAvatar()" style="background-image: url('{{ client.avatar }}');">
|
|
<div class="overlay"></div>
|
|
</div>
|
|
</div>
|
|
<div class="col-xs-8">
|
|
<table width="100%">
|
|
<tr>
|
|
<td class="text-muted" style="vertical-align: top;">Name</td>
|
|
<td class="text-right" style="vertical-align: top; white-space: nowrap;">{{ config.cloudronName }} <a href="" ng-click="cloudronNameChange.show()"><i class="fa fa-pencil text-small"></i></a></td>
|
|
</tr>
|
|
<tr ng-show="config.provider === 'caas'">
|
|
<td class="text-muted" style="vertical-align: top;">Model</td>
|
|
<td class="text-right" style="vertical-align: top; white-space: nowrap;">{{ config.size }} - {{ config.region }}</td>
|
|
</tr>
|
|
<tr>
|
|
<td class="text-muted" style="vertical-align: top;">Version</td>
|
|
<td class="text-right" style="vertical-align: top; white-space: nowrap;">{{ config.version }}</td>
|
|
</tr>
|
|
<tr>
|
|
<td class="text-muted" style="vertical-align: top;">Provider</td>
|
|
<td class="text-right" style="vertical-align: top; white-space: nowrap;">{{ prettyProviderName(config.provider) }}</td>
|
|
</tr>
|
|
</table>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="text-left" ng-show="config.provider === 'caas'">
|
|
<h3>Plans</h3>
|
|
</div>
|
|
|
|
<div class="card" style="margin-bottom: 15px;" ng-show="config.provider === 'caas'">
|
|
<div class="row">
|
|
<div class="col-xs-12 text-right">
|
|
<a href="{{ config.webServerOrigin }}/console.html#/userprofile?view=credit_card" target="_blank">Change payment method</a>
|
|
or
|
|
<a href="{{ config.webServerOrigin }}/console.html" target="_blank">Cancel this Cloudron</a>
|
|
</div>
|
|
</div>
|
|
<div class="row">
|
|
<div class="col-xs-10 plans" style="margin-left: 20px">
|
|
<div ng-repeat="plan in availablePlans">
|
|
<label>
|
|
<input type="radio" ng-model="planChange.requestedPlan" ng-value="plan">
|
|
{{ plan.name }} ({{ plan.slug | uppercase }}) - {{ plan.price/100 }}{{ currency }}/month
|
|
<span ng-show="currentPlan.name === plan.name" style="font-weight: bold"> (current plan)
|
|
</span>
|
|
</label>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<div class="col-xs-12">
|
|
<button class="btn btn-primary pull-right" ng-disabled="planChange.requestedPlan.name === currentPlan.name" ng-click="planChange.showChangePlan()">Change Plan</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="text-left" ng-show="backupConfig.provider !== 'caas'">
|
|
<h3>Cloudron.io Account</h3>
|
|
</div>
|
|
|
|
<div class="card" style="margin-bottom: 15px;" ng-show="backupConfig.provider !== 'caas'">
|
|
<div class="row">
|
|
<div class="col-xs-12">
|
|
A Cloudron subscription provides access to the Cloudron App Store. This ensures you are running the latest version and keeps your apps and server secure.
|
|
</div>
|
|
</div>
|
|
<br/>
|
|
<div class="row">
|
|
<div class="col-xs-6">
|
|
<span class="text-muted">Account Email</span>
|
|
</div>
|
|
<div class="col-xs-6 text-right">
|
|
<a ng-href="{{ config.webServerOrigin + '/console.html#/userprofile?email=' + appstoreConfig.profile.email }}" target="_blank">{{ appstoreConfig.profile.email }}</a>
|
|
</div>
|
|
</div>
|
|
<div class="row">
|
|
<div class="col-xs-6">
|
|
<span class="text-muted">Cloudron ID</span>
|
|
</div>
|
|
<div class="col-xs-6 text-right">
|
|
<span>{{ appstoreConfig.cloudronId }}</span>
|
|
</div>
|
|
</div>
|
|
<div class="row">
|
|
<div class="col-xs-6">
|
|
<span class="text-muted">Subscription</span>
|
|
</div>
|
|
<div class="col-xs-6 text-right">
|
|
<span>{{ subscription.plan.name }} <span ng-show="subscription.status === 'trialing'">(in trial)</span></span>
|
|
</div>
|
|
</div>
|
|
<br/>
|
|
<div class="row">
|
|
<div class="col-xs-12">
|
|
<a class="btn btn-primary pull-right" ng-href="{{ config.webServerOrigin + '/console.html#/userprofile?view=subscriptions&email=' + appstoreConfig.profile.email }}" target="_blank" ng-hide="subscription.plan.id === 'free'">Configure</a>
|
|
<a class="btn btn-success pull-right" ng-href="{{ config.webServerOrigin + '/console.html#/userprofile?view=subscriptions&email=' + appstoreConfig.profile.email + '&cloudronId=' + appstoreConfig.cloudronId }}" target="_blank" ng-show="subscription.plan.id === 'free'">Setup Subscription</a>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="text-left">
|
|
<h3>Backups</h3>
|
|
</div>
|
|
|
|
<div class="card" style="margin-bottom: 15px;">
|
|
<div class="row">
|
|
<div class="col-xs-6">
|
|
<span class="text-muted">Provider</span>
|
|
</div>
|
|
<div class="col-xs-6 text-right">
|
|
<span>{{ prettyProviderName(backupConfig.provider) }}</span>
|
|
</div>
|
|
</div>
|
|
<div class="row" ng-show="backupConfig.provider !== 'caas'">
|
|
<div class="col-xs-6">
|
|
<span class="text-muted">Location</span>
|
|
</div>
|
|
<div class="col-xs-6 text-right">
|
|
<span ng-show="backupConfig.provider === 'filesystem'">{{ backupConfig.backupFolder }}</span>
|
|
<span ng-show="backupConfig.provider === 'minio' || backupConfig.provider === 'exoscale-sos' || backupConfig.provider === 's3-v4-compat' || backupConfig.provider === 'digitalocean-spaces' || backupConfig.provider === 'gcs'">{{ backupConfig.bucket + '/' + backupConfig.prefix }}</span>
|
|
<span ng-show="backupConfig.provider === 's3'">{{ backupConfig.region + ' ' + backupConfig.bucket + '/' + backupConfig.prefix }}</span>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<div class="col-xs-6">
|
|
<span class="text-muted">Storage Format</span>
|
|
</div>
|
|
<div class="col-xs-6 text-right">
|
|
<span>{{ backupConfig.format }}</span>
|
|
</div>
|
|
</div>
|
|
|
|
<br/>
|
|
|
|
<div class="row">
|
|
<div class="col-xs-4">
|
|
<span class="text-muted">Backup ID</span>
|
|
</div>
|
|
<div class="col-xs-8 text-right">
|
|
<span ng-click-select ng-show="lastBackup">{{ lastBackup.id }}</span>
|
|
<span ng-hide="lastBackup">No backups have been made yet</span>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<div class="col-xs-6">
|
|
<span class="text-muted">Last backup</span>
|
|
</div>
|
|
<div class="col-xs-6 text-right">
|
|
<span ng-show="lastBackup">{{ lastBackup.creationTime | prettyDate }}</span>
|
|
<span ng-hide="lastBackup">-</span>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<br/>
|
|
<div class="col-md-12">
|
|
<div ng-show="createBackup.busy" class="progress progress-striped active animateMe">
|
|
<div class="progress-bar progress-bar-success" role="progressbar" style="width: {{ createBackup.percent }}%"></div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<div class="col-md-11" ng-show="createBackup.busy">
|
|
<p class="text-muted status" style="text-overflow: ellipsis; white-space: nowrap; overflow: hidden">
|
|
{{ createBackup.detail || 'Syncing ...' }}
|
|
</p>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<div class="col-md-6">
|
|
<p ng-show="createBackup.busy">{{ createBackup.message }}</p>
|
|
<p ng-hide="createBackup.busy">
|
|
<div class="has-error" ng-show="createBackup.percent === 100 && createBackup.result">{{ createBackup.result }}</div>
|
|
</p>
|
|
</div>
|
|
<div class="col-md-6 text-right" ng-show="backupConfig.provider !== 'caas'">
|
|
<button class="btn btn-outline btn-primary pull-right" ng-click="configureBackup.show()" ng-disabled="createBackup.busy">Configure</button>
|
|
|
|
<button class="btn btn-outline btn-primary" ng-click="createBackup.doCreateBackup()" ng-disabled="createBackup.busy" style="margin-right: 10px">Backup now</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="text-left">
|
|
<h3>App Updates</h3>
|
|
</div>
|
|
|
|
<div class="card" style="margin-bottom: 15px;">
|
|
<div class="row">
|
|
<div class="col-md-12">
|
|
<p>Configure the update schedule for the apps</p>
|
|
<p class="text-danger" ng-show="autoUpdate.error"><br/>{{ autoUpdate.error }}</p>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<div class="col-md-12">
|
|
<div class="radio">
|
|
<label>
|
|
<input type="radio" name="scheduleRadio" ng-change="autoUpdate.success = false" ng-model="autoUpdate.pattern" value="00 30 1,3,5,23 * * *">
|
|
Every night
|
|
</label>
|
|
</div>
|
|
<div class="radio">
|
|
<label>
|
|
<input type="radio" name="scheduleRadio" ng-change="autoUpdate.success = false" ng-model="autoUpdate.pattern" value="00 00 3,5 * * 3">
|
|
Wednesday night
|
|
</label>
|
|
</div>
|
|
<div class="radio">
|
|
<label>
|
|
<input type="radio" name="scheduleRadio" ng-change="autoUpdate.success = false" ng-model="autoUpdate.pattern" value="00 00 1,3,5,23 * * 6">
|
|
Saturday night
|
|
</label>
|
|
</div>
|
|
<div class="radio">
|
|
<label>
|
|
<input type="radio" name="scheduleRadio" ng-change="autoUpdate.success = false" ng-model="autoUpdate.pattern" value="never">
|
|
Update manually (Not recommended)
|
|
</label>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="row">
|
|
<div class="col-md-6">
|
|
<i class="fa fa-circle-o-notch fa-spin" ng-show="autoUpdate.busy"></i>
|
|
<span class="text-success text-bold" ng-show="autoUpdate.success && autoUpdate.pattern === autoUpdate.currentPattern">Saved</span>
|
|
</div>
|
|
|
|
<div class="col-md-6 text-right">
|
|
<button class="btn btn-outline btn-primary pull-right" ng-click="autoUpdate.submit()" ng-disabled="autoUpdate.busy || autoUpdate.pattern === autoUpdate.currentPattern"> Save</button>
|
|
|
|
<button class="btn btn-outline btn-primary" ng-click="autoUpdate.checkNow()" ng-disabled="autoUpdate.busy" style="margin-right: 10px">Check now</button>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</div>
|