Merge pull request #1867 from gitbucket/refine-system-settings-page

Refine the system settings page
This commit is contained in:
Naoki Takezoe
2018-02-11 01:13:33 +09:00
committed by GitHub
5 changed files with 537 additions and 515 deletions

View File

@@ -231,7 +231,7 @@ trait SystemSettingsControllerBase extends AccountManagementControllerBase {
})
get("/admin/system")(adminOnly {
html.system(flash.get("info"))
html.settings(flash.get("info"))
})
post("/admin/system", form)(adminOnly { form =>

View File

@@ -0,0 +1,47 @@
@(info: Option[Any])(implicit context: gitbucket.core.controller.Context)
@import gitbucket.core.service.OpenIDConnectService
@import gitbucket.core.util.DatabaseConfig
@gitbucket.core.html.main("System settings"){
@gitbucket.core.admin.html.menu("system"){
@gitbucket.core.helper.html.information(info)
<form action="@context.path/admin/system" method="POST" validate="true" class="form-horizontal">
<ul class="nav nav-tabs fill-width" id="pullreq-tab">
<li><a href="#system">System settings</a></li>
<li><a href="#authentication">Authentication</a></li>
</ul>
<div class="tab-content fill-width" style="padding-top: 20px;">
<div class="tab-pane" id="system">
@settings_system(info)
</div>
<div class="tab-pane" id="authentication">
@settings_authentication(info)
</div>
</div>
<hr>
<div class="align-right" style="margin-top: 20px;">
<input type="submit" class="btn btn-success" value="Apply changes"/>
</div>
</form>
}
}
<script>
$(function(){
// Determine active tab from hash
if(location.hash == '#authentication'){
$('li:has(a[href="#authentication"])').addClass('active');
$('div#authentication').addClass('active');
} else {
$('li:has(a[href="#system"])').addClass('active');
$('div#system').addClass('active');
}
// Set hash when tab is clicked
$('ul.nav-tabs li a').click(function(e){
location.href = $(e.delegateTarget).attr("href");
});
$('#pullreq-tab a').click(function (e) {
e.preventDefault();
$(this).tab('show');
});
});
</script>

View File

@@ -0,0 +1,160 @@
@(info: Option[Any])(implicit context: gitbucket.core.controller.Context)
@import gitbucket.core.service.OpenIDConnectService
<!--====================================================================-->
<!-- LDAP -->
<!--====================================================================-->
<fieldset>
<label class="checkbox">
<input type="checkbox" id="ldapAuthentication" name="ldapAuthentication"@if(context.settings.ldap){ checked} />
LDAP
</label>
</fieldset>
<div class="ldap">
<div class="form-group">
<label class="control-label col-md-2" for="ldapHost">LDAP host</label>
<div class="col-md-10">
<input type="text" id="ldapHost" name="ldap.host" class="form-control" value="@context.settings.ldap.map(_.host)"/>
<span id="error-ldap_host" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapPort">LDAP port</label>
<div class="col-md-10">
<input type="text" id="ldapPort" name="ldap.port" class="form-control input-mini" value="@context.settings.ldap.map(_.port)"/>
<span id="error-ldap_port" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapBindDN">Bind DN</label>
<div class="col-md-10">
<input type="text" id="ldapBindDN" name="ldap.bindDN" class="form-control" value="@context.settings.ldap.map(_.bindDN)"/>
<span id="error-ldap_bindDN" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapBindPassword">Bind password</label>
<div class="col-md-10">
<input type="password" id="ldapBindPassword" name="ldap.bindPassword" class="form-control" value="@context.settings.ldap.map(_.bindPassword)"/>
<span id="error-ldap_bindPassword" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapBaseDN">Base DN</label>
<div class="col-md-10">
<input type="text" id="ldapBaseDN" name="ldap.baseDN" class="form-control" value="@context.settings.ldap.map(_.baseDN)"/>
<span id="error-ldap_baseDN" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapUserNameAttribute">User name attribute</label>
<div class="col-md-10">
<input type="text" id="ldapUserNameAttribute" name="ldap.userNameAttribute" class="form-control" value="@context.settings.ldap.map(_.userNameAttribute)"/>
<span id="error-ldap_userNameAttribute" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapAdditionalFilterCondition">Additional filter condition</label>
<div class="col-md-10">
<input type="text" id="ldapAdditionalFilterCondition" name="ldap.additionalFilterCondition" class="form-control" value="@context.settings.ldap.map(_.additionalFilterCondition)"/>
<span id="error-ldap_additionalFilterCondition" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapFullNameAttribute">Full name attribute</label>
<div class="col-md-10">
<input type="text" id="ldapFullNameAttribute" name="ldap.fullNameAttribute" class="form-control" value="@context.settings.ldap.map(_.fullNameAttribute)"/>
<span id="error-ldap_fullNameAttribute" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapMailAttribute">Mail address attribute</label>
<div class="col-md-10">
<input type="text" id="ldapMailAttribute" name="ldap.mailAttribute" class="form-control" value="@context.settings.ldap.map(_.mailAttribute)"/>
<span id="error-ldap_mailAttribute" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2">Enable TLS</label>
<div class="col-md-10">
<input type="checkbox" name="ldap.tls"@if(context.settings.ldap.flatMap(_.tls).getOrElse(false)){ checked}/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2">Enable SSL</label>
<div class="col-md-10">
<input type="checkbox" name="ldap.ssl"@if(context.settings.ldap.flatMap(_.ssl).getOrElse(false)){ checked}/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapBindDN">Keystore</label>
<div class="col-md-10">
<input type="text" id="ldapKeystore" name="ldap.keystore" class="form-control" value="@context.settings.ldap.map(_.keystore)"/>
<span id="error-ldap_keystore" class="error"></span>
</div>
</div>
</div>
<!--====================================================================-->
<!-- OpenID Connect -->
<!--====================================================================-->
<hr>
<fieldset>
<label class="checkbox">
<input type="checkbox" id="oidcAuthentication" name="oidcAuthentication"@if(context.settings.oidc){ checked} />
OpenID Connect
</label>
</fieldset>
<div class="oidc">
<div class="form-group">
<label class="control-label col-md-2" for="oidcIssuer">Issuer</label>
<div class="col-md-10">
<input type="text" id="oidcIssuer" name="oidc.issuer" class="form-control" value="@context.settings.oidc.map(_.issuer.getValue)"/>
<span id="error-oidc_issuer" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="oidcClientID">Client ID</label>
<div class="col-md-10">
<input type="text" id="oidcClientID" name="oidc.clientID" class="form-control" value="@context.settings.oidc.map(_.clientID.getValue)"/>
<span id="error-oidc_clientID" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="oidcClientID">Client secret</label>
<div class="col-md-10">
<input type="password" id="oidcClientSecret" name="oidc.clientSecret" class="form-control" value="@context.settings.oidc.map(_.clientSecret.getValue)"/>
<span id="error-oidc_clientSecret" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="oidcJwsAlgorithm">Expected signature</label>
<div class="col-md-10">
<select id="oidcJwsAlgorithm" name="oidc.jwsAlgorithm" class="form-control">
<option value="" @if(context.settings.oidc.flatMap(_.jwsAlgorithm) == None){selected}>
No signature
</option>
@OpenIDConnectService.JWS_ALGORITHMS.map { case (family, algorithms) =>
<optgroup label="@family">
@algorithms.map { algorithm =>
<option value="@algorithm.getName" @if(context.settings.oidc.flatMap(_.jwsAlgorithm) == Some(algorithm)){selected}>
@algorithm.getName
</option>
}
</optgroup>
}
</select>
<span class="muted">Choose the expected signature algorithm of the token response. Most IdP provides RS256 or HS256.</span>
<span id="error-oidc_jwsAlgorithm" class="error"></span>
</div>
</div>
</div>
<script>
$(function(){
$('#ldapAuthentication').change(function(){
$('.ldap input').prop('disabled', !$(this).prop('checked'));
}).change();
$('#oidcAuthentication').change(function(){
$('.oidc input, .oidc select').prop('disabled', !$(this).prop('checked'));
}).change();
});
</script>

View File

@@ -0,0 +1,329 @@
@(info: Option[Any])(implicit context: gitbucket.core.controller.Context)
@import gitbucket.core.util.DatabaseConfig
<!--====================================================================-->
<!-- System properties -->
<!--====================================================================-->
<table class="table table-bordered">
<tr>
<th>Property</th>
<th>Value</th>
</tr>
<tr>
<td>GITBUCKET_HOME</td>
<td>@gitbucket.core.util.Directory.GitBucketHome</td>
</tr>
<tr>
<td>DATABASE_URL</td>
@if(DatabaseConfig.url.startsWith("jdbc:h2:")) {
<td class="danger">
<p>@gitbucket.core.util.DatabaseConfig.url</p>
<p>
Your GitBucket is running on embedded H2 database.
Recommend to <a href="https://github.com/gitbucket/gitbucket/wiki/External-database-configuration">configure to use external database</a> if you would like to use GitBucket for important purpose.
</p>
</td>
}else{
<td>@gitbucket.core.util.DatabaseConfig.url</td>
}
</tr>
</table>
<!--====================================================================-->
<!-- Base URL -->
<!--====================================================================-->
<hr>
<label><span class="strong">Base URL</span> (e.g. <code>http://example.com/gitbucket</code>)</label>
<fieldset>
<div class="controls">
<input type="text" name="baseUrl" id="baseUrl" class="form-control" value="@context.settings.baseUrl"/>
<span id="error-baseUrl" class="error"></span>
</div>
</fieldset>
<p class="muted">
The base URL is used for redirect, notification email, git repository URL box and more.
If the base URL is empty, GitBucket generates URL from the request information.
You can use this property to adjust to URL differences between the reverse proxy and GitBucket.
</p>
<!--====================================================================-->
<!-- Information -->
<!--====================================================================-->
<hr>
<label><span class="strong">Information</span> (HTML is available)</label>
<fieldset>
<textarea name="information" class="form-control" style="height: 100px;">@context.settings.information</textarea>
</fieldset>
<!--====================================================================-->
<!-- AdminLTE SkinName -->
<!--====================================================================-->
<hr>
<label class="strong">
AdminLTE skin name
</label>
<div class="form-group">
<label class="control-label col-md-2" for="skinName">Skin name</label>
<div class="col-md-10">
<select id="skinName" name="skinName" class="form-control">
<optgroup label="Dark">
@Seq(
("skin-black", "Black"),
("skin-blue", "Blue"),
("skin-green", "Green"),
("skin-purple", "Purple"),
("skin-red", "Red"),
("skin-yellow", "Yellow"),
).map{ skin =>
<option value="@skin._1"@if(skin._1 == context.settings.skinName){ selected=""}>@skin._2</option>
}
</optgroup>
<optgroup label="Light">
@Seq(
("skin-black-light", "Light black"),
("skin-blue-light", "Light blue"),
("skin-green-light", "Light green"),
("skin-purple-light", "Light purple"),
("skin-red-light", "Light red"),
("skin-yellow-light", "Light yellow"),
).map{ skin =>
<option value="@skin._1"@if(skin._1 == context.settings.skinName){ selected=""} >@skin._2</option>
}
</optgroup>
</select>
</div>
</div>
<!--====================================================================-->
<!-- Account registration -->
<!--====================================================================-->
<hr>
<label class="strong">Account registration</label>
<fieldset>
<label class="radio">
<input type="radio" name="allowAccountRegistration" value="true"@if(context.settings.allowAccountRegistration){ checked}>
<span class="strong">Allow</span> <span class="normal">- Users can create accounts by themselves.</span>
</label>
<label class="radio">
<input type="radio" name="allowAccountRegistration" value="false"@if(!context.settings.allowAccountRegistration){ checked}>
<span class="strong">Deny</span> <span class="normal">- Only administrators can create accounts.</span>
</label>
</fieldset>
<hr>
<label class="strong">Default permissions when creating a new repository</label>
<fieldset>
<label class="radio">
<input type="radio" name="isCreateRepoOptionPublic" value="true"@if(context.settings.isCreateRepoOptionPublic){ checked}>
<span class="strong">Public</span> <span class="normal">- All users and guests can read the repository.</span>
</label>
<label class="radio">
<input type="radio" name="isCreateRepoOptionPublic" value="false"@if(!context.settings.isCreateRepoOptionPublic){ checked}>
<span class="strong">Private</span> <span class="normal">- Only collaborators can read the repository.</span>
</label>
</fieldset>
<!--====================================================================-->
<!-- Anonymous access -->
<!--====================================================================-->
<hr>
<label class="strong">Anonymous access</label>
<fieldset>
<label class="radio">
<input type="radio" name="allowAnonymousAccess" value="true"@if(context.settings.allowAnonymousAccess){ checked}>
<span class="strong">Allow</span> <span class="normal">- Anyone can view public repositories and user/group profiles.</span>
</label>
<label class="radio">
<input type="radio" name="allowAnonymousAccess" value="false"@if(!context.settings.allowAnonymousAccess){ checked}>
<span class="strong">Deny</span> <span class="normal">- Users must authenticate before viewing any information.</span>
</label>
</fieldset>
<!--====================================================================-->
<!-- Activity -->
<!--====================================================================-->
<hr>
<label><span class="strong">Limit of activity logs</span> (Unlimited if it is not specified or zero)</label>
<fieldset>
<div class="form-group">
<label class="control-label col-md-2" for="activityLogLimit">Limit</label>
<div class="col-md-10">
<input type="text" id="activityLogLimit" name="activityLogLimit" class="form-control input-mini" value="@context.settings.activityLogLimit"/>
<span id="error-activityLogLimit" class="error"></span>
</div>
</div>
</fieldset>
<!--====================================================================-->
<!-- Services -->
<!--====================================================================-->
<hr>
<label class="strong">Services</label>
<fieldset>
<label class="checkbox">
<input type="checkbox" name="gravatar"@if(context.settings.gravatar){ checked}/>
Use Gravatar for profile images
</label>
</fieldset>
<!--====================================================================-->
<!-- SSH access -->
<!--====================================================================-->
<hr>
<label class="strong">SSH access</label>
<fieldset>
<label class="checkbox">
<input type="checkbox" id="ssh" name="ssh"@if(context.settings.ssh){ checked}/>
Enable SSH access to git repository
<span class="muted normal">(Both SSH host and Base URL are required if SSH access is enabled)</span>
</label>
</fieldset>
<div class="ssh">
<div class="form-group">
<label class="control-label col-md-2" for="sshHost">SSH host</label>
<div class="col-md-10">
<input type="text" id="sshHost" name="sshHost" class="form-control" value="@context.settings.sshHost"/>
<span id="error-sshHost" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="sshPort">SSH port</label>
<div class="col-md-10">
<input type="text" id="sshPort" name="sshPort" class="form-control" value="@context.settings.sshPort"/>
<span id="error-sshPort" class="error"></span>
</div>
</div>
</div>
<!--====================================================================-->
<!-- Communication email -->
<!--====================================================================-->
<hr>
<label class="strong">Communication</label>
<fieldset>
<label class="checkbox">
<input type="checkbox" id="useSMTP" name="useSMTP" @if(context.settings.useSMTP){ checked}/>
SMTP
<span class="muted normal">(Enable notification as well as SMTP configuration if you want to send notification email too)</span>
</label>
</fieldset>
<div class="useSMTP">
<div class="form-group">
<label class="control-label col-md-2" for="smtpHost">SMTP host</label>
<div class="col-md-10">
<input type="text" id="smtpHost" name="smtp.host" class="form-control" value="@context.settings.smtp.map(_.host)"/>
<span id="error-smtp_host" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpPort">SMTP port</label>
<div class="col-md-10">
<input type="text" id="smtpPort" name="smtp.port" class="form-control input-mini" value="@context.settings.smtp.map(_.port)"/>
<span id="error-smtp_port" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpUser">SMTP user</label>
<div class="col-md-10">
<input type="text" id="smtpUser" name="smtp.user" class="form-control" value="@context.settings.smtp.map(_.user)"/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpPassword">SMTP password</label>
<div class="col-md-10">
<input type="password" id="smtpPassword" name="smtp.password" class="form-control" value="@context.settings.smtp.map(_.password)"/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpSsl">Enable SSL</label>
<div class="col-md-10">
<input type="checkbox" id="smtpSsl" name="smtp.ssl"@if(context.settings.smtp.flatMap(_.ssl).getOrElse(false)){ checked}/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpStarttls">Enable STARTTLS</label>
<div class="col-md-10">
<input type="checkbox" id="smtpStarttls" name="smtp.starttls"@if(context.settings.smtp.flatMap(_.starttls).getOrElse(false)){ checked}/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="fromAddress">FROM address</label>
<div class="col-md-10">
<input type="text" id="fromAddress" name="smtp.fromAddress" class="form-control" value="@context.settings.smtp.map(_.fromAddress)"/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="fromName">FROM name</label>
<div class="col-md-10">
<input type="text" id="fromName" name="smtp.fromName" class="form-control" value="@context.settings.smtp.map(_.fromName)"/>
</div>
</div>
<div class="text-right">
Send test mail to:
<input type="text" id="testAddress" size="30"/>
<input type="button" id="sendTestMail" value="Send"/>
</div>
</div>
<!--====================================================================-->
<!-- Notification email -->
<!--====================================================================-->
<hr>
<label class="strong">Notifications</label>
<fieldset>
<label class="checkbox" for="notification">
<input type="checkbox" id="notification" name="notification"@if(context.settings.notification){ checked}/>
Send notifications
</label>
</fieldset>
<script>
$(function(){
$('#skinName').change(function(evt) {
var that = $(evt.target);
var themeCss = $('link[rel="stylesheet"][href*="skin-"]');
var oldVal = new RegExp('(skin-.*?).min.css').exec(themeCss.attr('href'))[1];
themeCss.attr('href', themeCss.attr('href').replace(oldVal, that.val()));
$(document.body).removeClass(oldVal).addClass(that.val());
});
$('#sendTestMail').click(function(){
var host = $('#smtpHost' ).val();
var port = $('#smtpPort' ).val();
var user = $('#smtpUser' ).val();
var password = $('#smtpPassword').val();
var ssl = $('#smtpSsl' ).prop('checked');
var starttls = $('#smtpStarttls').prop('checked');
var fromAddress = $('#fromAddress' ).val();
var fromName = $('#fromName' ).val();
var testAddress = $('#testAddress' ).val();
if(host == ''){
alert('SMTP Host is required.');
$('#smtpHost').focus();
} else if(testAddress == ''){
alert('Destination is required.');
$('#testAddress').focus();
} else {
$.post('@context.path/admin/system/sendmail', {
'smtp.host': host,
'smtp.port': port,
'smtp.user': user,
'smtp.password': password,
'smtp.ssl': ssl,
'smtp.starttls': starttls,
'smtp.fromAddress': fromAddress,
'smtp.fromName': fromName,
'testAddress': testAddress
}, function(data, status){
if(data != ''){
alert(data);
}
});
}
});
$('#ssh').change(function(){
$('.ssh input').prop('disabled', !$(this).prop('checked'));
}).change();
$('#useSMTP').change(function(){
$('.useSMTP input').prop('disabled', !$(this).prop('checked'));
// With only SMTP in current version, notification cannot be enabled if no communication channel exists
$('#notification').prop('disabled', !$(this).prop('checked'));
if (!$(this).prop('checked')) {
// With only SMTP in current version, if SMTP is unchecked then we disable notification
$('#notification').prop('checked', false);
}
}).change();
});
</script>

View File

@@ -1,514 +0,0 @@
@(info: Option[Any])(implicit context: gitbucket.core.controller.Context)
@import gitbucket.core.service.OpenIDConnectService
@import gitbucket.core.util.DatabaseConfig
@gitbucket.core.html.main("System settings"){
@gitbucket.core.admin.html.menu("system"){
@gitbucket.core.helper.html.information(info)
<form action="@context.path/admin/system" method="POST" validate="true" class="form-horizontal">
<div class="panel panel-default">
<div class="panel-heading strong">System settings</div>
<div class="panel-body">
<!--====================================================================-->
<!-- System properties -->
<!--====================================================================-->
<table class="table table-bordered">
<tr>
<th>Property</th>
<th>Value</th>
</tr>
<tr>
<td>GITBUCKET_HOME</td>
<td>@gitbucket.core.util.Directory.GitBucketHome</td>
</tr>
<tr>
<td>DATABASE_URL</td>
@if(DatabaseConfig.url.startsWith("jdbc:h2:")) {
<td class="danger">
<p>@gitbucket.core.util.DatabaseConfig.url</p>
<p>
Your GitBucket is running on embedded H2 database.
Recommend to <a href="https://github.com/gitbucket/gitbucket/wiki/External-database-configuration">configure to use external database</a> if you would like to use GitBucket for important purpose.
</p>
</td>
}else{
<td>@gitbucket.core.util.DatabaseConfig.url</td>
}
</tr>
</table>
<!--====================================================================-->
<!-- Base URL -->
<!--====================================================================-->
<hr>
<label><span class="strong">Base URL</span> (e.g. <code>http://example.com/gitbucket</code>)</label>
<fieldset>
<div class="controls">
<input type="text" name="baseUrl" id="baseUrl" class="form-control" value="@context.settings.baseUrl"/>
<span id="error-baseUrl" class="error"></span>
</div>
</fieldset>
<p class="muted">
The base URL is used for redirect, notification email, git repository URL box and more.
If the base URL is empty, GitBucket generates URL from the request information.
You can use this property to adjust to URL differences between the reverse proxy and GitBucket.
</p>
<!--====================================================================-->
<!-- Information -->
<!--====================================================================-->
<hr>
<label><span class="strong">Information</span> (HTML is available)</label>
<fieldset>
<textarea name="information" class="form-control" style="height: 100px;">@context.settings.information</textarea>
</fieldset>
<!--====================================================================-->
<!-- AdminLTE SkinName -->
<!--====================================================================-->
<hr>
<label class="strong">
AdminLTE skin name
</label>
<div class="form-group">
<label class="control-label col-md-2" for="skinName">Skin name</label>
<div class="col-md-10">
<select id="skinName" name="skinName" class="form-control">
<optgroup label="Dark">
@Seq(
("skin-black", "Black"),
("skin-blue", "Blue"),
("skin-green", "Green"),
("skin-purple", "Purple"),
("skin-red", "Red"),
("skin-yellow", "Yellow"),
).map{ skin =>
<option value="@skin._1"@if(skin._1 == context.settings.skinName){ selected=""}>@skin._2</option>
}
</optgroup>
<optgroup label="Light">
@Seq(
("skin-black-light", "Light black"),
("skin-blue-light", "Light blue"),
("skin-green-light", "Light green"),
("skin-purple-light", "Light purple"),
("skin-red-light", "Light red"),
("skin-yellow-light", "Light yellow"),
).map{ skin =>
<option value="@skin._1"@if(skin._1 == context.settings.skinName){ selected=""} >@skin._2</option>
}
</optgroup>
</select>
</div>
</div>
<!--====================================================================-->
<!-- Account registration -->
<!--====================================================================-->
<hr>
<label class="strong">Account registration</label>
<fieldset>
<label class="radio">
<input type="radio" name="allowAccountRegistration" value="true"@if(context.settings.allowAccountRegistration){ checked}>
<span class="strong">Allow</span> <span class="normal">- Users can create accounts by themselves.</span>
</label>
<label class="radio">
<input type="radio" name="allowAccountRegistration" value="false"@if(!context.settings.allowAccountRegistration){ checked}>
<span class="strong">Deny</span> <span class="normal">- Only administrators can create accounts.</span>
</label>
</fieldset>
<hr>
<label class="strong">Default permissions when creating a new repository</label>
<fieldset>
<label class="radio">
<input type="radio" name="isCreateRepoOptionPublic" value="true"@if(context.settings.isCreateRepoOptionPublic){ checked}>
<span class="strong">Public</span> <span class="normal">- All users and guests can read the repository.</span>
</label>
<label class="radio">
<input type="radio" name="isCreateRepoOptionPublic" value="false"@if(!context.settings.isCreateRepoOptionPublic){ checked}>
<span class="strong">Private</span> <span class="normal">- Only collaborators can read the repository.</span>
</label>
</fieldset>
<!--====================================================================-->
<!-- Anonymous access -->
<!--====================================================================-->
<hr>
<label class="strong">Anonymous access</label>
<fieldset>
<label class="radio">
<input type="radio" name="allowAnonymousAccess" value="true"@if(context.settings.allowAnonymousAccess){ checked}>
<span class="strong">Allow</span> <span class="normal">- Anyone can view public repositories and user/group profiles.</span>
</label>
<label class="radio">
<input type="radio" name="allowAnonymousAccess" value="false"@if(!context.settings.allowAnonymousAccess){ checked}>
<span class="strong">Deny</span> <span class="normal">- Users must authenticate before viewing any information.</span>
</label>
</fieldset>
<!--====================================================================-->
<!-- Activity -->
<!--====================================================================-->
<hr>
<label><span class="strong">Limit of activity logs</span> (Unlimited if it is not specified or zero)</label>
<fieldset>
<div class="form-group">
<label class="control-label col-md-2" for="activityLogLimit">Limit</label>
<div class="col-md-10">
<input type="text" id="activityLogLimit" name="activityLogLimit" class="form-control input-mini" value="@context.settings.activityLogLimit"/>
<span id="error-activityLogLimit" class="error"></span>
</div>
</div>
</fieldset>
<!--====================================================================-->
<!-- Services -->
<!--====================================================================-->
<hr>
<label class="strong">Services</label>
<fieldset>
<label class="checkbox">
<input type="checkbox" name="gravatar"@if(context.settings.gravatar){ checked}/>
Use Gravatar for profile images
</label>
</fieldset>
<!--====================================================================-->
<!-- SSH access -->
<!--====================================================================-->
<hr>
<label class="strong">SSH access</label>
<fieldset>
<label class="checkbox">
<input type="checkbox" id="ssh" name="ssh"@if(context.settings.ssh){ checked}/>
Enable SSH access to git repository
<span class="muted normal">(Both SSH host and Base URL are required if SSH access is enabled)</span>
</label>
</fieldset>
<div class="ssh">
<div class="form-group">
<label class="control-label col-md-2" for="sshHost">SSH host</label>
<div class="col-md-10">
<input type="text" id="sshHost" name="sshHost" class="form-control" value="@context.settings.sshHost"/>
<span id="error-sshHost" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="sshPort">SSH port</label>
<div class="col-md-10">
<input type="text" id="sshPort" name="sshPort" class="form-control" value="@context.settings.sshPort"/>
<span id="error-sshPort" class="error"></span>
</div>
</div>
</div>
<!--====================================================================-->
<!-- Authentication -->
<!--====================================================================-->
<hr>
<label class="strong">Authentication</label>
<fieldset>
<label class="checkbox">
<input type="checkbox" id="ldapAuthentication" name="ldapAuthentication"@if(context.settings.ldap){ checked} />
LDAP
</label>
</fieldset>
<div class="ldap">
<div class="form-group">
<label class="control-label col-md-2" for="ldapHost">LDAP host</label>
<div class="col-md-10">
<input type="text" id="ldapHost" name="ldap.host" class="form-control" value="@context.settings.ldap.map(_.host)"/>
<span id="error-ldap_host" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapPort">LDAP port</label>
<div class="col-md-10">
<input type="text" id="ldapPort" name="ldap.port" class="form-control input-mini" value="@context.settings.ldap.map(_.port)"/>
<span id="error-ldap_port" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapBindDN">Bind DN</label>
<div class="col-md-10">
<input type="text" id="ldapBindDN" name="ldap.bindDN" class="form-control" value="@context.settings.ldap.map(_.bindDN)"/>
<span id="error-ldap_bindDN" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapBindPassword">Bind password</label>
<div class="col-md-10">
<input type="password" id="ldapBindPassword" name="ldap.bindPassword" class="form-control" value="@context.settings.ldap.map(_.bindPassword)"/>
<span id="error-ldap_bindPassword" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapBaseDN">Base DN</label>
<div class="col-md-10">
<input type="text" id="ldapBaseDN" name="ldap.baseDN" class="form-control" value="@context.settings.ldap.map(_.baseDN)"/>
<span id="error-ldap_baseDN" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapUserNameAttribute">User name attribute</label>
<div class="col-md-10">
<input type="text" id="ldapUserNameAttribute" name="ldap.userNameAttribute" class="form-control" value="@context.settings.ldap.map(_.userNameAttribute)"/>
<span id="error-ldap_userNameAttribute" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapAdditionalFilterCondition">Additional filter condition</label>
<div class="col-md-10">
<input type="text" id="ldapAdditionalFilterCondition" name="ldap.additionalFilterCondition" class="form-control" value="@context.settings.ldap.map(_.additionalFilterCondition)"/>
<span id="error-ldap_additionalFilterCondition" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapFullNameAttribute">Full name attribute</label>
<div class="col-md-10">
<input type="text" id="ldapFullNameAttribute" name="ldap.fullNameAttribute" class="form-control" value="@context.settings.ldap.map(_.fullNameAttribute)"/>
<span id="error-ldap_fullNameAttribute" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapMailAttribute">Mail address attribute</label>
<div class="col-md-10">
<input type="text" id="ldapMailAttribute" name="ldap.mailAttribute" class="form-control" value="@context.settings.ldap.map(_.mailAttribute)"/>
<span id="error-ldap_mailAttribute" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2">Enable TLS</label>
<div class="col-md-10">
<input type="checkbox" name="ldap.tls"@if(context.settings.ldap.flatMap(_.tls).getOrElse(false)){ checked}/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2">Enable SSL</label>
<div class="col-md-10">
<input type="checkbox" name="ldap.ssl"@if(context.settings.ldap.flatMap(_.ssl).getOrElse(false)){ checked}/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="ldapBindDN">Keystore</label>
<div class="col-md-10">
<input type="text" id="ldapKeystore" name="ldap.keystore" class="form-control" value="@context.settings.ldap.map(_.keystore)"/>
<span id="error-ldap_keystore" class="error"></span>
</div>
</div>
</div>
<fieldset>
<label class="checkbox">
<input type="checkbox" id="oidcAuthentication" name="oidcAuthentication"@if(context.settings.oidc){ checked} />
OpenID Connect
</label>
</fieldset>
<div class="oidc">
<div class="form-group">
<label class="control-label col-md-2" for="oidcIssuer">Issuer</label>
<div class="col-md-10">
<input type="text" id="oidcIssuer" name="oidc.issuer" class="form-control" value="@context.settings.oidc.map(_.issuer.getValue)"/>
<span id="error-oidc_issuer" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="oidcClientID">Client ID</label>
<div class="col-md-10">
<input type="text" id="oidcClientID" name="oidc.clientID" class="form-control" value="@context.settings.oidc.map(_.clientID.getValue)"/>
<span id="error-oidc_clientID" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="oidcClientID">Client secret</label>
<div class="col-md-10">
<input type="password" id="oidcClientSecret" name="oidc.clientSecret" class="form-control" value="@context.settings.oidc.map(_.clientSecret.getValue)"/>
<span id="error-oidc_clientSecret" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="oidcJwsAlgorithm">Expected signature</label>
<div class="col-md-10">
<select id="oidcJwsAlgorithm" name="oidc.jwsAlgorithm" class="form-control">
<option value="" @if(context.settings.oidc.flatMap(_.jwsAlgorithm) == None){selected}>
No signature
</option>
@OpenIDConnectService.JWS_ALGORITHMS.map { case (family, algorithms) =>
<optgroup label="@family">
@algorithms.map { algorithm =>
<option value="@algorithm.getName" @if(context.settings.oidc.flatMap(_.jwsAlgorithm) == Some(algorithm)){selected}>
@algorithm.getName
</option>
}
</optgroup>
}
</select>
<span class="muted">Choose the expected signature algorithm of the token response. Most IdP provides RS256 or HS256.</span>
<span id="error-oidc_jwsAlgorithm" class="error"></span>
</div>
</div>
</div>
<!--====================================================================-->
<!-- Notification email -->
<!--====================================================================-->
<hr>
<label class="strong">Notifications</label>
<fieldset>
<label class="checkbox">
<input type="checkbox" id="notification" name="notification"@if(context.settings.notification){ checked}/>
Send notifications
</label>
</fieldset>
<!--====================================================================-->
<!-- Communication email -->
<!--====================================================================-->
<hr>
<label class="strong">Communication</label>
<fieldset>
<label class="checkbox">
<input type="checkbox" id="useSMTP" name="useSMTP" @if(context.settings.useSMTP){ checked}/>
SMTP
<span class="muted normal">(Enable notification as well as SMTP configuration if you want to send notification email too)</span>
</label>
</fieldset>
<div class="useSMTP">
<div class="form-group">
<label class="control-label col-md-2" for="smtpHost">SMTP host</label>
<div class="col-md-10">
<input type="text" id="smtpHost" name="smtp.host" class="form-control" value="@context.settings.smtp.map(_.host)"/>
<span id="error-smtp_host" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpPort">SMTP port</label>
<div class="col-md-10">
<input type="text" id="smtpPort" name="smtp.port" class="form-control input-mini" value="@context.settings.smtp.map(_.port)"/>
<span id="error-smtp_port" class="error"></span>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpUser">SMTP user</label>
<div class="col-md-10">
<input type="text" id="smtpUser" name="smtp.user" class="form-control" value="@context.settings.smtp.map(_.user)"/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpPassword">SMTP password</label>
<div class="col-md-10">
<input type="password" id="smtpPassword" name="smtp.password" class="form-control" value="@context.settings.smtp.map(_.password)"/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpSsl">Enable SSL</label>
<div class="col-md-10">
<input type="checkbox" id="smtpSsl" name="smtp.ssl"@if(context.settings.smtp.flatMap(_.ssl).getOrElse(false)){ checked}/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="smtpStarttls">Enable STARTTLS</label>
<div class="col-md-10">
<input type="checkbox" id="smtpStarttls" name="smtp.starttls"@if(context.settings.smtp.flatMap(_.starttls).getOrElse(false)){ checked}/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="fromAddress">FROM address</label>
<div class="col-md-10">
<input type="text" id="fromAddress" name="smtp.fromAddress" class="form-control" value="@context.settings.smtp.map(_.fromAddress)"/>
</div>
</div>
<div class="form-group">
<label class="control-label col-md-2" for="fromName">FROM name</label>
<div class="col-md-10">
<input type="text" id="fromName" name="smtp.fromName" class="form-control" value="@context.settings.smtp.map(_.fromName)"/>
</div>
</div>
<div class="text-right">
Send test mail to:
<input type="text" id="testAddress" size="30"/>
<input type="button" id="sendTestMail" value="Send"/>
</div>
</div>
@*
<!--====================================================================-->
<!-- GitLFS -->
<!--====================================================================-->
<hr>
<label class="strong">
GitLFS <span class="muted normal">(Enter the LFS server url to enable GitLFS support)</span>
</label>
<div class="form-group">
<label class="control-label col-md-2" for="smtpHost">LFS server url</label>
<div class="col-md-10">
<input type="text" id="lfsServerUrl" name="lfs.serverUrl" class="form-control" value="@context.settings.lfs.serverUrl"/>
<span id="error-lfs_serverUrl" class="error"></span>
</div>
</div>
*@
</div>
</div>
<div class="align-right" style="margin-top: 20px;">
<input type="submit" class="btn btn-success" value="Apply changes"/>
</div>
</form>
}
}
<script>
$(function(){
$('#skinName').change(function(evt) {
var that = $(evt.target);
var themeCss = $('link[rel="stylesheet"][href*="skin-"]');
var oldVal = new RegExp('(skin-.*?).min.css').exec(themeCss.attr('href'))[1];
themeCss.attr('href', themeCss.attr('href').replace(oldVal, that.val()));
$(document.body).removeClass(oldVal).addClass(that.val());
});
$('#sendTestMail').click(function(){
var host = $('#smtpHost' ).val();
var port = $('#smtpPort' ).val();
var user = $('#smtpUser' ).val();
var password = $('#smtpPassword').val();
var ssl = $('#smtpSsl' ).prop('checked');
var starttls = $('#smtpStarttls').prop('checked');
var fromAddress = $('#fromAddress' ).val();
var fromName = $('#fromName' ).val();
var testAddress = $('#testAddress' ).val();
if(host == ''){
alert('SMTP Host is required.');
$('#smtpHost').focus();
} else if(testAddress == ''){
alert('Destination is required.');
$('#testAddress').focus();
} else {
$.post('@context.path/admin/system/sendmail', {
'smtp.host': host,
'smtp.port': port,
'smtp.user': user,
'smtp.password': password,
'smtp.ssl': ssl,
'smtp.starttls': starttls,
'smtp.fromAddress': fromAddress,
'smtp.fromName': fromName,
'testAddress': testAddress
}, function(data, status){
if(data != ''){
alert(data);
}
});
}
});
$('#ssh').change(function(){
$('.ssh input').prop('disabled', !$(this).prop('checked'));
}).change();
$('#useSMTP').change(function(){
$('.useSMTP input').prop('disabled', !$(this).prop('checked'));
// With only SMTP in current version, notification cannot be enabled if no communication channel exists
$('#notification').prop('disabled', !$(this).prop('checked'));
if (!$(this).prop('checked')) {
// With only SMTP in current version, if SMTP is unchecked then we disable notification
$('#notification').prop('checked', false);
}
}).change();
$('#ldapAuthentication').change(function(){
$('.ldap input').prop('disabled', !$(this).prop('checked'));
}).change();
$('#oidcAuthentication').change(function(){
$('.oidc input, .oidc select').prop('disabled', !$(this).prop('checked'));
}).change();
});
</script>