Skip to content
Snippets Groups Projects
Verified Commit 03562691 authored by nd's avatar nd
Browse files

adding groups to roles works now

parent 6181b58c
No related branches found
No related tags found
No related merge requests found
...@@ -216,7 +216,7 @@ contextmanager-decorators=contextlib.contextmanager ...@@ -216,7 +216,7 @@ contextmanager-decorators=contextlib.contextmanager
# List of members which are set dynamically and missed by pylint inference # List of members which are set dynamically and missed by pylint inference
# system, and so shouldn't trigger E1101 when accessed. Python regular # system, and so shouldn't trigger E1101 when accessed. Python regular
# expressions are accepted. # expressions are accepted.
generated-members=query generated-members=query,UniqueConstraint
# Tells whether missing members accessed in mixin class should be ignored. A # Tells whether missing members accessed in mixin class should be ignored. A
# mixin class is detected if its name ends with "mixin" (case insensitive). # mixin class is detected if its name ends with "mixin" (case insensitive).
......
from operator import attrgetter
from sqlalchemy import Column, String, Integer, Text, ForeignKey from sqlalchemy import Column, String, Integer, Text, ForeignKey
from sqlalchemy.orm import relationship from sqlalchemy.orm import relationship
from sqlalchemy.ext.declarative import declared_attr from sqlalchemy.ext.declarative import declared_attr
from uffd.database import db from uffd.database import db
from uffd.user.models import User, Group from uffd.user import User, Group
class Role(db.Model): class Role(db.Model):
__tablename__ = 'role' __tablename__ = 'role'
id = Column(Integer(), primary_key=True, autoincrement=True) id = Column(Integer(), primary_key=True, autoincrement=True)
name = Column(String(32), unique=True) name = Column(String(32), unique=True)
description = Column(Text()) description = Column(Text())
members = relationship("RoleUser", backref="role") members = relationship("RoleUser", backref="role", cascade="all, delete-orphan")
groups = relationship("RoleGroup", backref="role") groups = relationship("RoleGroup", backref="role", cascade="all, delete-orphan")
def __init__(self, name='', description=''): def __init__(self, name='', description=''):
self.name = name self.name = name
self.description = description self.description = description
def group_dns(self):
return map(attrgetter('dn'), self.groups)
def member_dns(self):
return map(attrgetter('dn'), self.members)
class LdapMapping(): class LdapMapping():
id = Column(Integer(), primary_key=True, autoincrement=True) id = Column(Integer(), primary_key=True, autoincrement=True)
dn = Column(String(128)) dn = Column(String(128))
__table_args__ = (
db.UniqueConstraint('dn', 'role_id'),
)
@declared_attr @declared_attr
def role_id(self): def role_id(self):
return Column(ForeignKey('role.id')) return Column(ForeignKey('role.id'))
......
...@@ -15,6 +15,47 @@ ...@@ -15,6 +15,47 @@
<small class="form-text text-muted"> <small class="form-text text-muted">
</small> </small>
</div> </div>
<div class="form-group col">
<p>
Included groups
</p>
<table class="table table-striped table-sm">
<thead>
<tr>
<th scope="col"></th>
<th scope="col">name</th>
<th scope="col">description</th>
</tr>
</thead>
<tbody>
{% for group in groups|sort(attribute="name") %}
<tr id="group-{{ group.gid }}">
<td>
<div class="form-check">
<input class="form-check-input" type="checkbox" id="group-{{ group.gid }}-checkbox" name="group-{{ group.gid }}" value="1" aria-label="enabled" {% if group.dn in role.group_dns() %}checked{% endif %}>
</div>
</td>
<td>
<a href="{{ url_for("group.show", gid=group.gid) }}">
{{ group.name }}
</a>
</td>
<td>
{{ group.description }}
</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
<div class="form-group col">
<p>
Members
</p>
{% for member in role.members %}
{{ member.dn }}
{% endfor %}
</div>
<div class="form-group col"> <div class="form-group col">
<button type="submit" class="btn btn-primary"><i class="fa fa-save" aria-hidden="true"></i> Save</button> <button type="submit" class="btn btn-primary"><i class="fa fa-save" aria-hidden="true"></i> Save</button>
......
...@@ -2,7 +2,8 @@ from flask import Blueprint, render_template, request, url_for, redirect, flash, ...@@ -2,7 +2,8 @@ from flask import Blueprint, render_template, request, url_for, redirect, flash,
from uffd.navbar import register_navbar from uffd.navbar import register_navbar
from uffd.csrf import csrf_protect from uffd.csrf import csrf_protect
from uffd.role.models import Role from uffd.role.models import Role, RoleGroup
from uffd.user import Group
from uffd.session import get_current_user, login_required, is_valid_session from uffd.session import get_current_user, login_required, is_valid_session
from uffd.database import db from uffd.database import db
...@@ -29,7 +30,8 @@ def show(roleid=False): ...@@ -29,7 +30,8 @@ def show(roleid=False):
role = Role() role = Role()
else: else:
role = Role.query.get_or_404(roleid) role = Role.query.get_or_404(roleid)
return render_template('role.html', role=role) groups = Group.from_ldap_all()
return render_template('role.html', role=role, groups=groups)
@bp.route("/<int:roleid>/update", methods=['POST']) @bp.route("/<int:roleid>/update", methods=['POST'])
@bp.route("/new", methods=['POST']) @bp.route("/new", methods=['POST'])
...@@ -44,7 +46,20 @@ def update(roleid=False): ...@@ -44,7 +46,20 @@ def update(roleid=False):
role = session.query(Role).get_or_404(roleid) role = session.query(Role).get_or_404(roleid)
role.name = request.values['name'] role.name = request.values['name']
role.description = request.values['description'] role.description = request.values['description']
print(role)
groups = Group.from_ldap_all()
role_group_dns = list(role.group_dns())
for group in groups:
if request.values.get('group-{}'.format(group.gid), False):
if group.dn in role_group_dns:
continue
newmapping = RoleGroup()
newmapping.dn = group.dn
newmapping.role = role
session.add(newmapping)
elif group.dn in role_group_dns:
session.delete(RoleGroup.query.filter_by(role_id=role.id, dn=group.dn).one())
session.commit() session.commit()
return redirect(url_for('role.index')) return redirect(url_for('role.index'))
......
...@@ -106,12 +106,13 @@ class User(): ...@@ -106,12 +106,13 @@ class User():
return True return True
class Group(): class Group():
def __init__(self, gid=None, name='', members=None, description=''): def __init__(self, gid=None, name='', members=None, description='', dn=None):
self.gid = gid self.gid = gid
self.name = name self.name = name
self.members_ldap = members self.members_ldap = members
self._members = None self._members = None
self.description = description self.description = description
self.dn = dn
@classmethod @classmethod
def from_ldap(cls, ldapobject): def from_ldap(cls, ldapobject):
...@@ -120,6 +121,7 @@ class Group(): ...@@ -120,6 +121,7 @@ class Group():
name=ldapobject['cn'].value, name=ldapobject['cn'].value,
members=ldap.get_ldap_array_attribute_safe(ldapobject, 'uniqueMember'), members=ldap.get_ldap_array_attribute_safe(ldapobject, 'uniqueMember'),
description=ldap.get_ldap_attribute_safe(ldapobject, 'description') or '', description=ldap.get_ldap_attribute_safe(ldapobject, 'description') or '',
dn=ldapobject.entry_dn,
) )
@classmethod @classmethod
...@@ -130,6 +132,15 @@ class Group(): ...@@ -130,6 +132,15 @@ class Group():
return None return None
return Group.from_ldap(conn.entries[0]) return Group.from_ldap(conn.entries[0])
@classmethod
def from_ldap_all(cls):
conn = ldap.get_conn()
conn.search(current_app.config["LDAP_BASE_GROUPS"], '(objectclass=groupOfUniqueNames)')
groups = []
for i in conn.entries:
groups.append(Group.from_ldap(i))
return groups
def to_ldap(self, new): def to_ldap(self, new):
pass pass
......
...@@ -20,12 +20,7 @@ def group_acl_check(): ...@@ -20,12 +20,7 @@ def group_acl_check():
@bp.route("/") @bp.route("/")
@register_navbar('Groups', icon='layer-group', blueprint=bp, visible=group_acl_check) @register_navbar('Groups', icon='layer-group', blueprint=bp, visible=group_acl_check)
def index(): def index():
conn = get_conn() return render_template('group_list.html', groups=Group.from_ldap_all())
conn.search(current_app.config["LDAP_BASE_GROUPS"], '(objectclass=groupOfUniqueNames)')
groups = []
for i in conn.entries:
groups.append(Group.from_ldap(i))
return render_template('group_list.html', groups=groups)
@bp.route("/<int:gid>") @bp.route("/<int:gid>")
def show(gid): def show(gid):
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment