Basic administrator view
This commit is contained in:
parent
5918cde53b
commit
95e6a56f81
@ -54,7 +54,16 @@ class Voter(EmbeddedObject):
|
||||
votes = EmbeddedObjectListField()
|
||||
|
||||
class User(EmbeddedObject):
|
||||
pass
|
||||
admins = []
|
||||
|
||||
def matched_by(self, other):
|
||||
return self == other
|
||||
|
||||
def is_admin(self):
|
||||
for admin in User.admins:
|
||||
if admin.matched_by(self):
|
||||
return True
|
||||
return False
|
||||
|
||||
def generate_password():
|
||||
if is_python:
|
||||
|
@ -117,17 +117,21 @@ class Workflow(EmbeddedObject):
|
||||
# ==============
|
||||
|
||||
class TaskConfigureElection(WorkflowTask):
|
||||
label = 'Configure the election and freeze the election'
|
||||
|
||||
#def on_enter(self):
|
||||
# self.status = WorkflowTask.Status.COMPLETE
|
||||
pass
|
||||
|
||||
class TaskOpenVoting(WorkflowTask):
|
||||
label = 'Open voting'
|
||||
depends_on = ['eos.base.workflow.TaskConfigureElection']
|
||||
|
||||
class TaskCloseVoting(WorkflowTask):
|
||||
label = 'Close voting'
|
||||
depends_on = ['eos.base.workflow.TaskOpenVoting']
|
||||
|
||||
class TaskDecryptVotes(WorkflowTask):
|
||||
label = 'Decrypt the votes'
|
||||
depends_on = ['eos.base.workflow.TaskCloseVoting']
|
||||
|
||||
def on_enter(self):
|
||||
@ -148,6 +152,7 @@ class TaskDecryptVotes(WorkflowTask):
|
||||
self.exit()
|
||||
|
||||
class TaskReleaseResults(WorkflowTask):
|
||||
label = 'Release the results'
|
||||
depends_on = ['eos.base.workflow.TaskDecryptVotes']
|
||||
|
||||
# Concrete workflows
|
||||
|
@ -22,6 +22,7 @@ import eos.base.workflow
|
||||
# ==============
|
||||
|
||||
class TaskMixVotes(WorkflowTask):
|
||||
label = 'Mix the votes'
|
||||
depends_on = ['eos.base.workflow.TaskCloseVoting']
|
||||
|
||||
def on_enter(self):
|
||||
@ -40,6 +41,7 @@ class TaskMixVotes(WorkflowTask):
|
||||
self.exit()
|
||||
|
||||
class TaskProveMixes(WorkflowTask):
|
||||
label = 'Prove the mixes'
|
||||
depends_on = ['eos.psr.workflow.TaskMixVotes']
|
||||
|
||||
def on_enter(self):
|
||||
|
@ -33,6 +33,7 @@ import functools
|
||||
import importlib
|
||||
import json
|
||||
import os
|
||||
import subprocess
|
||||
|
||||
app = flask.Flask(__name__, static_folder=None)
|
||||
|
||||
@ -50,6 +51,9 @@ if 'EOSWEB_SETTINGS' in os.environ:
|
||||
# Connect to database
|
||||
db_connect(app.config['DB_NAME'], app.config['DB_URI'], app.config['DB_TYPE'])
|
||||
|
||||
# Set configs
|
||||
User.admins = app.config['ADMINS']
|
||||
|
||||
# Make Flask's serialisation, e.g. for sessions, EosObject aware
|
||||
class EosObjectJSONEncoder(flask.json.JSONEncoder):
|
||||
def default(self, obj):
|
||||
@ -126,14 +130,6 @@ def setup_test_election():
|
||||
election.questions.append(question)
|
||||
|
||||
election.save()
|
||||
|
||||
# Freeze election
|
||||
election.workflow.get_task('eos.base.workflow.TaskConfigureElection').enter()
|
||||
|
||||
# Open voting
|
||||
election.workflow.get_task('eos.base.workflow.TaskOpenVoting').enter()
|
||||
|
||||
election.save()
|
||||
|
||||
@app.cli.command('close_election')
|
||||
@click.option('--electionid', default=None)
|
||||
@ -194,6 +190,15 @@ def using_election(func):
|
||||
return func(election)
|
||||
return wrapped
|
||||
|
||||
def election_admin(func):
|
||||
@functools.wraps(func)
|
||||
def wrapped(election):
|
||||
if 'user' in flask.session and flask.session['user'].is_admin():
|
||||
return func(election)
|
||||
else:
|
||||
return flask.Response('Administrator credentials required', 403)
|
||||
return wrapped
|
||||
|
||||
@app.route('/election/<election_id>/')
|
||||
@using_election
|
||||
def election_api_json(election):
|
||||
@ -202,7 +207,7 @@ def election_api_json(election):
|
||||
@app.route('/election/<election_id>/view')
|
||||
@using_election
|
||||
def election_view(election):
|
||||
return flask.render_template('election/view.html', election=election)
|
||||
return flask.render_template('election/view/view.html', election=election)
|
||||
|
||||
@app.route('/election/<election_id>/booth')
|
||||
@using_election
|
||||
@ -210,22 +215,28 @@ def election_booth(election):
|
||||
selection_model_view_map = EosObject.to_json({key._name: val for key, val in model_view_map.items()}) # ewww
|
||||
auth_methods = EosObject.to_json(app.config['AUTH_METHODS'])
|
||||
|
||||
return flask.render_template('election/booth.html', election=election, selection_model_view_map=selection_model_view_map, auth_methods=auth_methods)
|
||||
return flask.render_template('election/view/booth.html', election=election, selection_model_view_map=selection_model_view_map, auth_methods=auth_methods)
|
||||
|
||||
@app.route('/election/<election_id>/view/questions')
|
||||
@using_election
|
||||
def election_view_questions(election):
|
||||
return flask.render_template('election/questions.html', election=election)
|
||||
return flask.render_template('election/view/questions.html', election=election)
|
||||
|
||||
@app.route('/election/<election_id>/view/ballots')
|
||||
@using_election
|
||||
def election_view_ballots(election):
|
||||
return flask.render_template('election/ballots.html', election=election)
|
||||
return flask.render_template('election/view/ballots.html', election=election)
|
||||
|
||||
@app.route('/election/<election_id>/view/trustees')
|
||||
@using_election
|
||||
def election_view_trustees(election):
|
||||
return flask.render_template('election/trustees.html', election=election)
|
||||
return flask.render_template('election/view/trustees.html', election=election)
|
||||
|
||||
@app.route('/election/<election_id>/admin')
|
||||
@using_election
|
||||
@election_admin
|
||||
def election_admin_summary(election):
|
||||
return flask.render_template('election/admin/admin.html', election=election)
|
||||
|
||||
@app.route('/election/<election_id>/cast_ballot', methods=['POST'])
|
||||
@using_election
|
||||
|
@ -29,7 +29,7 @@
|
||||
<a href="https://github.com/RunasSudo/Eos" class="item">Source Code</a>
|
||||
{% if session.user %}
|
||||
<div class="ui simple dropdown item right">
|
||||
{{ session.user.name }} <i class="dropdown icon"></i>
|
||||
<i class="{% if session.user.is_admin() %}legal{% else %}user circle{% endif %} icon"></i> {{ session.user.name }} <i class="dropdown icon"></i>
|
||||
<div class="menu">
|
||||
<a href="{{ url_for('logout') }}?next={{ request.full_path|urlencode }}" class="item">Log out</a>
|
||||
</div>
|
||||
|
31
eosweb/core/templates/election/admin/admin.html
Normal file
31
eosweb/core/templates/election/admin/admin.html
Normal file
@ -0,0 +1,31 @@
|
||||
{% extends 'election/base.html' %}
|
||||
|
||||
{#
|
||||
Eos - Verifiable elections
|
||||
Copyright © 2017 RunasSudo (Yingtong Li)
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU Affero General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Affero General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Affero General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#}
|
||||
|
||||
{% block electioncontent %}
|
||||
<h2>Next tasks</h2>
|
||||
|
||||
<ul>
|
||||
{% for task in election.workflow.tasks %}
|
||||
{% if task.status == eos.base.workflow.WorkflowTask.Status.READY %}
|
||||
<li>{{ task.label }}</li>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</ul>
|
||||
{% endblock %}
|
@ -31,6 +31,9 @@
|
||||
|
||||
<div class="ui secondary pointing menu" id="election-tab-menu">
|
||||
{% include eosweb.core.main.model_view_map[election.__class__]['tabs'] %}
|
||||
{% if session.user and session.user.is_admin() %}
|
||||
<a href="{{ url_for('election_admin_summary', election_id=election._id) }}" class="election-tab-ajax item{% if request.endpoint == 'election_admin' %} active{% endif %} right"><i class="configure icon"></i> Administrate this election</a>
|
||||
{% endif %}
|
||||
</div>
|
||||
<div class="ui container" id="election-tab-content">
|
||||
{% block electioncontent %}
|
||||
|
@ -9,6 +9,11 @@ AUTH_METHODS = [
|
||||
('reddit', 'Reddit')
|
||||
]
|
||||
|
||||
import eos.redditauth.election
|
||||
ADMINS = [
|
||||
#eos.redditauth.election.RedditUser(username='xxxxxxxx')
|
||||
]
|
||||
|
||||
# MongoDB
|
||||
|
||||
DB_TYPE = 'mongodb'
|
||||
|
Loading…
Reference in New Issue
Block a user