Browse Source

Init repo

Guillaume Subiron 12 years ago
commit
a9e03d3f11

+ 99 - 0
main.py

@@ -0,0 +1,99 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+
+from flask import Flask, request, session, g, redirect, url_for, abort, \
+    render_template, flash, jsonify 
+import sqlite3
+from datetime import date, time, timedelta, datetime
+import locale
+locale.setlocale(locale.LC_ALL, '')
+import string
+
+from settings import *
+
+app = Flask(__name__) 
+app.config.from_object(__name__)
+
+def connect_db():
+    return sqlite3.connect(app.config['DATABASE'])
+
+@app.before_request
+def before_request():
+    g.db = connect_db()
+    #g.db.execute("PRAGMA foreign_keys = ON")
+
+@app.teardown_request
+def teardown_request(exception):
+    g.db.close()
+
+@app.route('/')
+def home():
+    return render_template('index.html', active_button="home")
+
+def query_db(query, args=(), one=False):
+    cur = g.db.execute(query, args)
+    rv = [dict((cur.description[idx][0], value)
+        for idx, value in enumerate(row)) for row in cur.fetchall()]
+    return (rv[0] if rv else None) if one else rv
+
+def init_db():
+    with closing(connect_db()) as db:
+        with app.open_resource('schema.sql') as f:
+            db.cursor().executescript(f.read())
+        db.commit()
+
+@app.route('/members')
+def members():
+    members = query_db('select * from fai where is_member = 1')
+    return render_template('members.html', members=members)
+
+@app.route('/projects')
+def projects():
+    projects = list()
+    for project in query_db('select * from fai order by is_member,step,name'):
+        project['stepname'] = STEPS[project['step']]
+        projects.append(project)
+    return render_template('projects.html', projects=projects)
+
+@app.route('/fai/<projectid>')
+def project(projectid):
+    project = query_db('select * from fai where id = ?', (projectid), one=True) 
+    if project is None:
+        abort(404)
+    project['stepname'] = STEPS[project['step']]
+    return render_template('project.html', project=project)
+
+@app.route('/edit/<projectid>', methods=['GET', 'POST'])
+def edit_project(projectid):
+    project = query_db('select * from fai where id = ?', (projectid), one=True)
+    if project is None:
+        abort(404)
+    project['stepname'] = STEPS[project['step']]
+    if request.method == 'POST':
+        d.db.execute('update fai set name = ?, description = ? where id = ?', [request.form['name'], request.form['description'], projectid]) 
+        g.db.commit()
+    return render_template('edit_project.html', project=project)
+
+@app.route('/create/<projectid>')
+def create_project(projectid):
+    abort(404) # TODO
+
+@app.route('/api/<projects>.json')
+def projects_json(projects):
+    if projects == 'projects':
+        query = 'select * from fai'
+    elif projects == 'members':
+        query = 'select * from fai where is_member = 1'
+    else:
+        abort(404)
+    fais = dict()
+    for fai in query_db(query):
+        fais[fai['name']] = fai
+    return jsonify(fais)
+
+#------
+# Main
+
+if __name__ == '__main__':
+    app.run()
+

+ 21 - 0
schema.sql

@@ -0,0 +1,21 @@
+drop table if exists fai;
+
+create table fai (
+    id INTEGER PRIMARY KEY AUTOINCREMENT,
+    name TEXT UNIQUE NOT NULL,
+    shortname TEXT UNIQUE NOT NULL,
+    zone TEXT NOT NULL,
+    gps TEXT,
+    description TEXT,
+    services TEXT,
+    website TEXT,
+    email TEXT,
+    irc_server TEXT,
+    irc_channel TEXT,
+    step INTEGER NOT NULL,
+    is_member BOOLEAN DEFAULT 0 NOT NULL, 
+    CHECK (is_member IN (0,1)) 
+);
+
+INSERT INTO fai VALUES (1, "Aquilenet", "Aquilenet", "Aquitaine", "10:10", "Fournisseur d'accès Internet en Aquitaine", "ADSL", "http://www.aquilenet.fr", "contact@aquilenet.fr", "freenode.net", "#aquilenet", 7, 1);
+INSERT INTO fai VALUES (2, "FaiMaison", "FaiMaison", "Nantes", "10:10", "", "ADSL", "http://faimaison.net/", "", "", "", 7, 1);

+ 13 - 0
settings.py

@@ -0,0 +1,13 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+
+DATABASE = '/tmp/cavote.db'
+#PASSWD_SALT = 'change this value to some random chars!'
+SECRET_KEY = '{J@uRKO,xO-PK7B,jF?>iHbxLasF9s#zjOoy=+:'
+DEBUG = True
+TITLE = u"Fédéral Database"
+#EMAIL = '"' + TITLE + '"' + ' <' + u"cavote@ffdn.org" + '>'
+#VERSION = "cavote 0.3.0"
+#SMTP_SERVER = "127.0.0.1"
+#PATTERNS = {u'Oui/Non': [u'Oui', u'Non'], u'Oui/Non/Blanc': [u'Oui', u'Non', u'Blanc'], u'Oui/Non/Peut-être': [u'Oui', u'Non', u'Peut-être']}
+STEPS = {1:u'Projet envisagé', 2:u'Porteurs du projet identifiés', 3:u'Structure en cours de création', 4:u'Structure constituée', 5:u'Outils de base créés (compte en banque, premiers adhérents)', 6:u'FAI opérationnel partiellement (premiers accès ouverts, p-e en mode dégradé)', 7:u'FAI pleinement opérationnel'}

File diff suppressed because it is too large
+ 1058 - 0
static/css/bootstrap-responsive.css


File diff suppressed because it is too large
+ 9 - 0
static/css/bootstrap-responsive.min.css


File diff suppressed because it is too large
+ 5774 - 0
static/css/bootstrap.css


File diff suppressed because it is too large
+ 9 - 0
static/css/bootstrap.min.css


+ 34 - 0
static/css/cavote.css

@@ -0,0 +1,34 @@
+.table-votes th {
+    text-align: right;
+}
+
+.table-votes input {
+    margin: 0;
+}
+
+.table-votes td {
+    text-align: center;
+}
+
+.table-votes .yes {
+    background-color: #46a546; /* green */
+    /*background-color: #049cdb;*/ /* blue */
+    color: white;
+    font-weight: bold;
+}
+
+.table-votes .no {
+    background-color: #9d261d; /* red */
+    color: white;
+    font-weight: bold;
+}
+
+.table-votes tr:hover .yes {
+    /*background-color: #60C160; [> green <]*/
+    background-color: #55ab55; /* green */
+    /*background-color: #049cdb;*/ /* blue */
+}
+
+.table-votes tr:hover .no {
+    background-color: #C73F38; /* red */
+}

+ 10 - 0
static/css/jquery.ui.accordion.css

@@ -0,0 +1,10 @@
+/* Accordion
+----------------------------------*/
+.ui-accordion .ui-accordion-header { cursor: pointer; position: relative; margin-top: 1px; zoom: 1; }
+.ui-accordion .ui-accordion-li-fix { display: inline; }
+.ui-accordion .ui-accordion-header-active { border-bottom: 0 !important; }
+.ui-accordion .ui-accordion-header a { display: block; font-size: 1em; padding: .5em .5em .5em .7em; }
+.ui-accordion-icons .ui-accordion-header a { padding-left: 2.2em; }
+.ui-accordion .ui-accordion-header .ui-icon { position: absolute; left: .5em; top: 50%; margin-top: -8px; }
+.ui-accordion .ui-accordion-content { padding: 1em 2.2em; border-top: 0; margin-top: -2px; position: relative; top: 1px; margin-bottom: 2px; overflow: auto; display: none; zoom: 1; }
+.ui-accordion .ui-accordion-content-active { display: block; }

+ 2 - 0
static/css/jquery.ui.all.css

@@ -0,0 +1,2 @@
+@import "jquery.ui.base.css";
+@import "jquery.ui.theme.css";

+ 35 - 0
static/css/jquery.ui.autocomplete.css

@@ -0,0 +1,35 @@
+/* Autocomplete
+----------------------------------*/
+.ui-autocomplete { position: absolute; cursor: default; }	
+.ui-autocomplete-loading { background: white url('images/ui-anim_basic_16x16.gif') right center no-repeat; }
+
+/* workarounds */
+* html .ui-autocomplete { width:1px; } /* without this, the menu expands to 100% in IE6 */
+
+/* Menu
+----------------------------------*/
+.ui-menu {
+	list-style:none;
+	padding: 2px;
+	margin: 0;
+	display:block;
+}
+.ui-menu .ui-menu {
+	margin-top: -3px;
+}
+.ui-menu .ui-menu-item {
+	margin:0;
+	padding: 0;
+	width: 100%;
+}
+.ui-menu .ui-menu-item a {
+	text-decoration:none;
+	display:block;
+	padding:.2em .4em;
+	line-height:1.5;
+	zoom:1;
+}
+.ui-menu .ui-menu-item a.ui-state-hover,
+.ui-menu .ui-menu-item a.ui-state-active {
+	margin: -1px;
+}

+ 10 - 0
static/css/jquery.ui.base.css

@@ -0,0 +1,10 @@
+@import url("jquery.ui.core.css");
+@import url("jquery.ui.resizable.css");
+@import url("jquery.ui.accordion.css");
+@import url("jquery.ui.autocomplete.css");
+@import url("jquery.ui.button.css");
+@import url("jquery.ui.dialog.css");
+@import url("jquery.ui.slider.css");
+@import url("jquery.ui.tabs.css");
+@import url("jquery.ui.datepicker.css");
+@import url("jquery.ui.progressbar.css");

+ 35 - 0
static/css/jquery.ui.button.css

@@ -0,0 +1,35 @@
+/* Button
+----------------------------------*/
+
+.ui-button { display: inline-block; position: relative; padding: 0; margin-right: .1em; text-decoration: none !important; cursor: pointer; text-align: center; zoom: 1; overflow: visible; } /* the overflow property removes extra width in IE */
+.ui-button-icon-only { width: 2.2em; } /* to make room for the icon, a width needs to be set here */
+button.ui-button-icon-only { width: 2.4em; } /* button elements seem to need a little more width */
+.ui-button-icons-only { width: 3.4em; } 
+button.ui-button-icons-only { width: 3.7em; } 
+
+/*button text element */
+.ui-button .ui-button-text { display: block; line-height: 1.4;  }
+.ui-button-text-only .ui-button-text { padding: .4em 1em; }
+.ui-button-icon-only .ui-button-text, .ui-button-icons-only .ui-button-text { padding: .4em; text-indent: -9999999px; }
+.ui-button-text-icon .ui-button-text, .ui-button-text-icons .ui-button-text { padding: .4em 1em .4em 2.1em; }
+.ui-button-text-icons .ui-button-text { padding-left: 2.1em; padding-right: 2.1em; }
+/* no icon support for input elements, provide padding by default */
+input.ui-button { padding: .4em 1em; }
+
+/*button icon element(s) */
+.ui-button-icon-only .ui-icon, .ui-button-text-icon .ui-icon, .ui-button-text-icons .ui-icon, .ui-button-icons-only .ui-icon { position: absolute; top: 50%; margin-top: -8px; }
+.ui-button-icon-only .ui-icon { left: 50%; margin-left: -8px; }
+.ui-button-text-icon .ui-button-icon-primary, .ui-button-text-icons .ui-button-icon-primary, .ui-button-icons-only .ui-button-icon-primary { left: .5em; }
+.ui-button-text-icons .ui-button-icon-secondary, .ui-button-icons-only .ui-button-icon-secondary { right: .5em; }
+
+/*button sets*/
+.ui-buttonset { margin-right: 7px; }
+.ui-buttonset .ui-button { margin-left: 0; margin-right: -.3em; }
+
+/* workarounds */
+button.ui-button::-moz-focus-inner { border: 0; padding: 0; } /* reset extra padding in Firefox */
+
+
+
+
+

+ 37 - 0
static/css/jquery.ui.core.css

@@ -0,0 +1,37 @@
+/*
+* jQuery UI CSS Framework
+* Copyright (c) 2010 AUTHORS.txt (http://jqueryui.com/about)
+* Dual licensed under the MIT (MIT-LICENSE.txt) and GPL (GPL-LICENSE.txt) licenses.
+*/
+
+/* Layout helpers
+----------------------------------*/
+.ui-helper-hidden { display: none; }
+.ui-helper-hidden-accessible { position: absolute; left: -99999999px; }
+.ui-helper-reset { margin: 0; padding: 0; border: 0; outline: 0; line-height: 1.3; text-decoration: none; font-size: 100%; list-style: none; }
+.ui-helper-clearfix:after { content: "."; display: block; height: 0; clear: both; visibility: hidden; }
+.ui-helper-clearfix { display: inline-block; }
+/* required comment for clearfix to work in Opera \*/
+* html .ui-helper-clearfix { height:1%; }
+.ui-helper-clearfix { display:block; }
+/* end clearfix */
+.ui-helper-zfix { width: 100%; height: 100%; top: 0; left: 0; position: absolute; opacity: 0; filter:Alpha(Opacity=0); }
+
+
+/* Interaction Cues
+----------------------------------*/
+.ui-state-disabled { cursor: default !important; }
+
+
+/* Icons
+----------------------------------*/
+
+/* states and images */
+.ui-icon { display: block; text-indent: -99999px; overflow: hidden; background-repeat: no-repeat; }
+
+
+/* Misc visuals
+----------------------------------*/
+
+/* Overlays */
+.ui-widget-overlay { position: absolute; top: 0; left: 0; width: 100%; height: 100%; }

+ 61 - 0
static/css/jquery.ui.datepicker.css

@@ -0,0 +1,61 @@
+/* Datepicker
+----------------------------------*/
+.ui-datepicker { width: 17em; padding: .2em .2em 0; }
+.ui-datepicker .ui-datepicker-header { position:relative; padding:.2em 0; }
+.ui-datepicker .ui-datepicker-prev, .ui-datepicker .ui-datepicker-next { position:absolute; top: 2px; width: 1.8em; height: 1.8em; }
+.ui-datepicker .ui-datepicker-prev-hover, .ui-datepicker .ui-datepicker-next-hover { top: 1px; }
+.ui-datepicker .ui-datepicker-prev { left:2px; }
+.ui-datepicker .ui-datepicker-next { right:2px; }
+.ui-datepicker .ui-datepicker-prev-hover { left:1px; }
+.ui-datepicker .ui-datepicker-next-hover { right:1px; }
+.ui-datepicker .ui-datepicker-prev span, .ui-datepicker .ui-datepicker-next span { display: block; position: absolute; left: 50%; margin-left: -8px; top: 50%; margin-top: -8px;  }
+.ui-datepicker .ui-datepicker-title { margin: 0 2.3em; line-height: 1.8em; text-align: center; }
+.ui-datepicker .ui-datepicker-title select { font-size:1em; margin:1px 0; }
+.ui-datepicker select.ui-datepicker-month-year {width: 100%;}
+.ui-datepicker select.ui-datepicker-month, 
+.ui-datepicker select.ui-datepicker-year { width: 49%;}
+.ui-datepicker table {width: 100%; font-size: .9em; border-collapse: collapse; margin:0 0 .4em; }
+.ui-datepicker th { padding: .7em .3em; text-align: center; font-weight: bold; border: 0;  }
+.ui-datepicker td { border: 0; padding: 1px; }
+.ui-datepicker td span, .ui-datepicker td a { display: block; padding: .2em; text-align: right; text-decoration: none; }
+.ui-datepicker .ui-datepicker-buttonpane { background-image: none; margin: .7em 0 0 0; padding:0 .2em; border-left: 0; border-right: 0; border-bottom: 0; }
+.ui-datepicker .ui-datepicker-buttonpane button { float: right; margin: .5em .2em .4em; cursor: pointer; padding: .2em .6em .3em .6em; width:auto; overflow:visible; }
+.ui-datepicker .ui-datepicker-buttonpane button.ui-datepicker-current { float:left; }
+
+/* with multiple calendars */
+.ui-datepicker.ui-datepicker-multi { width:auto; }
+.ui-datepicker-multi .ui-datepicker-group { float:left; }
+.ui-datepicker-multi .ui-datepicker-group table { width:95%; margin:0 auto .4em; }
+.ui-datepicker-multi-2 .ui-datepicker-group { width:50%; }
+.ui-datepicker-multi-3 .ui-datepicker-group { width:33.3%; }
+.ui-datepicker-multi-4 .ui-datepicker-group { width:25%; }
+.ui-datepicker-multi .ui-datepicker-group-last .ui-datepicker-header { border-left-width:0; }
+.ui-datepicker-multi .ui-datepicker-group-middle .ui-datepicker-header { border-left-width:0; }
+.ui-datepicker-multi .ui-datepicker-buttonpane { clear:left; }
+.ui-datepicker-row-break { clear:both; width:100%; }
+
+/* RTL support */
+.ui-datepicker-rtl { direction: rtl; }
+.ui-datepicker-rtl .ui-datepicker-prev { right: 2px; left: auto; }
+.ui-datepicker-rtl .ui-datepicker-next { left: 2px; right: auto; }
+.ui-datepicker-rtl .ui-datepicker-prev:hover { right: 1px; left: auto; }
+.ui-datepicker-rtl .ui-datepicker-next:hover { left: 1px; right: auto; }
+.ui-datepicker-rtl .ui-datepicker-buttonpane { clear:right; }
+.ui-datepicker-rtl .ui-datepicker-buttonpane button { float: left; }
+.ui-datepicker-rtl .ui-datepicker-buttonpane button.ui-datepicker-current { float:right; }
+.ui-datepicker-rtl .ui-datepicker-group { float:right; }
+.ui-datepicker-rtl .ui-datepicker-group-last .ui-datepicker-header { border-right-width:0; border-left-width:1px; }
+.ui-datepicker-rtl .ui-datepicker-group-middle .ui-datepicker-header { border-right-width:0; border-left-width:1px; }
+
+/* IE6 IFRAME FIX (taken from datepicker 1.5.3 */
+.ui-datepicker-cover {
+    display: none; /*sorry for IE5*/
+    display/**/: block; /*sorry for IE5*/
+    position: absolute; /*must have*/
+    z-index: -1; /*must have*/
+    filter: mask(); /*must have*/
+    top: -4px; /*must have*/
+    left: -4px; /*must have*/
+    width: 200px; /*must have*/
+    height: 200px; /*must have*/
+}

+ 13 - 0
static/css/jquery.ui.dialog.css

@@ -0,0 +1,13 @@
+/* Dialog
+----------------------------------*/
+.ui-dialog { position: absolute; padding: .2em; width: 300px; overflow: hidden; }
+.ui-dialog .ui-dialog-titlebar { padding: .5em 1em .3em; position: relative;  }
+.ui-dialog .ui-dialog-title { float: left; margin: .1em 16px .2em 0; } 
+.ui-dialog .ui-dialog-titlebar-close { position: absolute; right: .3em; top: 50%; width: 19px; margin: -10px 0 0 0; padding: 1px; height: 18px; }
+.ui-dialog .ui-dialog-titlebar-close span { display: block; margin: 1px; }
+.ui-dialog .ui-dialog-titlebar-close:hover, .ui-dialog .ui-dialog-titlebar-close:focus { padding: 0; }
+.ui-dialog .ui-dialog-content { border: 0; padding: .5em 1em; background: none; overflow: auto; zoom: 1; }
+.ui-dialog .ui-dialog-buttonpane { text-align: left; border-width: 1px 0 0 0; background-image: none; margin: .5em 0 0 0; padding: .3em 1em .5em .4em; }
+.ui-dialog .ui-dialog-buttonpane button { float: right; margin: .5em .4em .5em 0; cursor: pointer; padding: .2em .6em .3em .6em; line-height: 1.4em; width:auto; overflow:visible; }
+.ui-dialog .ui-resizable-se { width: 14px; height: 14px; right: 3px; bottom: 3px; }
+.ui-draggable .ui-dialog-titlebar { cursor: move; }

+ 4 - 0
static/css/jquery.ui.progressbar.css

@@ -0,0 +1,4 @@
+/* Progressbar
+----------------------------------*/
+.ui-progressbar { height:2em; text-align: left; }
+.ui-progressbar .ui-progressbar-value {margin: -1px; height:100%; }

+ 13 - 0
static/css/jquery.ui.resizable.css

@@ -0,0 +1,13 @@
+/* Resizable
+----------------------------------*/
+.ui-resizable { position: relative;}
+.ui-resizable-handle { position: absolute;font-size: 0.1px;z-index: 99999; display: block;}
+.ui-resizable-disabled .ui-resizable-handle, .ui-resizable-autohide .ui-resizable-handle { display: none; }
+.ui-resizable-n { cursor: n-resize; height: 7px; width: 100%; top: -5px; left: 0; }
+.ui-resizable-s { cursor: s-resize; height: 7px; width: 100%; bottom: -5px; left: 0; }
+.ui-resizable-e { cursor: e-resize; width: 7px; right: -5px; top: 0; height: 100%; }
+.ui-resizable-w { cursor: w-resize; width: 7px; left: -5px; top: 0; height: 100%; }
+.ui-resizable-se { cursor: se-resize; width: 12px; height: 12px; right: 1px; bottom: 1px; }
+.ui-resizable-sw { cursor: sw-resize; width: 9px; height: 9px; left: -5px; bottom: -5px; }
+.ui-resizable-nw { cursor: nw-resize; width: 9px; height: 9px; left: -5px; top: -5px; }
+.ui-resizable-ne { cursor: ne-resize; width: 9px; height: 9px; right: -5px; top: -5px;}

+ 17 - 0
static/css/jquery.ui.slider.css

@@ -0,0 +1,17 @@
+/* Slider
+----------------------------------*/
+.ui-slider { position: relative; text-align: left; }
+.ui-slider .ui-slider-handle { position: absolute; z-index: 2; width: 1.2em; height: 1.2em; cursor: default; }
+.ui-slider .ui-slider-range { position: absolute; z-index: 1; font-size: .7em; display: block; border: 0; background-position: 0 0; }
+
+.ui-slider-horizontal { height: .8em; }
+.ui-slider-horizontal .ui-slider-handle { top: -.3em; margin-left: -.6em; }
+.ui-slider-horizontal .ui-slider-range { top: 0; height: 100%; }
+.ui-slider-horizontal .ui-slider-range-min { left: 0; }
+.ui-slider-horizontal .ui-slider-range-max { right: 0; }
+
+.ui-slider-vertical { width: .8em; height: 100px; }
+.ui-slider-vertical .ui-slider-handle { left: -.3em; margin-left: 0; margin-bottom: -.6em; }
+.ui-slider-vertical .ui-slider-range { left: 0; width: 100%; }
+.ui-slider-vertical .ui-slider-range-min { bottom: 0; }
+.ui-slider-vertical .ui-slider-range-max { top: 0; }

+ 11 - 0
static/css/jquery.ui.tabs.css

@@ -0,0 +1,11 @@
+/* Tabs
+----------------------------------*/
+.ui-tabs { position: relative; padding: .2em; zoom: 1; } /* position: relative prevents IE scroll bug (element with position: relative inside container with overflow: auto appear as "fixed") */
+.ui-tabs .ui-tabs-nav { margin: 0; padding: .2em .2em 0; }
+.ui-tabs .ui-tabs-nav li { list-style: none; float: left; position: relative; top: 1px; margin: 0 .2em 1px 0; border-bottom: 0 !important; padding: 0; white-space: nowrap; }
+.ui-tabs .ui-tabs-nav li a { float: left; padding: .5em 1em; text-decoration: none; }
+.ui-tabs .ui-tabs-nav li.ui-tabs-selected { margin-bottom: 0; padding-bottom: 1px; }
+.ui-tabs .ui-tabs-nav li.ui-tabs-selected a, .ui-tabs .ui-tabs-nav li.ui-state-disabled a, .ui-tabs .ui-tabs-nav li.ui-state-processing a { cursor: text; }
+.ui-tabs .ui-tabs-nav li a, .ui-tabs.ui-tabs-collapsible .ui-tabs-nav li.ui-tabs-selected a { cursor: pointer; } /* first selector in group seems obsolete, but required to overcome bug in Opera applying cursor: text overall if defined elsewhere... */
+.ui-tabs .ui-tabs-panel { display: block; border: 0; padding: 1em 1.4em; background: none; }
+.ui-tabs .ui-tabs-hide { display: none !important; }

File diff suppressed because it is too large
+ 247 - 0
static/css/jquery.ui.theme.css


BIN
static/img/glyphicons-halflings-white.png


BIN
static/img/glyphicons-halflings.png


BIN
static/img/icon-cog.png


File diff suppressed because it is too large
+ 2027 - 0
static/js/bootstrap.js


File diff suppressed because it is too large
+ 6 - 0
static/js/bootstrap.min.js


File diff suppressed because it is too large
+ 9252 - 0
static/js/jquery.js


+ 63 - 0
templates/edit_project.html

@@ -0,0 +1,63 @@
+{% extends "layout.html" %}
+{% block body %}
+
+<div class="row">
+  <div class="span6 well">
+    <form action="{{ url_for('edit_project', projectid=project.id) }}" method="post" class="form-horizontal">
+      <fieldset><legend>Édition du projet</legend>
+        <div class="control-group">
+          <label class="control-label" for="name">Nom</label>
+          <div class="controls">
+            <input type="text" size=30 name="name" id="name" value="{{ project.name }}" />
+            <span class="help-inline"><font color="red">*</font></span>
+          </div>
+        </div>
+        <div class="control-group">
+          <label class="control-label" for="description">Description</label>
+          <div class="controls">
+            <input type="description" size=50 name="description" id="description" value="{{ project.description }}"></input>
+          </div>
+        </div>
+
+        <div class="form-actions">
+          <input type="submit" class="btn btn-primary" value="Enregistrer" />
+          <input type="reset" class="btn" value="Annuler" />
+        </div>
+      </fieldset>
+    </form>
+  </div>
+
+  <div class="span5 well pull-right">
+    <fieldset><legend>Pièces jointes</legend>
+      <table class="table table-stripped table-condensed">
+        <thead>
+          <tr>
+            <th>Lien
+            <th>Actions
+          </tr>
+        </thead>
+        <tbody>
+        {% for attachment in attachments %}
+          <tr>
+            <td>{{ attachment.url }}</td>
+            <td><a href="" class="btn btn-small btn-danger">Supprimer</a></td>
+          </tr>
+        {% endfor %}
+        </tbody>
+        <tfoot>
+          <tr>
+            <form action="" method="post">
+              <td><input type="text" name="url" value="Nouveau document" 
+                onfocus="if(this.value=='Nouveau document')this.value='';"
+                onblur="if(this.value=='')this.value='Nouveau document';" /></td>
+              <td><input type="submit" class="btn btn-small btn-primary" value="+ Ajouter" />
+            </form>
+          </tr>
+        </tfoot>
+      </table>
+    </fieldset>
+  </div>
+
+</div>
+
+{% endblock %}

+ 9 - 0
templates/index.html

@@ -0,0 +1,9 @@
+{% extends "layout.html" %}
+{% block body %}
+  {% if error %}<p class=error><strong>Error:</strong> {{ error }}{% endif %}
+  <p>
+  <ul>
+    <li><a href="/members">Liste des membres de la fédération</a> (<a href="/api/members.json">JSON</a>)</li>
+    <li><a href="/projects">Liste des projets recencés</a> (<a href="/api/projects.json">JSON</a>)</li>
+  </p>
+{% endblock %}

+ 45 - 0
templates/layout.html

@@ -0,0 +1,45 @@
+<!doctype html>
+<html lang="fr">
+  <head>
+    <meta charset="utf-8">
+    <title>CA vote ou pas </title>
+    <!-- meta -->
+    <!-- icon
+    <link rel="shortcut icon" href="favicon.ico"> -->
+    <!-- ma template.css -->
+    <link rel=stylesheet type=text/css href="{{ url_for('static', filename='css/bootstrap.css') }}">
+    <!--<link rel=stylesheet type=text/css href="{{ url_for('static', filename='css/cavote.css') }}">-->
+    <!-- css javascript -->
+    <link rel=stylesheet type=text/css href="{{ url_for('static', filename='css/jquery.ui.all.css') }}">
+    <!-- javascript -->
+  </head>
+<body>
+
+<div class="container-fluid">
+
+<h1 class="page-header"><a href="/">Fédéral Database</a> <small>{% block subtitle %}{% endblock %}</small></h1>
+{% with messages = get_flashed_messages(with_categories="true") %}
+  {% if messages %}
+    {% for category, message in messages %}
+    <div class="alert alert-{{ category }} fade in">
+      <button class="close" data-dismiss="alert">×</button>
+      {{ message }}
+    </div>
+    {% endfor %}
+  {% endif %}
+{% endwith %}
+
+<div class="container">
+{% block body %}{% endblock %}
+</div>
+
+</div> <!-- container -->   
+  <script src="{{ url_for('static', filename='js/jquery.js') }}"></script>
+  <script src="{{ url_for('static', filename='js/bootstrap.js') }}"></script>
+  <script type="text/javascript">
+    $(document).ready(function () {
+      $("[rel=tooltip]").tooltip();
+    });
+  </script>
+</body>
+</html>

+ 13 - 0
templates/members.html

@@ -0,0 +1,13 @@
+{% extends "layout.html" %}
+{% block subtitle %}
+Liste des membres de la Fédération FDN
+{% endblock %}
+{% block body %}
+  {% for member in members %}
+  <div class="well">
+    {{ member.name }}
+  </div>
+  {% else %}
+  <div class="alert">Il n'y a aucun membre. Désolé.</div>
+  {% endfor %}
+{% endblock %}

+ 21 - 0
templates/project.html

@@ -0,0 +1,21 @@
+{% extends "layout.html" %}
+{% block subtitle %}
+{% endblock %}
+{% block body %}
+<!--<div class="row">-->
+<!--<div class="span9">-->
+  <a class="pull-right btn btn-success btn-small" href="{{ url_for('edit_project', projectid=project.id) }}"><i class="icon-edit icon-white"></i> Éditer</a>
+  {% if project.name != project.shortname %}
+  <h2 class='page-header'>{{ project.name }} ({{ project.shortname }})</h2> 
+  {% else %}
+  <h2 class='page-header'>{{ project.name }} <small> &nbsp;-&nbsp; {{ project.description }}</small></h2> 
+  {% endif %}
+  {{ project }}
+  <dl class="dl-horizontal">
+    <dt>Website<dd><a href="{{ project.website }}">{{ project.website }}</a>
+    <dt>Email<dd>{{ project.email }}
+    <dt>IRC<dd>Canal {{ project.irc_channel }}, Serveur {{ project.irc_server }}
+    <dt>Étape<dd>{{ project.stepname }}
+<!--</div>-->
+<!--</div>-->
+{% endblock %}

+ 29 - 0
templates/projects.html

@@ -0,0 +1,29 @@
+{% extends "layout.html" %}
+{% block subtitle %}
+Liste des projets recencés
+{% endblock %}
+{% block body %}
+<div>
+<table class="table">
+  <thead>
+    <tr>
+      <th>Nom</th>
+      <th>Zone</th>
+      <th>Étape</th>
+      <th></th>
+    </tr>
+  </thead>
+  <tbody>
+    {% for project in projects %}
+    <tr>
+      <td>{{ project.name }}</td>
+      <td>{{ project.zone }}</td>
+      <td><a href="#" rel="tooltip" data-placement="right" title="{{ project.stepname }}">{{ project.step }}</a></td>
+      <td><a class="pull-right btn btn-small" href="{{ url_for('project', projectid=project.id) }}"><i class="icon-search"></i></a>
+    </tr>
+    {% endfor %}
+  </tbody>
+</table>
+<a class="pull-right btn btn-primary btn-small" href="">Ajoutez le votre !</a>
+</div>
+{% endblock %}