KEYCLOAK-115 add social provider config page
This commit is contained in:
parent
fd6bde829c
commit
508a9a1e6b
9 changed files with 251 additions and 28 deletions
|
@ -41,7 +41,7 @@ module.config([ '$routeProvider', function($routeProvider) {
|
|||
return RealmLoader();
|
||||
}
|
||||
},
|
||||
controller : 'RealmTokenDetailCtrl'
|
||||
controller : 'RealmSocialCtrl'
|
||||
})
|
||||
.when('/realms/:realm/required-credentials', {
|
||||
templateUrl : 'partials/realm-credentials.html',
|
||||
|
|
|
@ -196,6 +196,123 @@ module.controller('RealmRequiredCredentialsCtrl', function($scope, Realm, realm,
|
|||
};
|
||||
});
|
||||
|
||||
module.controller('RealmSocialCtrl', function($scope, realm, Realm, $location, Notifications) {
|
||||
console.log('RealmSocialCtrl');
|
||||
|
||||
$scope.realm = { id : realm.id, realm : realm.realm, social : realm.social, tokenLifespan : realm.tokenLifespan, accessCodeLifespan : realm.accessCodeLifespan };
|
||||
|
||||
if (!realm["socialProviders"]){
|
||||
$scope.realm["socialProviders"] = {};
|
||||
} else {
|
||||
$scope.realm["socialProviders"] = realm.socialProviders;
|
||||
}
|
||||
|
||||
// Hardcoded provider list
|
||||
$scope.availableProviders = [ "google", "facebook", "twitter"];
|
||||
|
||||
var oldCopy = angular.copy($scope.realm);
|
||||
$scope.changed = false;
|
||||
$scope.callbackUrl = "http://mock.url.org/don/t/know/what/to/place/here";
|
||||
|
||||
// To get rid of the "undefined" option in the provider select list
|
||||
// Setting the 1st option from the list (if the list is not empty)
|
||||
var selectFirstProvider = function(){
|
||||
if ($scope.unsetProviders.length > 0){
|
||||
$scope.newProviderId = $scope.unsetProviders[0];
|
||||
} else {
|
||||
$scope.newProviderId = null;
|
||||
}
|
||||
}
|
||||
|
||||
// Fill in configured providers
|
||||
var initSocial = function() {
|
||||
$scope.unsetProviders = [];
|
||||
$scope.configuredProviders = [];
|
||||
|
||||
for (var providerConfig in $scope.realm.socialProviders){
|
||||
// Get the provider ID which is before the '.' (i.e. google in google.key or google.secret)
|
||||
if ($scope.realm.socialProviders.hasOwnProperty(providerConfig)){
|
||||
var pId = providerConfig.split('.')[0];
|
||||
if ($scope.configuredProviders.indexOf(pId) < 0){
|
||||
$scope.configuredProviders.push(pId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// If no providers are already configured, you can add any of them
|
||||
if ($scope.configuredProviders.length == 0){
|
||||
$scope.unsetProviders = $scope.availableProviders;
|
||||
} else {
|
||||
for (var i = 0; i < $scope.availableProviders.length; i++){
|
||||
var providerId = $scope.availableProviders[i];
|
||||
if ($scope.configuredProviders.indexOf(providerId) < 0){
|
||||
$scope.unsetProviders.push(providerId);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
selectFirstProvider();
|
||||
};
|
||||
|
||||
initSocial();
|
||||
|
||||
$scope.addProvider = function() {
|
||||
if ($scope.availableProviders.indexOf($scope.newProviderId) > -1){
|
||||
$scope.realm.socialProviders[$scope.newProviderId+".key"]="";
|
||||
$scope.realm.socialProviders[$scope.newProviderId+".secret"]="";
|
||||
$scope.configuredProviders.push($scope.newProviderId);
|
||||
$scope.unsetProviders.remove($scope.unsetProviders.indexOf($scope.newProviderId));
|
||||
selectFirstProvider();
|
||||
}
|
||||
};
|
||||
|
||||
$scope.removeProvider = function(pId) {
|
||||
delete $scope.realm.socialProviders[pId+".key"];
|
||||
delete $scope.realm.socialProviders[pId+".secret"];
|
||||
$scope.configuredProviders.remove($scope.configuredProviders.indexOf(pId));
|
||||
$scope.unsetProviders.push(pId);
|
||||
};
|
||||
|
||||
$scope.$watch('realm', function() {
|
||||
if (!angular.equals($scope.realm, oldCopy)) {
|
||||
$scope.changed = true;
|
||||
}
|
||||
}, true);
|
||||
|
||||
$scope.save = function() {
|
||||
$scope.saveClicked = true;
|
||||
|
||||
if ($scope.realmForm.$valid) {
|
||||
var realmCopy = angular.copy($scope.realm);
|
||||
realmCopy.social = true;
|
||||
$scope.changed = false;
|
||||
Realm.update(realmCopy, function () {
|
||||
$location.url("/realms/" + realm.id + "/social-settings");
|
||||
Notifications.success("Saved changes to realm");
|
||||
});
|
||||
} else {
|
||||
$scope.realmForm.showErrors = true;
|
||||
Notifications.error("Some required fields are missing values.");
|
||||
}
|
||||
};
|
||||
|
||||
$scope.reset = function() {
|
||||
$scope.realm = angular.copy(oldCopy);
|
||||
$scope.changed = false;
|
||||
// Initialize lists of configured and unset providers again
|
||||
initSocial();
|
||||
};
|
||||
|
||||
$scope.openHelp = function(pId) {
|
||||
$scope.helpPId = pId;
|
||||
$scope.providerHelpModal = true;
|
||||
};
|
||||
|
||||
$scope.closeHelp = function() {
|
||||
$scope.providerHelpModal = false;
|
||||
};
|
||||
|
||||
});
|
||||
|
||||
module.controller('RealmTokenDetailCtrl', function($scope, Realm, realm, $http, $location, Dialog, Notifications) {
|
||||
console.log('RealmTokenDetailCtrl');
|
||||
|
|
|
@ -0,0 +1,28 @@
|
|||
<p>
|
||||
Mock page for <i>Facebook provider help</i>.
|
||||
</p>
|
||||
|
||||
<p>Fill in name, description and website. For <i>Callback URL</i> use the following value:</p>
|
||||
|
||||
<ul>
|
||||
<li><b>Callback URL:</b> {{callbackUrl}}</li>
|
||||
</ul>
|
||||
|
||||
<form class="form-horizontal" name="fbHelpForm">
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="providerHelp.key">Consumer key </label>
|
||||
<div class="controls">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.key" ng-model="realm.socialProviders[helpPId+'.key']">
|
||||
</div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="providerHelp.secret">Consumer secret </label>
|
||||
<div class="controls">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.secret" ng-model="realm.socialProviders[helpPId+'.secret']">
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<p>
|
||||
Close the help panel and click <i>save changes</i>.
|
||||
</p>
|
|
@ -21,18 +21,14 @@
|
|||
<form class="form-horizontal" name="googleHelpForm">
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="providerHelp.key">Client ID </label>
|
||||
|
||||
<div class="controls">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.key"
|
||||
data-ng-model="application.providers[providerHelp.index].key">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.key" ng-model="realm.socialProviders[helpPId+'.key']">
|
||||
</div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="providerHelp.secret">Client secret </label>
|
||||
|
||||
<div class="controls">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.secret"
|
||||
data-ng-model="application.providers[providerHelp.index].secret">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.secret" ng-model="realm.socialProviders[helpPId+'.secret']">
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
|
|
16
admin-ui/src/main/resources/META-INF/resources/admin/partials/provider/twitter-help.html
Executable file → Normal file
16
admin-ui/src/main/resources/META-INF/resources/admin/partials/provider/twitter-help.html
Executable file → Normal file
|
@ -1,6 +1,5 @@
|
|||
<p>
|
||||
Open <a href="https://dev.twitter.com/apps" target="_blank">https://dev.twitter.com/apps</a>. Click on <i>Create a
|
||||
new
|
||||
Open <a href="https://dev.twitter.com/apps" target="_blank">https://dev.twitter.com/apps</a>. Click on <i>Create a new
|
||||
application</i>.
|
||||
</p>
|
||||
|
||||
|
@ -16,28 +15,23 @@
|
|||
|
||||
<p>Insert <i>Consumer key</i> and <i>Consumer secret</i> in the form below.</p>
|
||||
|
||||
<form class="form-horizontal" name="googleHelpForm">
|
||||
<form class="form-horizontal" name="twitterHelpForm">
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="providerHelp.key">Consumer key </label>
|
||||
|
||||
<div class="controls">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.key"
|
||||
data-ng-model="application.providers[providerHelp.index].key">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.key" ng-model="realm.socialProviders[helpPId+'.key']">
|
||||
</div>
|
||||
</div>
|
||||
<div class="control-group">
|
||||
<label class="control-label" for="providerHelp.secret">Consumer secret </label>
|
||||
|
||||
<div class="controls">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.secret"
|
||||
data-ng-model="application.providers[providerHelp.index].secret">
|
||||
<input type="text" class="input-xlarge" id="providerHelp.secret" ng-model="realm.socialProviders[helpPId+'.secret']">
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<p>
|
||||
Now click on <i>Settings</i> and tick the box <i>Allow this application to be used to Sign in with Twitter</i>, and
|
||||
click on <i>Update
|
||||
Now click on <i>Settings</i> and tick the box <i>Allow this application to be used to Sign in with Twitter</i>, and click on <i>Update
|
||||
this Twitter application's settings</i>.
|
||||
</p>
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
<div id="wrapper" class="container">
|
||||
<div id="wrapper" class="container social-provider">
|
||||
<div class="row">
|
||||
<div class="bs-sidebar col-md-3 clearfix" data-ng-include data-src="'partials/realm-menu.html'"></div>
|
||||
<div id="content-area" class="col-md-9" role="main">
|
||||
|
@ -12,11 +12,61 @@
|
|||
</ul>
|
||||
</div>
|
||||
<div id="content">
|
||||
<h2 class="pull-left"><span>{{realm.realm}}</span> Social Providers</h2>
|
||||
<p class="subtitle"></p>
|
||||
<ol class="breadcrumb">
|
||||
<li><a href="#/realms/{{realm.id}}">{{realm.realm}}</a></li>
|
||||
<li><a href="#/realms/{{realm.id}}">Settings</a></li>
|
||||
<li class="active">Social</li>
|
||||
</ol>
|
||||
<h2><span>{{realm.realm}}</span> Social Providers Settings</h2>
|
||||
<form name="realmForm" novalidate>
|
||||
<fieldset>
|
||||
<legend uncollapsed><span class="text">Social Settings</span></legend>
|
||||
<div>
|
||||
<table>
|
||||
<caption class="hidden">Table of social providers</caption>
|
||||
<thead>
|
||||
<tr>
|
||||
<th colspan="5" class="rcue-table-actions">
|
||||
<div class="actions">
|
||||
<div class="select-rcue">
|
||||
<select ng-model="newProviderId"
|
||||
ng-options="p for p in unsetProviders"></select>
|
||||
</div>
|
||||
<div>
|
||||
<button ng-click="addProvider()" ng-disabled="">Add Provider</button>
|
||||
</div>
|
||||
</div>
|
||||
</th>
|
||||
</tr>
|
||||
<tr ng-show="configuredProviders.length > 0">
|
||||
<th>Provider</th>
|
||||
<th>Key <span class="required">*</span></th>
|
||||
<th>Secret <span class="required">*</span></th>
|
||||
<th colspan="1">Actions</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody ng-show="configuredProviders.length > 0">
|
||||
<tr ng-repeat="pId in configuredProviders">
|
||||
<td>
|
||||
<div class="clearfix">
|
||||
<input class="input-small disabled" type="text" placeholder="Key" value="{{pId}}" readonly>
|
||||
</div>
|
||||
</td>
|
||||
<td>
|
||||
<input class="input-small" type="text" placeholder="Key" ng-model="realm.socialProviders[pId+'.key']"
|
||||
ng-class="{'dirty': saveClicked}" required>
|
||||
</td>
|
||||
<td>
|
||||
<input class="input-small" type="text" placeholder="Secret" ng-model="realm.socialProviders[pId+'.secret']"
|
||||
ng-class="{'dirty': saveClicked}" required>
|
||||
</td>
|
||||
<td>
|
||||
<div class="action-div"><i class="icon-question" ng-click="openHelp(pId)"></i></div>
|
||||
<div class="action-div"><i class="icon-remove" ng-click="removeProvider(pId)"></i></div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</fieldset>
|
||||
<div class="form-actions">
|
||||
<button type="submit" data-ng-click="save()" class="primary" data-ng-show="changed">Save
|
||||
|
@ -31,3 +81,41 @@
|
|||
<div id="container-right-bg"></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div modal="providerHelpModal" close="closeHelp()" options="opts">
|
||||
<div class="modal-dialog">
|
||||
<div class="modal-content">
|
||||
<div class="modal-header">
|
||||
<h3>Configure {{helpPId}}</h3>
|
||||
</div>
|
||||
<div class="modal-body">
|
||||
<div ng-include src="'partials/provider/'+ helpPId +'-help.html'"></div>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button class="btn" ng-click="closeHelp()">Close</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- TODO remove once this page is properly styled -->
|
||||
<style type="text/css">
|
||||
.social-provider input.ng-invalid.dirty,
|
||||
.social-provider input.ng-invalid.ng-dirty {
|
||||
background-color: #FFEEEE;
|
||||
}
|
||||
|
||||
.social-provider .actions > div {
|
||||
display: inline-block;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.social-provider td {
|
||||
font-size: 10px;
|
||||
}
|
||||
|
||||
.social-provider .action-div {
|
||||
display: inline-block;
|
||||
margin: 5px;
|
||||
}
|
||||
</style>
|
|
@ -5,7 +5,7 @@
|
|||
<div class="top-nav">
|
||||
<ul class="rcue-tabs">
|
||||
<li><a href="#/realms/{{realm.id}}">General</a></li>
|
||||
<li data-ng-show="realm.social"><a href="#">Social</a></li>
|
||||
<li data-ng-show="realm.social"><a href="#/realms/{{realm.id}}/social-settings">Social</a></li>
|
||||
<li class="active"><a href="#/realms/{{realm.id}}/roles">Roles</a></li>
|
||||
<li><a href="#/realms/{{realm.id}}/required-credentials">Credentials</a></li>
|
||||
<li><a href="#/realms/{{realm.id}}/token-settings">Token</a></li>
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
<div class="top-nav">
|
||||
<ul class="rcue-tabs">
|
||||
<li><a href="#/realms/{{realm.id}}">General</a></li>
|
||||
<li data-ng-show="realm.social"><a href="#">Social</a></li>
|
||||
<li data-ng-show="realm.social"><a href="#/realms/{{realm.id}}/social-settings">Social</a></li>
|
||||
<li class="active"><a href="#/realms/{{realm.id}}/roles">Roles</a></li>
|
||||
<li><a href="#/realms/{{realm.id}}/required-credentials">Credentials</a></li>
|
||||
<li><a href="#/realms/{{realm.id}}/token-settings">Token</a></li>
|
||||
|
|
|
@ -253,7 +253,7 @@ public class RealmManager {
|
|||
}
|
||||
}
|
||||
|
||||
if (rep.getAccountManagement() != null && rep.getAccountManagement()) {
|
||||
if (rep.isAccountManagement() != null && rep.isAccountManagement()) {
|
||||
enableAccountManagement(newRealm);
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue