@@ -1,5 +1,5 @@ | |||
# @name: book.py | |||
# @creation_date: 2021-11-03 | |||
# @creation_date: 2022-04-05 | |||
# @license: The MIT License <https://opensource.org/licenses/MIT> | |||
# @author: Simon Bowie <ad7588@coventry.ac.uk> | |||
# @purpose: book route for book-related functions and pages | |||
@@ -9,35 +9,30 @@ | |||
from flask import Blueprint, render_template, request, flash, redirect, url_for | |||
from flask_login import login_required, current_user | |||
from .models import Resource | |||
from .resources import * | |||
from werkzeug.exceptions import abort | |||
from . import db | |||
book = Blueprint('book', __name__) | |||
# function to retrieve data about a single book from the database | |||
def get_book(book_id): | |||
book = Book.query.filter_by(id=book_id).first() | |||
if book is None: | |||
abort(404) | |||
return book | |||
# route for displaying all books in database | |||
@book.route('/books') | |||
def get_books(): | |||
books = Book.query | |||
return render_template('books.html', books=books) | |||
books = Resource.query.filter_by(type='book') | |||
return render_template('resources.html', resources=books, type='book') | |||
# route for displaying a single book based on the ID in the database | |||
@book.route('/books/<int:book_id>') | |||
def show_book(book_id): | |||
book = get_book(book_id) | |||
return render_template('book.html', book=book) | |||
book = get_resource(book_id) | |||
links = get_linked_resources(book_id) | |||
return render_template('resource.html', resource=book, links=links) | |||
# route for editing a single book based on the ID in the database | |||
@book.route('/books/<int:book_id>/edit', methods=('GET', 'POST')) | |||
@login_required | |||
def edit_book(book_id): | |||
book = get_book(book_id) | |||
book = get_resource(book_id) | |||
if request.method == 'POST': | |||
name = request.form['name'] | |||
@@ -46,21 +41,17 @@ def edit_book(book_id): | |||
if not name: | |||
flash('Name is required!') | |||
else: | |||
book = Book.query.get(book_id) | |||
book = Resource.query.get(book_id) | |||
book.name = name | |||
book.description = description | |||
db.session.commit() | |||
return redirect(url_for('book.get_books')) | |||
return render_template('edit.html', book=book) | |||
return render_template('edit.html', resource=book) | |||
# route for function to delete a single book from the edit page | |||
@book.route('/books/<int:book_id>/delete', methods=('POST',)) | |||
@login_required | |||
def delete_book(book_id): | |||
book = get_book(book_id) | |||
deletion = Book.query.get(book_id) | |||
db.session.delete(deletion) | |||
db.session.commit() | |||
flash('Successfully deleted!') | |||
delete_resource(book_id) | |||
return redirect(url_for('book.get_books')) |
@@ -19,14 +19,14 @@ practice = Blueprint('practice', __name__) | |||
@practice.route('/practices') | |||
def get_practices(): | |||
practices = Resource.query.filter_by(type='practice') | |||
return render_template('practices.html', practices=practices) | |||
return render_template('resources.html', resources=practices, type='practice') | |||
# route for displaying a single practice based on the ID in the database | |||
@practice.route('/practices/<int:practice_id>') | |||
def show_practice(practice_id): | |||
practice = get_resource(practice_id) | |||
resources = get_linked_resources(practice_id) | |||
return render_template('practice.html', practice=practice, resources=resources) | |||
links = get_linked_resources(practice_id) | |||
return render_template('resource.html', resource=practice, links=links) | |||
# route for editing a single practice based on the ID in the database | |||
@practice.route('/practices/<int:practice_id>/edit', methods=('GET', 'POST')) |
@@ -1,5 +1,5 @@ | |||
# @name: publisher.py | |||
# @creation_date: 2022-02-08 | |||
# @creation_date: 2022-04-05 | |||
# @license: The MIT License <https://opensource.org/licenses/MIT> | |||
# @author: Simon Bowie <ad7588@coventry.ac.uk> | |||
# @purpose: publisher route for publisher-related functions and pages | |||
@@ -9,35 +9,30 @@ | |||
from flask import Blueprint, render_template, request, flash, redirect, url_for | |||
from flask_login import login_required, current_user | |||
from .models import Resource | |||
from .resources import * | |||
from werkzeug.exceptions import abort | |||
from . import db | |||
publisher = Blueprint('publisher', __name__) | |||
# function to retrieve data about a single publisher from the database | |||
def get_publisher(publisher_id): | |||
publisher = Publisher.query.filter_by(id=publisher_id).first() | |||
if publisher is None: | |||
abort(404) | |||
return publisher | |||
# route for displaying all publishers in database | |||
@publisher.route('/publishers') | |||
def get_publishers(): | |||
publishers = Publisher.query | |||
return render_template('publishers.html', publishers=publishers) | |||
publishers = Resource.query.filter_by(type='publisher') | |||
return render_template('resources.html', resources=publishers, type='publisher') | |||
# route for displaying a single publisher based on the ID in the database | |||
@publisher.route('/publishers/<int:publisher_id>') | |||
def show_publisher(publisher_id): | |||
publisher = get_publisher(publisher_id) | |||
return render_template('publisher.html', publisher=publisher) | |||
publisher = get_resource(publisher_id) | |||
links = get_linked_resources(publisher_id) | |||
return render_template('resource.html', resource=publisher, links=links) | |||
# route for editing a single publisher based on the ID in the database | |||
@publisher.route('/publishers/<int:publisher_id>/edit', methods=('GET', 'POST')) | |||
@login_required | |||
def edit_publisher(publisher_id): | |||
publisher = get_publisher(publisher_id) | |||
publisher = get_resource(publisher_id) | |||
if request.method == 'POST': | |||
name = request.form['name'] | |||
@@ -46,21 +41,17 @@ def edit_publisher(publisher_id): | |||
if not name: | |||
flash('Name is required!') | |||
else: | |||
publisher = Publisher.query.get(publisher_id) | |||
publisher = Resource.query.get(publisher_id) | |||
publisher.name = name | |||
publisher.description = description | |||
db.session.commit() | |||
return redirect(url_for('publisher.get_publishers')) | |||
return render_template('edit.html', publisher=publisher) | |||
return render_template('edit.html', resource=publisher) | |||
# route for function to delete a single publisher from the edit page | |||
@publisher.route('/publishers/<int:publisher_id>/delete', methods=('POST',)) | |||
@login_required | |||
def delete_publisher(publisher_id): | |||
publisher = get_publisher(publisher_id) | |||
deletion = Publisher.query.get(publisher_id) | |||
db.session.delete(deletion) | |||
db.session.commit() | |||
flash('Successfully deleted!') | |||
delete_resource(publisher_id) | |||
return redirect(url_for('publisher.get_publishers')) |
@@ -1,5 +1,5 @@ | |||
# @name: reference.py | |||
# @creation_date: 2022-02-08 | |||
# @creation_date: 2022-04-05 | |||
# @license: The MIT License <https://opensource.org/licenses/MIT> | |||
# @author: Simon Bowie <ad7588@coventry.ac.uk> | |||
# @purpose: reference route for reference-related functions and pages | |||
@@ -9,35 +9,30 @@ | |||
from flask import Blueprint, render_template, request, flash, redirect, url_for | |||
from flask_login import login_required, current_user | |||
from .models import Resource | |||
from .resources import * | |||
from werkzeug.exceptions import abort | |||
from . import db | |||
reference = Blueprint('reference', __name__) | |||
# function to retrieve data about a single reference from the database | |||
def get_reference(reference_id): | |||
reference = Reference.query.filter_by(id=reference_id).first() | |||
if reference is None: | |||
abort(404) | |||
return reference | |||
# route for displaying all references in database | |||
@reference.route('/references') | |||
def get_references(): | |||
references = Reference.query | |||
return render_template('references.html', references=references) | |||
references = Resource.query.filter_by(type='reference') | |||
return render_template('resources.html', resources=references, type='reference') | |||
# route for displaying a single reference based on the ID in the database | |||
@reference.route('/references/<int:reference_id>') | |||
def show_reference(reference_id): | |||
reference = get_reference(reference_id) | |||
return render_template('reference.html', reference=reference) | |||
reference = get_resource(reference_id) | |||
links = get_linked_resources(reference_id) | |||
return render_template('resource.html', resource=reference, links=links) | |||
# route for editing a single reference based on the ID in the database | |||
@reference.route('/references/<int:reference_id>/edit', methods=('GET', 'POST')) | |||
@login_required | |||
def edit_reference(reference_id): | |||
reference = get_reference(reference_id) | |||
reference = get_resource(reference_id) | |||
if request.method == 'POST': | |||
name = request.form['name'] | |||
@@ -46,21 +41,17 @@ def edit_reference(reference_id): | |||
if not name: | |||
flash('Name is required!') | |||
else: | |||
reference = Reference.query.get(reference_id) | |||
reference = Resource.query.get(reference_id) | |||
reference.name = name | |||
reference.description = description | |||
db.session.commit() | |||
return redirect(url_for('reference.get_references')) | |||
return render_template('edit.html', reference=reference) | |||
return render_template('edit.html', resource=reference) | |||
# route for function to delete a single reference from the edit page | |||
@reference.route('/references/<int:reference_id>/delete', methods=('POST',)) | |||
@login_required | |||
def delete_reference(reference_id): | |||
reference = get_reference(reference_id) | |||
deletion = Reference.query.get(reference_id) | |||
db.session.delete(deletion) | |||
db.session.commit() | |||
flash('Successfully deleted!') | |||
delete_resource(reference_id) | |||
return redirect(url_for('reference.get_references')) |
@@ -9,35 +9,30 @@ | |||
from flask import Blueprint, render_template, request, flash, redirect, url_for | |||
from flask_login import login_required, current_user | |||
from .models import Resource | |||
from .resources import * | |||
from werkzeug.exceptions import abort | |||
from . import db | |||
sensitivity = Blueprint('sensitivity', __name__) | |||
# function to retrieve data about a single sensitivity from the database | |||
def get_sensitivity(sensitivity_id): | |||
sensitivity = Sensitivity.query.filter_by(id=sensitivity_id).first() | |||
if sensitivity is None: | |||
abort(404) | |||
return sensitivity | |||
# route for displaying all sensitivities in database | |||
@sensitivity.route('/sensitivities') | |||
def get_sensitivities(): | |||
sensitivities = Sensitivity.query | |||
return render_template('sensitivities.html', sensitivities=sensitivities) | |||
sensitivities = Resource.query.filter_by(type='sensitivity') | |||
return render_template('resources.html', resources=sensitivities, type='sensitivity') | |||
# route for displaying a single sensitivity based on the ID in the database | |||
@sensitivity.route('/sensitivities/<int:sensitivity_id>') | |||
def show_sensitivity(sensitivity_id): | |||
sensitivity = get_sensitivity(sensitivity_id) | |||
return render_template('sensitivity.html', sensitivity=sensitivity) | |||
sensitivity = get_resource(sensitivity_id) | |||
links = get_linked_resources(sensitivity_id) | |||
return render_template('resource.html', resource=sensitivity, links=links) | |||
# route for editing a single sensitivity based on the ID in the database | |||
@sensitivity.route('/sensitivities/<int:sensitivity_id>/edit', methods=('GET', 'POST')) | |||
@login_required | |||
def edit_sensitivity(sensitivity_id): | |||
sensitivity = get_sensitivity(sensitivity_id) | |||
sensitivity = get_resource(sensitivity_id) | |||
if request.method == 'POST': | |||
name = request.form['name'] | |||
@@ -46,7 +41,7 @@ def edit_sensitivity(sensitivity_id): | |||
if not name: | |||
flash('Name is required!') | |||
else: | |||
sensitivity = Sensitivity.query.get(sensitivity_id) | |||
sensitivity = Resource.query.get(sensitivity_id) | |||
sensitivity.name = name | |||
sensitivity.description = description | |||
db.session.commit() | |||
@@ -58,9 +53,5 @@ def edit_sensitivity(sensitivity_id): | |||
@sensitivity.route('/sensitivities/<int:sensitivity_id>/delete', methods=('POST',)) | |||
@login_required | |||
def delete_sensitivity(sensitivity_id): | |||
sensitivity = get_sensitivity(sensitivity_id) | |||
deletion = Sensitivity.query.get(sensitivity_id) | |||
db.session.delete(deletion) | |||
db.session.commit() | |||
flash('Successfully deleted!') | |||
delete_resource(sensitivity_id) | |||
return redirect(url_for('sensitivity.get_sensitivities')) |
@@ -14,6 +14,16 @@ | |||
--highlight-colour:#EB7F1D; | |||
--hover-link-colour:#EB7F1D; | |||
--light-highlight-colour:#F8D9AA; | |||
--bs-primary-rgb: 13,110,253; | |||
--bs-secondary-rgb: 108,117,125; | |||
--bs-success-rgb: 25,135,84; | |||
--bs-tool-rgb: 13,202,240; | |||
--bs-practice-rgb: 255,193,7; | |||
--bs-danger-rgb: 220,53,69; | |||
--bs-light-rgb: 248,249,250; | |||
--bs-dark-rgb: 33,37,41; | |||
--bs-white-rgb: 255,255,255; | |||
--bs-black-rgb: 0,0,0; | |||
} | |||
@import "https://fonts.googleapis.com/css?family=Lato:300,400,700&display=swap"; | |||
@@ -123,28 +133,6 @@ h6, | |||
font-size: 15px | |||
} | |||
.btn-primary { | |||
background: var(--primary-color); | |||
color: #fff | |||
} | |||
.btn-primary.active { | |||
opacity: .8; | |||
} | |||
.btn-primary:active { | |||
background: var(--primary-color) !important | |||
} | |||
.btn-primary:hover { | |||
background: var(--primary-color) | |||
} | |||
.btn-primary.focus, | |||
.btn-primary.active { | |||
background: var(--primary-color) !important; | |||
box-shadow: none !important | |||
} | |||
.btn-transparent { | |||
background: transparent; | |||
@@ -1037,3 +1025,13 @@ main > .container { | |||
.carousel-indicators { | |||
filter: invert(100%); | |||
} | |||
.bg-tool { | |||
--bs-bg-opacity: 1; | |||
background-color: rgba(var(--bs-tool-rgb),var(--bs-bg-opacity))!important; | |||
} | |||
.bg-practice { | |||
--bs-bg-opacity: 1; | |||
background-color: rgba(var(--bs-practice-rgb),var(--bs-bg-opacity))!important; | |||
} |
@@ -139,7 +139,7 @@ | |||
<!-- Sticky footer--> | |||
<footer class="footer py-3 mt-auto" style="background-color: #dcddde;"> | |||
<div class="container"> | |||
<span class="text-muted">© {{ moment().format('YYYY') }} <a href="https://copim.ac.uk/">COPIM</a> and licensed under a <a href="https://creativecommons.org/licenses/by/4.0/">Creative Commons Attribution 4.0 International License (CC BY 4.0)</a>.</span> | |||
<span class="text-muted">© 2022–{{ moment().format('YYYY') }} <a href="https://copim.ac.uk/">COPIM</a> and licensed under a <a href="https://creativecommons.org/licenses/by/4.0/">Creative Commons Attribution 4.0 International License (CC BY 4.0)</a>.</span> | |||
</div> | |||
</footer> | |||
<!-- JavaScript --> |
@@ -1,40 +0,0 @@ | |||
{% extends 'base.html' %} | |||
{% block content %} | |||
<div class="row"> | |||
<div class="col-12 text-center"> | |||
<h1>{% block title %} Books {% endblock %}</h1> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
<div class="col-12 text-center"> | |||
<p> | |||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque eget viverra magna. Nam in ante ultricies purus feugiat vestibulum et ac erat. Donec in sagittis ante. Maecenas non mauris et eros commodo fringilla. Integer accumsan ullamcorper diam, non rhoncus tellus molestie ut. Maecenas finibus pretium dolor ac sagittis. | |||
</p> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
{% for example in examples %} | |||
<div class="col-md-4 col-sm-6 py-3"> | |||
<div class="card"> | |||
<div class="card-header"> | |||
<a href="{{ url_for('book.show_book', book_id=book['id']) }}"> | |||
<h2 class="card-title">{{ book['name'] }}</h2> | |||
</a> | |||
</div> | |||
<div class="card-body"> | |||
<p class="card-text"> | |||
{{ example['description']|truncate(100) }} | |||
</p> | |||
<span class="badge bg-secondary">{{ example['created'].strftime("%Y-%m-%d %H:%M") }} UTC</span> | |||
{% if current_user.is_authenticated %} | |||
<a href="{{ url_for('book.edit_book', book_id=book['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
{% endif %} | |||
</div> | |||
</div> | |||
</div> | |||
{% endfor %} | |||
</div> | |||
{% endblock %} |
@@ -1,65 +0,0 @@ | |||
{% extends 'base.html' %} | |||
{% block content %} | |||
<div class="row"> | |||
<div class="col"> | |||
<h1 class="text-center">{% block title %} {{ practice['name'] }} {% endblock %}</h1> | |||
</div> | |||
</div> | |||
{% if current_user.is_authenticated %} | |||
<div class="row text-center py-3"> | |||
<a href="{{ url_for('practice.edit_practice', practice_id=practice['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
</div> | |||
{% endif %} | |||
<div class="row"> | |||
<div class="col"> | |||
<table class="table table-hover"> | |||
<tbody> | |||
<tr> | |||
<th> | |||
Created: | |||
</th> | |||
<td> | |||
{{ practice['created'].strftime("%Y-%m-%d %H:%M") }} UTC | |||
</td> | |||
</tr> | |||
<tr> | |||
<th> | |||
Description: | |||
</th> | |||
<td> | |||
{{ practice['description'] }} | |||
</td> | |||
</tr> | |||
</tbody> | |||
</table> | |||
</div> | |||
</div> | |||
{% if resources %} | |||
<div class="row"> | |||
<div class="col"> | |||
<h2 class="text-center">Linked resources:</h2> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
{% for resource in resources %} | |||
<div class="col-md-4 col-sm-6 py-3"> | |||
{% if resource['type'] == 'tool' %} | |||
<div class="card text-dark bg-info mb-3"> | |||
<div class="card-body"> | |||
<a href="{{ url_for('tool.show_tool', tool_id=resource['id']) }}"> | |||
<h3 class="card-title text-center text-dark">{{ resource['name'] }}</h3> | |||
</a> | |||
<p class="card-text"> | |||
{{ resource['description']|truncate(100) }} | |||
</p> | |||
</div> | |||
</div> | |||
{% endif %} | |||
</div> | |||
{% endfor %} | |||
</div> | |||
{% endif %} | |||
{% endblock %} |
@@ -1,37 +0,0 @@ | |||
{% extends 'base.html' %} | |||
{% block content %} | |||
<div class="row"> | |||
<div class="col-12 text-center"> | |||
<h1>{% block title %} Practices {% endblock %}</h1> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
<div class="col-12 text-center"> | |||
<p> | |||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque eget viverra magna. Nam in ante ultricies purus feugiat vestibulum et ac erat. Donec in sagittis ante. Maecenas non mauris et eros commodo fringilla. Integer accumsan ullamcorper diam, non rhoncus tellus molestie ut. Maecenas finibus pretium dolor ac sagittis. | |||
</p> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
{% for practice in practices %} | |||
<div class="col-md-4 col-sm-6 py-3"> | |||
<div class="card text-dark bg-warning mb-3"> | |||
<div class="card-body"> | |||
<a href="{{ url_for('practice.show_practice', practice_id=practice['id']) }}"> | |||
<h3 class="card-title text-center text-dark">{{ practice['name'] }}</h3> | |||
</a> | |||
<p class="card-text"> | |||
{{ practice['description']|truncate(100) }} | |||
</p> | |||
{% if current_user.is_authenticated %} | |||
<a href="{{ url_for('practice.edit_practice', practice_id=practice['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
{% endif %} | |||
</div> | |||
</div> | |||
</div> | |||
{% endfor %} | |||
</div> | |||
{% endblock %} |
@@ -3,15 +3,24 @@ | |||
{% block content %} | |||
<div class="row"> | |||
<div class="col"> | |||
<h1 class="text-center">{% block title %} {{ tool['name'] }} {% endblock %}</h1> | |||
<h1 class="text-center">{% block title %} {{ resource['name'] }} {% endblock %}</h1> | |||
</div> | |||
</div> | |||
{% if current_user.is_authenticated %} | |||
<div class="row text-center py-3"> | |||
<a href="{{ url_for('tool.edit_tool', tool_id=tool['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
</div> | |||
{% if resource['type'] == 'tool' %} | |||
<div class="row text-center py-3"> | |||
<a href="{{ url_for('tool.edit_tool', tool_id=resource['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
</div> | |||
{% endif %} | |||
{% if resource['type'] == 'practice' %} | |||
<div class="row text-center py-3"> | |||
<a href="{{ url_for('practice.edit_practice', practice_id=resource['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
</div> | |||
{% endif %} | |||
{% endif %} | |||
<div class="row"> | |||
<div class="col"> | |||
@@ -22,7 +31,7 @@ | |||
Created: | |||
</th> | |||
<td> | |||
{{ tool['created'].strftime("%Y-%m-%d %H:%M") }} UTC | |||
{{ resource['created'].strftime("%Y-%m-%d %H:%M") }} UTC | |||
</td> | |||
</tr> | |||
<tr> | |||
@@ -30,94 +39,110 @@ | |||
Description: | |||
</th> | |||
<td> | |||
{{ tool['description'] }} | |||
{{ resource['description'] }} | |||
</td> | |||
</tr> | |||
{% if resource['projectUrl'] %} | |||
<tr> | |||
<th> | |||
Project page: | |||
</th> | |||
<td> | |||
<a href="{{ tool['projectUrl'] }}">{{ tool['projectUrl'] }}</a> | |||
<a href="{{ resource['projectUrl'] }}">{{ resource['projectUrl'] }}</a> | |||
</td> | |||
</tr> | |||
{% endif %} | |||
{% if resource['repositoryUrl'] %} | |||
<tr> | |||
<th> | |||
Code repository: | |||
</th> | |||
<td> | |||
<a href="{{ tool['repositoryUrl'] }}">{{ tool['repositoryUrl'] }}</a> | |||
<a href="{{ resource['repositoryUrl'] }}">{{ resource['repositoryUrl'] }}</a> | |||
</td> | |||
</tr> | |||
{% endif %} | |||
{% if resource['expertiseToUse'] %} | |||
<tr> | |||
<th> | |||
Expertise required to use: | |||
</th> | |||
<td> | |||
{{ tool['expertiseToUse'] }} | |||
{{ resource['expertiseToUse'] }} | |||
</td> | |||
</tr> | |||
{% endif %} | |||
{% if resource['expertiseToHost'] %} | |||
<tr> | |||
<th> | |||
Expertise required to self-host: | |||
</th> | |||
<td> | |||
{{ tool['expertiseToHost'] }} | |||
{{ resource['expertiseToHost'] }} | |||
</td> | |||
</tr> | |||
{% endif %} | |||
{% if resource['dependencies'] %} | |||
<tr> | |||
<th> | |||
Technical dependencies: | |||
</th> | |||
<td> | |||
{{ tool['dependencies'] }} | |||
{{ resource['dependencies'] }} | |||
</td> | |||
</tr> | |||
{% endif %} | |||
{% if resource['ingestFormats'] %} | |||
<tr> | |||
<th> | |||
Import / ingest formats: | |||
</th> | |||
<td> | |||
{{ tool['ingestFormats'] }} | |||
{{ resource['ingestFormats'] }} | |||
</td> | |||
</tr> | |||
{% endif %} | |||
{% if resource['outputFormats'] %} | |||
<tr> | |||
<th> | |||
Output formats: | |||
</th> | |||
<td> | |||
{{ tool['outputFormats'] }} | |||
{{ resource['outputFormats'] }} | |||
</td> | |||
</tr> | |||
{% endif %} | |||
{% if resource['status'] %} | |||
<tr> | |||
<th> | |||
Platform status: | |||
</th> | |||
<td> | |||
{{ tool['status'] }} | |||
{{ resource['status'] }} | |||
</td> | |||
</tr> | |||
{% endif %} | |||
</tbody> | |||
</table> | |||
</div> | |||
</div> | |||
{% if resources %} | |||
{% if links %} | |||
<div class="row"> | |||
<div class="col"> | |||
<h2 class="text-center">Linked resources:</h2> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
{% for resource in resources %} | |||
{% for link in links %} | |||
<div class="col-md-4 col-sm-6 py-3"> | |||
{% if resource['type'] == 'practice' %} | |||
<div class="card text-dark bg-warning mb-3"> | |||
{% if link['type'] == 'practice' %} | |||
<div class="card text-dark bg-practice mb-3"> | |||
<div class="card-body"> | |||
<a href="{{ url_for('practice.show_practice', practice_id=resource['id']) }}"> | |||
<h3 class="card-title text-center text-dark">{{ resource['name'] }}</h3> | |||
<a href="{{ url_for('practice.show_practice', practice_id=link['id']) }}"> | |||
<h3 class="card-title text-center text-dark">{{ link['name'] }}</h3> | |||
</a> | |||
<p class="card-text"> | |||
{{ resource['description']|truncate(100) }} | |||
{{ link['description']|truncate(100) }} | |||
</p> | |||
</div> | |||
</div> |
@@ -0,0 +1,59 @@ | |||
{% extends 'base.html' %} | |||
{% block content %} | |||
<div class="row"> | |||
<div class="col-12 text-center"> | |||
<h1>{% block title %} | |||
{% if (type == 'sensitivity') %} | |||
{{ type|capitalize|replace("ty", "ties") }} | |||
{% elif (type == 'typology') %} | |||
{{ type|capitalize|replace("gy", "gies") }} | |||
{% else %} | |||
{{ type|capitalize + 's' }} | |||
{% endif %} | |||
{% endblock %} | |||
</h1> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
<div class="col-12 text-center"> | |||
<p> | |||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque eget viverra magna. Nam in ante ultricies purus feugiat vestibulum et ac erat. Donec in sagittis ante. Maecenas non mauris et eros commodo fringilla. Integer accumsan ullamcorper diam, non rhoncus tellus molestie ut. Maecenas finibus pretium dolor ac sagittis. | |||
</p> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
{% for resource in resources %} | |||
<div class="col-md-4 col-sm-6 py-3"> | |||
<div class="card text-dark bg-{{type}} mb-3"> | |||
<div class="card-body"> | |||
{% if resource['type'] == 'tool' %} | |||
<a href="{{ url_for('tool.show_tool', tool_id=resource['id']) }}"> | |||
<h3 class="card-title text-center text-dark">{{ resource['name'] }}</h3> | |||
</a> | |||
{% elif resource['type'] == 'practice' %} | |||
<a href="{{ url_for('practice.show_practice', practice_id=resource['id']) }}"> | |||
<h3 class="card-title text-center text-dark">{{ resource['name'] }}</h3> | |||
</a> | |||
{% endif %} | |||
<p class="card-text"> | |||
{{ resource['description']|truncate(100) }} | |||
</p> | |||
{% if current_user.is_authenticated %} | |||
{% if resource['type'] == 'tool' %} | |||
<a href="{{ url_for('tool.edit_tool', tool_id=resource['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
{% endif %} | |||
{% if resource['type'] == 'practice' %} | |||
<a href="{{ url_for('practice.edit_practice', practice_id=resource['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
{% endif %} | |||
{% endif %} | |||
</div> | |||
</div> | |||
</div> | |||
{% endfor %} | |||
</div> | |||
{% endblock %} |
@@ -1,37 +0,0 @@ | |||
{% extends 'base.html' %} | |||
{% block content %} | |||
<div class="row"> | |||
<div class="col-12 text-center"> | |||
<h1>{% block title %} Tools {% endblock %}</h1> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
<div class="col-12 text-center"> | |||
<p> | |||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque eget viverra magna. Nam in ante ultricies purus feugiat vestibulum et ac erat. Donec in sagittis ante. Maecenas non mauris et eros commodo fringilla. Integer accumsan ullamcorper diam, non rhoncus tellus molestie ut. Maecenas finibus pretium dolor ac sagittis. | |||
</p> | |||
</div> | |||
</div> | |||
<div class="row"> | |||
{% for tool in tools %} | |||
<div class="col-md-4 col-sm-6 py-3"> | |||
<div class="card text-dark bg-info mb-3"> | |||
<div class="card-body"> | |||
<a href="{{ url_for('tool.show_tool', tool_id=tool['id']) }}"> | |||
<h3 class="card-title text-center text-dark">{{ tool['name'] }}</h3> | |||
</a> | |||
<p class="card-text"> | |||
{{ tool['description']|truncate(100) }} | |||
</p> | |||
{% if current_user.is_authenticated %} | |||
<a href="{{ url_for('tool.edit_tool', tool_id=tool['id']) }}"> | |||
<span class="badge bg-dark">Edit</span> | |||
</a> | |||
{% endif %} | |||
</div> | |||
</div> | |||
</div> | |||
{% endfor %} | |||
</div> | |||
{% endblock %} |
@@ -19,14 +19,14 @@ tool = Blueprint('tool', __name__) | |||
@tool.route('/tools') | |||
def get_tools(): | |||
tools = Resource.query.filter_by(type='tool') | |||
return render_template('tools.html', tools=tools) | |||
return render_template('resources.html', resources=tools, type='tool') | |||
# route for displaying a single tool based on the ID in the database | |||
@tool.route('/tools/<int:tool_id>') | |||
def show_tool(tool_id): | |||
tool = get_resource(tool_id) | |||
resources = get_linked_resources(tool_id) | |||
return render_template('tool.html', tool=tool, resources=resources) | |||
links = get_linked_resources(tool_id) | |||
return render_template('resource.html', resource=tool, links=links) | |||
# route for editing a single tool based on the ID in the database | |||
@tool.route('/tools/<int:tool_id>/edit', methods=('GET', 'POST')) | |||
@@ -37,14 +37,14 @@ def edit_tool(tool_id): | |||
if request.method == 'POST': | |||
name = request.form['name'] | |||
description = request.form['description'] | |||
projectUrl = request.form.get('projectUrl') | |||
repositoryUrl = request.form.get('repositoryUrl') | |||
expertiseToUse = request.form.get('expertiseToUse') | |||
expertiseToHost = request.form.get('expertiseToHost') | |||
dependencies = request.form.get('dependencies') | |||
ingestFormats = request.form.get('ingestFormats') | |||
outputFormats = request.form.get('outputFormats') | |||
status = request.form.get('status') | |||
projectUrl = request.form['projectUrl'] | |||
repositoryUrl = request.form['repositoryUrl'] | |||
expertiseToUse = request.form['expertiseToUse'] | |||
expertiseToHost = request.form['expertiseToHost'] | |||
dependencies = request.form['dependencies'] | |||
ingestFormats = request.form['ingestFormats'] | |||
outputFormats = request.form['outputFormats'] | |||
status = request.form['status'] | |||
if not name: | |||
flash('Name is required!') |
@@ -1,5 +1,5 @@ | |||
# @name: typology.py | |||
# @creation_date: 2022-02-08 | |||
# @creation_date: 2022-04-05 | |||
# @license: The MIT License <https://opensource.org/licenses/MIT> | |||
# @author: Simon Bowie <ad7588@coventry.ac.uk> | |||
# @purpose: typology route for typology-related functions and pages | |||
@@ -9,35 +9,30 @@ | |||
from flask import Blueprint, render_template, request, flash, redirect, url_for | |||
from flask_login import login_required, current_user | |||
from .models import Resource | |||
from .resources import * | |||
from werkzeug.exceptions import abort | |||
from . import db | |||
typology = Blueprint('typology', __name__) | |||
# function to retrieve data about a single typology from the database | |||
def get_typology(typology_id): | |||
typology = Typology.query.filter_by(id=typology_id).first() | |||
if typology is None: | |||
abort(404) | |||
return typology | |||
# route for displaying all typologies in database | |||
@typology.route('/typologies') | |||
def get_typologies(): | |||
typologies = Typology.query | |||
return render_template('typologies.html', typologies=typologies) | |||
typologies = Resource.query.filter_by(type='typology') | |||
return render_template('resources.html', resources=typologies, type='typology') | |||
# route for displaying a single typology based on the ID in the database | |||
@typology.route('/typologies/<int:typology_id>') | |||
def show_typology(typology_id): | |||
typology = get_typology(typology_id) | |||
return render_template('typology.html', typology=typology) | |||
typology = get_resource(typology_id) | |||
links = get_linked_resources(typology_id) | |||
return render_template('resource.html', resource=typology, links=links) | |||
# route for editing a single typology based on the ID in the database | |||
@typology.route('/typologies/<int:typology_id>/edit', methods=('GET', 'POST')) | |||
@login_required | |||
def edit_typology(typology_id): | |||
typology = get_typology(typology_id) | |||
typology = get_resource(typology_id) | |||
if request.method == 'POST': | |||
name = request.form['name'] | |||
@@ -46,21 +41,17 @@ def edit_typology(typology_id): | |||
if not name: | |||
flash('Name is required!') | |||
else: | |||
typology = Typology.query.get(typology_id) | |||
typology = Resource.query.get(typology_id) | |||
typology.name = name | |||
typology.description = description | |||
db.session.commit() | |||
return redirect(url_for('typology.get_typologies')) | |||
return render_template('edit.html', typology=typology) | |||
return render_template('edit.html', resource=typology) | |||
# route for function to delete a single typology from the edit page | |||
@typology.route('/typologies/<int:typology_id>/delete', methods=('POST',)) | |||
@login_required | |||
def delete_typology(typology_id): | |||
typology = get_typology(typology_id) | |||
deletion = Typology.query.get(typology_id) | |||
db.session.delete(deletion) | |||
db.session.commit() | |||
flash('Successfully deleted!') | |||
delete_resource(typology_id) | |||
return redirect(url_for('typology.get_typologies')) |
@@ -1,5 +1,5 @@ | |||
# @name: workflow.py | |||
# @creation_date: 2022-02-08 | |||
# @creation_date: 2022-04-05 | |||
# @license: The MIT License <https://opensource.org/licenses/MIT> | |||
# @author: Simon Bowie <ad7588@coventry.ac.uk> | |||
# @purpose: workflow route for workflow-related functions and pages | |||
@@ -9,35 +9,30 @@ | |||
from flask import Blueprint, render_template, request, flash, redirect, url_for | |||
from flask_login import login_required, current_user | |||
from .models import Resource | |||
from .resources import * | |||
from werkzeug.exceptions import abort | |||
from . import db | |||
workflow = Blueprint('workflow', __name__) | |||
# function to retrieve data about a single workflow from the database | |||
def get_workflow(workflow_id): | |||
workflow = Workflow.query.filter_by(id=workflow_id).first() | |||
if workflow is None: | |||
abort(404) | |||
return workflow | |||
# route for displaying all workflows in database | |||
@workflow.route('/workflows') | |||
def get_workflows(): | |||
workflows = Workflow.query | |||
return render_template('workflows.html', workflows=workflows) | |||
workflows = Resource.query.filter_by(type='workflow') | |||
return render_template('resources.html', resources=workflows, type='workflow') | |||
# route for displaying a single workflow based on the ID in the database | |||
@workflow.route('/workflows/<int:workflow_id>') | |||
def show_workflow(workflow_id): | |||
workflow = get_workflow(workflow_id) | |||
return render_template('workflow.html', workflow=workflow) | |||
workflow = get_resource(workflow_id) | |||
links = get_linked_resources(workflow_id) | |||
return render_template('resource.html', resource=workflow, links=links) | |||
# route for editing a single workflow based on the ID in the database | |||
@workflow.route('/workflows/<int:workflow_id>/edit', methods=('GET', 'POST')) | |||
@login_required | |||
def edit_workflow(workflow_id): | |||
workflow = get_workflow(workflow_id) | |||
workflow = get_resource(workflow_id) | |||
if request.method == 'POST': | |||
name = request.form['name'] | |||
@@ -46,21 +41,17 @@ def edit_workflow(workflow_id): | |||
if not name: | |||
flash('Name is required!') | |||
else: | |||
workflow = Workflow.query.get(workflow_id) | |||
workflow = Resource.query.get(workflow_id) | |||
workflow.name = name | |||
workflow.description = description | |||
db.session.commit() | |||
return redirect(url_for('workflow.get_workflows')) | |||
return render_template('edit.html', workflow=workflow) | |||
return render_template('edit.html', resource=workflow) | |||
# route for function to delete a single workflow from the edit page | |||
@workflow.route('/workflows/<int:workflow_id>/delete', methods=('POST',)) | |||
@login_required | |||
def delete_workflow(workflow_id): | |||
workflow = get_workflow(workflow_id) | |||
deletion = Workflow.query.get(workflow_id) | |||
db.session.delete(deletion) | |||
db.session.commit() | |||
flash('Successfully deleted!') | |||
delete_resource(workflow_id) | |||
return redirect(url_for('workflow.get_workflows')) |