* Modifying the way roles are assigned.

* Adding migration scripts.

* Adding endpoints field for future use.

* Fixing dropdowns.
This commit is contained in:
kevgliss 2016-05-23 18:38:04 -07:00
parent 656269ff17
commit 1ca38015bc
13 changed files with 63 additions and 94 deletions

View File

@ -39,7 +39,7 @@
"angular-ui-switch": "~0.1.0", "angular-ui-switch": "~0.1.0",
"angular-sanitize": "^1.5.0", "angular-sanitize": "^1.5.0",
"angular-file-saver": "~1.0.1", "angular-file-saver": "~1.0.1",
"angular-selectize2": "^3.0.1" "angular-ui-select": "~0.17.1"
}, },
"resolutions": { "resolutions": {
"moment": ">=2.8.0 <2.11.0", "moment": ">=2.8.0 <2.11.0",

View File

@ -81,7 +81,7 @@ gulp.task('dev:styles', function () {
'bower_components/angular-wizard/dist/angular-wizard.css', 'bower_components/angular-wizard/dist/angular-wizard.css',
'bower_components/ng-table/ng-table.css', 'bower_components/ng-table/ng-table.css',
'bower_components/angularjs-toaster/toaster.css', 'bower_components/angularjs-toaster/toaster.css',
'bower_components/selectize/dist/css/selectize.bootstrap3.css', 'bower_components/angular-ui-select/dist/select.css',
'lemur/static/app/styles/lemur.css' 'lemur/static/app/styles/lemur.css'
]; ];

View File

@ -38,7 +38,7 @@ class AuthorityInputSchema(LemurInputSchema):
# signing related options # signing related options
type = fields.String(validate=validate.OneOf(['root', 'subca']), missing='root') type = fields.String(validate=validate.OneOf(['root', 'subca']), missing='root')
authority = fields.Nested(AssociatedAuthoritySchema) parent = fields.Nested(AssociatedAuthoritySchema)
signing_algorithm = fields.String(validate=validate.OneOf(['sha256WithRSA', 'sha1WithRSA']), missing='sha256WithRSA') signing_algorithm = fields.String(validate=validate.OneOf(['sha256WithRSA', 'sha1WithRSA']), missing='sha256WithRSA')
key_type = fields.String(validate=validate.OneOf(['RSA2048', 'RSA4096']), missing='RSA2048') key_type = fields.String(validate=validate.OneOf(['RSA2048', 'RSA4096']), missing='RSA2048')
key_name = fields.String() key_name = fields.String()

View File

@ -48,7 +48,7 @@ def mint(**kwargs):
return body, chain, roles return body, chain, roles
def create_authority_roles(roles, **kwargs): def create_authority_roles(**kwargs):
""" """
Creates all of the necessary authority roles. Creates all of the necessary authority roles.
:param roles: :param roles:
@ -56,7 +56,7 @@ def create_authority_roles(roles, **kwargs):
:return: :return:
""" """
role_objs = [] role_objs = []
for r in roles: for r in kwargs['roles']:
role = role_service.create( role = role_service.create(
r['name'], r['name'],
password=r['password'], password=r['password'],
@ -91,7 +91,12 @@ def create(**kwargs):
kwargs['body'] = body kwargs['body'] = body
kwargs['chain'] = chain kwargs['chain'] = chain
kwargs['roles'] = create_authority_roles(roles, **kwargs) if kwargs.get('roles'):
kwargs['roles'] += roles
else:
kwargs['roles'] = roles
kwargs['roles'] = create_authority_roles(**kwargs)
if kwargs['type'] == 'subca': if kwargs['type'] == 'subca':
description = "This is the ROOT certificate for the {0} sub certificate authority the parent \ description = "This is the ROOT certificate for the {0} sub certificate authority the parent \

View File

@ -120,6 +120,7 @@ class CertificateOutputSchema(LemurOutputSchema):
replaces = fields.Nested(CertificateNestedOutputSchema, many=True) replaces = fields.Nested(CertificateNestedOutputSchema, many=True)
authority = fields.Nested(AuthorityNestedOutputSchema) authority = fields.Nested(AuthorityNestedOutputSchema)
roles = fields.Nested(RoleNestedOutputSchema, many=True) roles = fields.Nested(RoleNestedOutputSchema, many=True)
endpoints = fields.List(fields.Dict(), missing=[])
class CertificateUploadInputSchema(CertificateSchema): class CertificateUploadInputSchema(CertificateSchema):

View File

@ -12,8 +12,10 @@ down_revision = '412b22cb656a'
from alembic import op from alembic import op
import sqlalchemy as sa import sqlalchemy as sa
from sqlalchemy.sql import text
from sqlalchemy.dialects import postgresql from sqlalchemy.dialects import postgresql
def upgrade(): def upgrade():
### commands auto generated by Alembic - please adjust! ### ### commands auto generated by Alembic - please adjust! ###
op.alter_column('authorities', 'owner', op.alter_column('authorities', 'owner',
@ -35,6 +37,18 @@ def upgrade():
op.create_foreign_key(None, 'certificates', 'authorities', ['root_authority_id'], ['id'], ondelete='CASCADE') op.create_foreign_key(None, 'certificates', 'authorities', ['root_authority_id'], ['id'], ondelete='CASCADE')
### end Alembic commands ### ### end Alembic commands ###
# link existing certificate to their authority certificates
conn = op.get_bind()
for id, body in conn.execute(text('select id, body from authorities')):
# look up certificate by body, if duplications are found, pick one
stmt = text('select id from certificates where body=:body')
stmt = stmt.bindparams(body=body)
root_certificate = conn.execute(stmt).fetchone()
if root_certificate:
stmt = text('update certificates set root_authority_id=:root_authority_id where id=:id')
stmt = stmt.bindparams(root_authority_id=id, id=root_certificate[0])
op.execute(stmt)
def downgrade(): def downgrade():
### commands auto generated by Alembic - please adjust! ### ### commands auto generated by Alembic - please adjust! ###

View File

@ -15,8 +15,6 @@ import sqlalchemy as sa
from sqlalchemy.sql import text from sqlalchemy.sql import text
def upgrade(): def upgrade():
### commands auto generated by Alembic - please adjust! ### ### commands auto generated by Alembic - please adjust! ###
op.create_table('roles_authorities', op.create_table('roles_authorities',

View File

@ -19,7 +19,7 @@
'angular-clipboard', 'angular-clipboard',
'ngFileSaver', 'ngFileSaver',
'ngSanitize', 'ngSanitize',
'selectize' 'ui.select'
]); ]);

View File

@ -36,49 +36,14 @@ angular.module('lemur')
.controller('AuthorityCreateController', function ($scope, $uibModalInstance, AuthorityService, AuthorityApi, LemurRestangular, RoleService, PluginService, WizardHandler, toaster) { .controller('AuthorityCreateController', function ($scope, $uibModalInstance, AuthorityService, AuthorityApi, LemurRestangular, RoleService, PluginService, WizardHandler, toaster) {
$scope.authority = LemurRestangular.restangularizeElement(null, {}, 'authorities'); $scope.authority = LemurRestangular.restangularizeElement(null, {}, 'authorities');
$scope.authorities = [];
AuthorityApi.getList().then(function (authorities) {
angular.extend($scope.authorities, authorities);
});
$scope.authorityConfig = {
valueField: 'id',
labelField: 'name',
placeholder: 'Select Authority',
maxItems: 1,
onChange: function (value) {
angular.forEach($scope.authorities, function (authority) {
if (authority.id === parseInt(value)) {
$scope.authority.authority = authority;
}
});
},
render: {
option: function(item) {
return '<div><dl>' +
'<dt>' +
'<span>' + item.name + ' <small>' + item.owner + '</small></span>' +
'</dt>' +
'<dd>' +
'<span>' + item.description + '</span>' +
'</dd>' +
'</dl></div>';
}
},
load: function (value) {
AuthorityService.findAuthorityByName(value).then(function (authorities) {
$scope.authorities = authorities;
});
}
};
// set the defaults // set the defaults
AuthorityService.getDefaults($scope.authority); AuthorityService.getDefaults($scope.authority);
AuthorityApi.getList().then(function (authorities) { $scope.getAuthoritiesByName = function (value) {
$scope.authorities = authorities; return AuthorityService.findAuthorityByName(value).then(function (authorities) {
}); $scope.authorities = authorities;
});
};
$scope.cancel = function () { $scope.cancel = function () {
$uibModalInstance.dismiss('cancel'); $uibModalInstance.dismiss('cancel');

View File

@ -65,8 +65,17 @@
Parent Authority Parent Authority
</label> </label>
<div class="col-sm-10"> <div class="col-sm-10">
<selectize placeholder="Select an Authority..." options='authorities' config="authorityConfig" <ui-select class="input-md" ng-model="authority.parent" theme="bootstrap" title="choose an authority">
ng-model="authority.parent" ng-disabled='disable' required='true'></selectize> <ui-select-match placeholder="select an authority...">{{$select.selected.name}}</ui-select-match>
<ui-select-choices class="form-control" repeat="authority in authorities"
refresh="getAuthoritiesByName($select.search)"
refresh-delay="300">
<div ng-bind-html="authority.name | highlight: $select.search"></div>
<small>
<span ng-bind-html="''+authority.description | highlight: $select.search"></span>
</small>
</ui-select-choices>
</ui-select>
</div> </div>
</div> </div>
<div class="form-group" <div class="form-group"
@ -93,8 +102,8 @@
is-open="popup1.opened" is-open="popup1.opened"
datepicker-options="dateOptions" datepicker-options="dateOptions"
close-text="Close" close-text="Close"
max-date="authority.authority.authorityCertificate.notAfter" max-date="authority.parent.authorityCertificate.notAfter"
min-date="authority.authority.authorityCertificate.notBefore" min-date="authority.parent.authorityCertificate.notBefore"
alt-input-formats="altInputFormats" /> alt-input-formats="altInputFormats" />
<span class="input-group-btn"> <span class="input-group-btn">
<button type="button" class="btn btn-default" ng-click="open1()"><i class="glyphicon glyphicon-calendar"></i></button> <button type="button" class="btn btn-default" ng-click="open1()"><i class="glyphicon glyphicon-calendar"></i></button>
@ -111,8 +120,8 @@
is-open="popup2.opened" is-open="popup2.opened"
datepicker-options="dateOptions" datepicker-options="dateOptions"
close-text="Close" close-text="Close"
max-date="authority.authority.notAfter" max-date="authority.parent.authorityCertificate.notAfter"
min-date="authority.authority.notBefore" min-date="authority.parent.authorityCertificate.notBefore"
alt-input-formats="altInputFormats" /> alt-input-formats="altInputFormats" />
<span class="input-group-btn"> <span class="input-group-btn">
<button type="button" class="btn btn-default" ng-click="open2()"><i class="glyphicon glyphicon-calendar"></i></button> <button type="button" class="btn btn-default" ng-click="open2()"><i class="glyphicon glyphicon-calendar"></i></button>

View File

@ -94,43 +94,12 @@ angular.module('lemur')
$uibModalInstance.dismiss('cancel'); $uibModalInstance.dismiss('cancel');
}; };
$scope.authorities = []; $scope.getAuthoritiesByName = function (value) {
AuthorityApi.getList().then(function (authorities) { return AuthorityService.findAuthorityByName(value).then(function (authorities) {
angular.extend($scope.authorities, authorities); $scope.authorities = authorities;
}); });
$scope.authorityConfig = {
valueField: 'id',
labelField: 'name',
highlight: true,
placeholder: 'Select Authority',
maxItems: 1,
onChange: function (value) {
angular.forEach($scope.authorities, function (authority) {
if (authority.id === parseInt(value)) {
$scope.certificate.authority = authority;
}
});
},
render: {
option: function(item) {
return '<div><dl>' +
'<dt>' +
'<span>' + item.name + ' <small>' + item.owner + '</small></span>' +
'</dt>' +
'<dd>' +
'<span>' + item.description + '</span>' +
'</dd>' +
'</dl></div>';
}
},
load: function (value) {
AuthorityService.findAuthorityByName(value).then(function (authorities) {
$scope.authorities = authorities;
});
}
}; };
$scope.dateOptions = { $scope.dateOptions = {
formatYear: 'yy', formatYear: 'yy',
maxDate: new Date(2020, 5, 22), maxDate: new Date(2020, 5, 22),

View File

@ -46,8 +46,17 @@
Certificate Authority Certificate Authority
</label> </label>
<div class="col-sm-10"> <div class="col-sm-10">
<selectize name="selectedAuthority" placeholder="Select an Authority..." options="authorities" config="authorityConfig" <ui-select class="input-md" ng-model="certificate.authority" theme="bootstrap" title="choose an authority">
ng-model="certificate.selectedAuthority" required="true"></selectize> <ui-select-match placeholder="select an authority...">{{$select.selected.name}}</ui-select-match>
<ui-select-choices class="form-control" repeat="authority in authorities"
refresh="getauthoritiesbyname($select.search)"
refresh-delay="300">
<div ng-bind-html="authority.name | highlight: $select.search"></div>
<small>
<span ng-bind-html="''+authority.description | highlight: $select.search"></span>
</small>
</ui-select-choices>
</ui-select>
</div> </div>
</div> </div>
<div class="form-group"> <div class="form-group">

View File

@ -30,7 +30,6 @@
<!-- inject:ngviews --> <!-- inject:ngviews -->
<!-- endinject --> <!-- endinject -->
<!-- endbuild --> <!-- endbuild -->
</head> </head>
<body ng-csp> <body ng-csp>
<toaster-container></toaster-container> <toaster-container></toaster-container>