changeset 11:7a573ec679a6

added more files, can now display charts a bit
author sean
date Tue, 04 Aug 2015 14:23:53 +0200
parents d71f39618d6f
children 50f4c64834cb
files dash.conf doc/connect_with_mon/bottledash.alert modules/roundup_cc/__init__.py modules/roundup_cc/collect_issues.py modules/roundup_cc/display_issues.py modules/roundup_cc/graph.html modules/roundup_cc/roundup_content_data/__init__.py views/hello_template.tpl
diffstat 8 files changed, 835 insertions(+), 21 deletions(-) [+]
line wrap: on
line diff
--- a/dash.conf	Wed Jul 29 12:27:26 2015 +0200
+++ b/dash.conf	Tue Aug 04 14:23:53 2015 +0200
@@ -61,16 +61,5 @@
 status=up
 
 [tile4]
-type=mon
-source=192.168.4.3
-status=up
-
-[tile5]
-type=mon
-source=192.168.4.3
-status=up
-
-[tile6]
-type=mon
-source=192.168.4.3
-status=up
+type=d3js
+status=modules/roundup-cc/display_issues._techintern.py
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/doc/connect_with_mon/bottledash.alert	Tue Aug 04 14:23:53 2015 +0200
@@ -0,0 +1,54 @@
+#!/usr/bin/perl
+#
+#
+# Sean Engelhardt, sean.engelhardt@intevation.de
+#
+#
+#    Copyright (C) 2015, Intevation
+#
+#    This program is free software; you can redistribute it and/or modify
+#    it under the terms of the GNU General Public License as published by
+#    the Free Software Foundation; either version 2 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 General Public License for more details.
+#
+#    You should have received a copy of the GNU General Public License
+#    along with this program; if not, write to the Free Software
+#    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+#
+
+#STD
+use Getopt::Std;
+
+#get LWP functionallity
+use LWP::UserAgent;
+
+#alert-status propbably? every Mon-alert uses that
+getopts ("s:g:h:t:l:u");
+
+#Creates a new LWP-use-agent
+my $ua = LWP::UserAgent->new;
+
+#defines the server-Endpoint. Usually the bottledash-server
+my $server_endpoint = "http://<IP_des_Bottledash_servers>:8080/updown";
+
+#determinates if the altert is an upalert or a "down"-alert
+$ALERT = $opt_u ? "UPALERT" : "ALERT";
+
+# set custom HTTP request header fields
+my $req = HTTP::Request->new(POST => $server_endpoint);
+$req->header('content-type' => 'application/json');
+$req->header('x-auth-token' => 'kfksj48sdfj4jd9d');
+
+# add POST data to HTTP request body
+my $post_data = '{ "server": $ALERT, "status": $opt_u }';
+$req->content($post_data);  
+
+#every-alert uses that. Dont know what that is
+while (<STDIN>) {
+    print;
+}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/modules/roundup_cc/__init__.py	Tue Aug 04 14:23:53 2015 +0200
@@ -0,0 +1,21 @@
+#!/usr/bin/env python
+
+""" supplys the data needed to comunicate with the roundup-server,
+and the sqlite database. Represents the types of errors used in roundup.
+
+author: Sascha L. Teichmann <sascha.teichmann@intevation.de>
+author: Bernhard Reiter <bernhard@intevation.de>
+author: Sean Engelhardt <sean.engelhardt@intevation.de>
+
+(c) 2010,2015 by Intevation GmbH
+
+This is Free Software unter the terms of the
+GNU GENERAL PUBLIC LICENSE Version 3 or later.
+See http://www.gnu.org/licenses/gpl-3.0.txt for details
+"""
+
+import roundup_cc.display_issues as display
+import roundup_cc.roundup_content_data as rcd
+
+def get_tech_intern_chart():
+    return display.render_db_stats_as_html(rcd.DATABASE_TECH_INTERN, rcd.SELECT_ALL)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/modules/roundup_cc/collect_issues.py	Tue Aug 04 14:23:53 2015 +0200
@@ -0,0 +1,158 @@
+#!/usr/bin/env python3
+
+""" Fetch issues from a roundup-tracker and save them in a databse.
+
+author: Sascha L. Teichmann <sascha.teichmann@intevation.de>
+author: Bernhard Reiter <bernhard@intevation.de>
+author: Sean Engelhardt <sean.engelhardt@intevation.de>
+
+(c) 2010,2015 by Intevation GmbH
+
+This is Free Software unter the terms of the
+GNU GENERAL PUBLIC LICENSE Version 3 or later.
+See http://www.gnu.org/licenses/gpl-3.0.txt for details
+
+
+##USAGE EXAMPLE: ##
+
+BASE_URL_DEMO = "http://localhost:8917/demo/"
+SEARCH_URL_DEMO = "issue?@action=export_csv&@columns=title,priority&@filter=status&@pagesize=50&@startwith=0&status=-1,1,2,3,4,5,6,7"
+
+LOGIN_PARAMETERS_DEMO = (
+    ("__login_name", "demo"),
+    ("__login_password", "demo"),
+    ("@action", "Login"),
+    )
+
+save_stats_in_db(LOGIN_PARAMETERS_DEMO, BASE_URL_DEMO, rcd.DATABASE_DEMO, rcd.COLUMNS, rcd.CREATE_DB, rcd.INSERT_NEW, SEARCH_URL_DEMO)
+"""
+
+import http.cookiejar
+import urllib.parse
+import urllib.request
+import csv
+import io
+import sqlite3 as db
+import os
+import roundup_cc.roundup_content_data as rcd
+
+
+CHECK_ROUNDUP_ORDER = "priority?@action=export_csv&@columns=id,order"
+CHECK_ROUNDUP_SEARCH_VALUES = "status?@action=export_csv&@columns=id&@filter=open&open=1"
+SEARCH_ROUNDUP = "issue?@action=export_csv&@columns=priority&@filter=status&@pagesize=500&@startwith=0&status=-1,{search_values}"
+
+
+def connect_to_server(params, baseurl):
+    enc_data = urllib.parse.urlencode(params).encode()
+    cj = http.cookiejar.CookieJar()
+    opener = urllib.request.build_opener(urllib.request.HTTPCookieProcessor(cj))
+    req = urllib.request.Request(url=baseurl, data=enc_data)
+    opener.open(req)
+    return opener
+
+
+def get_csv_from_server(opener, roundup_url, sub_url):
+    csv_req = urllib.request.Request(url=roundup_url+sub_url)
+    f = opener.open(csv_req)
+    csv_reader = csv.DictReader(io.TextIOWrapper(f))
+    return csv_reader
+
+
+def set_search_paramters_on_URL(url, search_param_csv):
+
+    id_list = []
+
+    for row in search_param_csv:
+        id_list.append(row["id"])
+
+    new_url = url.format(search_values = ",".join(id_list))
+
+    return new_url
+
+
+def check_create_database(database_file, sql_create_db):
+    if not os.path.isfile(database_file):
+        con = None
+        cur = None
+        try:
+            con = db.connect(database_file)
+            cur = con.cursor()
+            try:
+                cur.execute(sql_create_db)
+                con.commit()
+                os.chmod(database_file, 0o644)
+            except:
+                con.rollback()
+                raise
+        finally:
+            if cur:
+                cur.close()
+            if con:
+                con.close()
+
+
+def issues_to_quantities(issue_csv, columns, orders_csv):
+
+    quantities = [0] * len(columns)
+    order_dict = {}
+
+    #convert the csv-dict reader to real dict
+    for row in orders_csv:
+        order_dict[row["id"]] = int(float(row["order"])) # int(float()) because the order-value is indeed "1.0, 2.0" etc
+
+    for issue in issue_csv:
+        priority = issue["priority"]
+
+        if priority.isdigit() == True :
+            quantities[order_dict[priority] -1 ] += 1
+
+    # print("quantities : " + str(quantities))
+
+    return quantities
+
+
+def save_issues_to_db(quantities, database_file, sql_create_db, sql_insert_in_db):
+    check_create_database(database_file, sql_create_db)
+
+    cur = None
+    con = None
+
+    try:
+        con = db.connect(database_file)
+        cur = con.cursor()
+        try:
+            cur.execute(sql_insert_in_db, quantities)
+            con.commit()
+        except:
+            con.rollback()
+            raise
+    finally:
+        if cur:
+            cur.close()
+        if con:
+            con.close()
+
+
+def save_stats_in_db(login_parmeters, baseurl, db_file, columns, sql_create_db, sql_insert_in_db, searchurl=False):
+    try:
+
+        opener = connect_to_server(login_parmeters, baseurl)
+
+        search_operators_csv = get_csv_from_server(opener, baseurl, CHECK_ROUNDUP_SEARCH_VALUES)
+        order_csv = get_csv_from_server(opener, baseurl, CHECK_ROUNDUP_ORDER)
+
+        if searchurl == False:
+            formated_search_url = set_search_paramters_on_URL(SEARCH_ROUNDUP, search_operators_csv)
+        else:
+            formated_search_url = searchurl
+
+        current_issues_csv = get_csv_from_server(opener, baseurl, formated_search_url)
+
+        opener.close()
+
+        quantities = issues_to_quantities(current_issues_csv, columns, order_csv)
+
+        save_issues_to_db(quantities, db_file, sql_create_db, sql_insert_in_db)
+
+    except urllib.error.URLError as e:
+        print("No Valid Connection to server : " + baseurl + "\nerror: " + str(e))
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/modules/roundup_cc/display_issues.py	Tue Aug 04 14:23:53 2015 +0200
@@ -0,0 +1,98 @@
+#!/usr/bin/env python3
+
+""" Display previously saved issues from a database on webpage via CGI.
+
+author: Sascha L. Teichmann <sascha.teichmann@intevation.de>
+author: Bernhard Reiter <bernhard@intevation.de>
+author: Sean Engelhardt <sean.engelhardt@intevation.de>
+
+(c) 2010,2015 by Intevation GmbH
+
+This is Free Software unter the terms of the
+GNU GENERAL PUBLIC LICENSE Version 3 or later.
+See http://www.gnu.org/licenses/gpl-3.0.txt for details
+
+
+##Usage Example: ##
+
+render_db_stats_as_html(rcd.DATABASE_DEMO, rcd.SELECT_ALL)
+"""
+
+import sqlite3 as db
+import cgitb, os, sys
+import roundup_cc.roundup_content_data as rcd
+
+PATH = os.path.abspath(os.path.dirname(sys.argv[0]))
+HTML_DATA = "graph.html"
+PATH_TO_HTML = PATH + "/modules/roundup_cc/" + HTML_DATA
+
+def make_js_object_string(array):
+    formated = []
+
+    for item in array:
+        formated.append("{points: " + str(item) + "}")
+
+    return ",".join(formated)
+
+
+def make_js_object_date(array):
+    formated = []
+
+    for item in array:
+        formated.append("{date : new Date('" + str(item) + "')}")
+
+    return ", ".join(formated)
+
+
+def get_webpage():
+
+    with open(PATH_TO_HTML, "r") as html_chart_file:
+        base_html_data = html_chart_file.read()
+
+    base_html_data = (base_html_data
+        .replace("var critical=[];", "var critical=[" + make_js_object_string(rcd.data_dict["critical"]) + "]")
+        .replace("var urgent=[];", "var urgent=[" + make_js_object_string(rcd.data_dict["urgent"]) + "]")
+        .replace("var bug=[];", "var bug=[" + make_js_object_string(rcd.data_dict["bug"]) + "]")
+        .replace("var feature=[];", "var feature=[" + make_js_object_string(rcd.data_dict["feature"]) + "]")
+        .replace("var wish=[];", "var wish=[" + make_js_object_string(rcd.data_dict["wish"]) + "]")
+        .replace("var timestamp=[];", "var timestamp=[" + make_js_object_date(rcd.data_dict["date"]) + "]"))
+
+    return base_html_data
+
+
+# def render_webpage(content):
+#     webpage_string = ""
+#     for line in content.split("\n"):
+#         print(line)
+
+
+def render_db_stats_as_html(db_file, sql_select):
+
+    con = None
+    cur = None
+
+    try:
+        con = db.connect(db_file)
+        cur = con.cursor()
+        cur.execute(sql_select)
+
+        for row in cur.fetchall():
+            rcd.data_dict["date"].append(row[0])
+            rcd.data_dict["critical"].append(row[1])
+            rcd.data_dict["urgent"].append(row[2])
+            rcd.data_dict["bug"].append(row[3])
+            rcd.data_dict["feature"].append(row[4])
+            rcd.data_dict["wish"].append(row[5])
+    finally:
+        if cur:
+            cur.close()
+        if con:
+            con.close()
+
+    # render_webpage(get_webpage())
+    # print(get_webpage())
+    return get_webpage()
+
+# cgitb.enable()
+# print("Content-Type: text/html")
+# print()
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/modules/roundup_cc/graph.html	Tue Aug 04 14:23:53 2015 +0200
@@ -0,0 +1,408 @@
+<style type = text/css>
+
+	* {
+		font-family: "Sans-serif";
+		font-size: 14px;
+	}
+
+	.svg div{
+			font: 10px;
+			text-align: right;
+			float: left;
+			display: block;
+			padding: 10px;
+			margin: 10px;
+			color: white;
+	}
+
+	.axis path,
+
+	.axis line {
+			fill: none;
+			stroke: lightgrey;
+			/*opacity: 0.7;*/
+			stroke-width: 1px;
+	}
+
+	.y.axis path {
+	  display: none;
+	}
+
+	.line {
+			fill: none;
+			stroke-width: 3px;
+			opacity: 1;
+	}
+
+	.line.critical {
+			stroke: red;
+	}
+
+	.line.critical.legend {
+			fill: red;
+	}
+
+	.line.urgent {
+			stroke: orange;
+	}
+
+	.line.urgent.legend {
+			fill: orange;
+	}
+
+	.line.bug {
+			stroke: violet;
+	}
+
+	.line.bug.legend {
+			fill: violet;
+	}
+
+	.line.feature {
+			stroke: chartreuse;
+			style: stroke-dasharray;
+	}
+
+	.line.feature.legend {
+			fill: chartreuse;
+	}
+
+	.line.wish {
+			stroke: blue;
+	}
+
+	.line.wish.legend {
+			fill: blue;
+	}
+
+	.grid .tick {
+			stroke: lightgrey;
+			/*opacity: 0.7;*/
+	}
+
+	.grid path {
+			stroke-width: 0;
+	}
+
+</style>
+
+<!-- <div id="content" style="display: inline-block"></div> -->
+<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.6/d3.min.js" charset="utf-8"></script>
+<script type="text/javascript">
+
+	// window.onresize = function(){
+	// 	document.getElementsByClassName("chart")[0].innerHTML = "";
+	// 	makeChart();
+	// };
+
+	var critical=[];
+	
+
+	// var critical=[
+	// 		{points: 4},
+	// 		{points: 12},
+	// 		{points: 8},
+	// 		{points: 2}
+	// 	]
+	//
+	// var urgent=[
+	// 		{points: 3},
+	// 		{points: 24},
+	// 		{points: 17},
+	// 		{points: 19}
+	// 	]
+	//
+	// var bug=[
+	// 		{points: 10},
+	// 		{points: 2},
+	// 		{points: 2},
+	// 		{points: 12}
+	// 	]
+	//
+	// var feature=[
+	// 		{points: 4},
+	// 		{points: 21},
+	// 		{points: 12},
+	// 		{points: 4}
+	// 	]
+	//
+	// var wish=[
+	// 		{points: 22},
+	// 		{points: 18},
+	// 		{points: 32},
+	// 		{points: 10}
+	// 	]
+	//
+	//
+	// var timestamp=[
+	// 		{date : new Date('2015-06-30T12:36:47')},
+	// 		{date : new Date('2015-07-01T12:37:26')},
+	// 		{date : new Date('2015-07-02T12:38:26')},
+	// 		{date : new Date('2015-07-03T12:39:26')}
+	// 	]
+
+
+
+	document.addEventListener("DOMContentLoaded", function(event) {
+		makeChart();
+	});
+
+	function assignIssueToDate(issueArray, dateArray){
+		a = [];
+		for (var i = 0; i < issueArray.length; i++) {
+			a.push({points: issueArray[i].points, date : dateArray[i].date});
+		}
+
+		return a;
+	}
+
+	function limitDatesOnXAxis(limit){
+		if (timestamp.length < limit){
+			return timestamp.length;
+		} else {
+			return limit;
+		}
+	}
+
+	function maxInObject( array ){
+		var maxVal = 0;
+		for (var i = 0; i < array.length; i++) {
+			if (maxVal < array[i].points){
+				maxVal = array[i].points;
+			}
+		}
+		return maxVal;
+	}
+
+
+	function getMaxIssues(){
+		maxIssuesOfAllArrays = [];
+		maxIssuesOfAllArrays.push(maxInObject(critical));
+		maxIssuesOfAllArrays.push(maxInObject(urgent));
+		maxIssuesOfAllArrays.push(maxInObject(bug));
+		maxIssuesOfAllArrays.push(maxInObject(feature));
+		maxIssuesOfAllArrays.push(maxInObject(wish));
+
+		return Math.max.apply(Math, maxIssuesOfAllArrays)+1;
+	}
+
+
+	function dayDifference(first, second) {
+		"use strict";
+		var difference = (second - first) / (1000 * 60 * 60 * 24);
+
+		// just to avoid the get thousands of lines... would look ugly.
+		if (difference > 60){
+			difference = 60;
+		}
+
+		return difference;
+	}
+
+
+	// function for the grid lines
+	function makeGrid(direction, orientation, ticknumber) {
+		return d3.svg.axis()
+			.scale(direction)
+			.orient(orientation)
+			.ticks( ticknumber );
+	}
+
+
+	//append a svg_path. pretty generic
+	function draw_line(svg, data_array, css_class, line_object, lineShape){
+		svg.append("path")
+			.datum(assignIssueToDate(data_array, timestamp))
+			.attr("class", css_class)
+			.style("stroke-dasharray", (lineShape))
+			.attr("d", line_object);
+	}
+
+
+	function makeLegend(svg, width){
+
+		var legend_distance = width+40;
+		var top_distance = 20;
+		var distance_steps = 50;
+
+
+		function set_propper_distance(steps){
+			top_distance += steps;
+			return top_distance;
+		}
+
+		function draw_legend_line(svg, width, Ypos, text, issues){
+			svg.append("svg:text")
+				.attr("class", "legend")
+				.attr("x", width-30	)
+				.attr("y", Ypos)
+				.text(text + ":");
+
+			svg.append("svg:text")
+				.attr("class", "legend")
+				.attr("x", width+35	)
+				.attr("y", Ypos)
+				.text(issues);
+
+			svg.append("rect")
+				.attr("class", "line " + text.toLowerCase() + " legend")
+				.attr("x", width-30)
+				.attr("y", Ypos-20)
+				.attr("width", 100)
+				.attr("height", 2);
+		}
+
+		draw_legend_line(svg, legend_distance, set_propper_distance(distance_steps), "Critical", critical[critical.length-1].points);
+		draw_legend_line(svg, legend_distance, set_propper_distance(distance_steps), "Urgent", urgent[urgent.length-1].points);
+		draw_legend_line(svg, legend_distance, set_propper_distance(distance_steps), "Bug", bug[bug.length-1].points);
+		draw_legend_line(svg, legend_distance, set_propper_distance(distance_steps), "Feature", feature[feature.length-1].points);
+		draw_legend_line(svg, legend_distance, set_propper_distance(distance_steps), "Wish", wish[wish.length-1].points);
+	}
+
+
+
+	//draw the chart
+	function makeChart(){
+
+		//declaration
+		var sizeOfSystemBorders = 20;
+		// var margin = {top: 20, right: 100, bottom: 90, left: 60};
+		// var margin = {top: 0, right: 0, bottom: 0, left: 0}
+
+		var width = document.getElementsByClassName("chart")[0].clientWidth;
+		var height = document.getElementsByClassName("chart")[0].clientHeight;
+		// var	width = (document.documentElement.clientWidth-sizeOfSystemBorders) - margin.left - margin.right;
+		// var	height = (document.documentElement.clientHeight-sizeOfSystemBorders) - margin.top - margin.bottom;
+
+		var x = d3.time.scale()
+			.range([0, width]);
+
+		var y = d3.scale.linear()
+			.range([height, 0]);
+
+		var base_line = d3.svg.line()
+			.x(function(d) { return x(d.date); })
+			.y(function(d) { return y(d.points); });
+
+		//lines
+		var criticalLine = base_line;
+		var urgentLine = base_line;
+		var bugLine = base_line;
+		var featureLine = base_line;
+		var wishLine = base_line;
+		var timestampLine = base_line;
+
+
+		//set domain of y axis
+		var yDomain = [	];
+		yDomain[0] = 0;
+		yDomain[1] = getMaxIssues();
+		y.domain(d3.extent(yDomain, function(d){return d; }));
+
+		//set domain of y axis
+		x.domain(d3.extent(timestamp, function(d){return d.date; }));
+
+
+		var xAxis = d3.svg.axis()
+			.scale(x)
+			.orient("bottom")
+			.ticks(limitDatesOnXAxis(10))
+			.tickFormat(d3.time.format("%d.%m"));
+			// .tickFormat(d3.time.format("%d.%m:%H:%M"));
+			// .tickFormat(d3.time.format("%X"));
+			// .tickFormat(d3.time.format.iso);
+
+
+		var yAxis = d3.svg.axis()
+			.scale(y)
+			.orient("left");
+
+
+		var svg = d3.select(".chart")
+			.append("svg")
+			.attr("class", "svg")
+			// .attr("width", width)
+			// .attr("height", height)
+			.attr("width", width-20)
+			.attr("height", height-10)
+			.append("g")
+			// .attr("transform", "translate( +50,+0,+0,+0)");
+			.attr("transform", "translate(40 , 0)");
+
+
+		// creation
+
+
+		// Draw the x Grid lines
+		// svg.append("g")
+		// 	.attr("class", "grid")
+		// 	.attr("transform", "translate(0," + height + ")")
+		// 	.call(makeGrid(x, "bottom", timestamp.length)
+		// 		.tickSize(-height, 0, 0)
+		// 		.tickFormat("")
+		// 	);
+
+
+		// Draw the y Grid lines
+		svg.append("g")
+			.attr("class", "grid")
+			.call(makeGrid(y, "left", function(){return Math.min(getMaxIssues(), 10);}())
+				.tickSize(-width, 0, 0)
+				.tickFormat("")
+			);
+
+
+		// Draw the x-axis
+		svg.append("g")
+			.attr("class", "x axis")
+			// .attr("transform", "translate(0, " + 20-height + ")")
+			.call(xAxis)
+			.selectAll("text")
+			.style("text-anchor", "end")
+			// .attr("dx", "-.5em")
+			// .attr("dy", ".1em")
+			// .attr("transform", function() {
+			// 	return "rotate(-30)";
+			// });
+
+
+		// Draw the y-axis
+		svg.append("g")
+			.attr("class", "y axis")
+			.call(yAxis)
+			.append("text")
+			.attr("transform", "rotate(-90)")
+			.attr("y", 6)
+			.attr("dy", ".71em")
+			.style("text-anchor", "end");
+
+
+		// Text for y-axis
+		// svg.append("text")
+		// 	.attr("transform", "rotate(-90)")
+		// 	.attr("y", 10 - margin.left)
+		// 	.attr("x", 0 - (height / 2))
+		// 	.attr("dy", "1em")
+		// 	.style("text-anchor", "middle")
+		// 	.text("Issues");
+
+
+		//Titel und Legende
+		// svg.append("svg:text")
+		// 	.attr("class", "text")
+		// 	.attr("x", 10)
+		// 	.attr("y", -5)
+		// 	.text("Issues Nach Zeit");
+
+		draw_line(svg, wish, "line wish", wishLine, "0, 0");
+		draw_line(svg, feature, "line feature", featureLine, "3, 3");
+		draw_line(svg, bug, "line bug", bugLine, "7, 7");
+		draw_line(svg, urgent, "line urgent", urgentLine, "13, 13");
+		draw_line(svg, critical, "line critical", criticalLine, "17, 17");
+
+
+		// makeLegend(svg, width);
+	}
+
+
+</script>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/modules/roundup_cc/roundup_content_data/__init__.py	Tue Aug 04 14:23:53 2015 +0200
@@ -0,0 +1,82 @@
+#!/usr/bin/env python
+
+""" supplys the data needed to comunicate with the roundup-server,
+and the sqlite database. Represents the types of errors used in roundup.
+
+author: Sascha L. Teichmann <sascha.teichmann@intevation.de>
+author: Bernhard Reiter <bernhard@intevation.de>
+author: Sean Engelhardt <sean.engelhardt@intevation.de>
+
+(c) 2010,2015 by Intevation GmbH
+
+This is Free Software unter the terms of the
+GNU GENERAL PUBLIC LICENSE Version 3 or later.
+See http://www.gnu.org/licenses/gpl-3.0.txt for details
+"""
+
+import os
+
+#Add desired sqlite databases here
+DATABASE_REFERENCCE = os.path.dirname(os.path.realpath(__file__)) + "/test_reference.db"
+DATABASE_DEMO = os.path.dirname(os.path.realpath(__file__)) + "/demo.db"
+DATABASE_ERRORDB = os.path.dirname(os.path.realpath(__file__)) + "/errordatabase.db"
+DATABASE_TECH_INTERN = os.path.dirname(os.path.realpath(__file__)) + "/tech_intern.db"
+DATABASE_INT_TEST = os.path.dirname(os.path.realpath(__file__)) + "/int_test.db"
+
+COLUMNS= [
+    "critical", "urgent", "bug", "feature", "wish",
+]
+
+data_dict = {
+    "date": [],
+    "critical": [],
+    "urgent": [],
+    "bug": [],
+    "feature": [],
+    "wish": []
+}
+
+#SQL
+
+#DEMO System
+SELECT_ALL = """
+SELECT strftime("%Y-%m-%dT%H:%M:%S", timestamp),
+    critical,
+    urgent,
+    bug,
+    feature,
+    wish
+FROM issues
+ORDER BY timestamp
+"""
+
+
+CREATE_DB = """
+CREATE TABLE issues (
+    timestamp TIMESTAMP NOT NULL UNIQUE DEFAULT current_timestamp,
+    critical INTEGER NOT NULL DEFAULT 0,
+    urgent INTEGER NOT NULL DEFAULT 0,
+    bug INTEGER NOT NULL DEFAULT 0,
+    feature INTEGER NOT NULL DEFAULT 0,
+    wish INTEGER NOT NULL DEFAULT 0
+)
+"""
+
+
+INSERT_NEW = """
+    INSERT INTO issues (critical, urgent, bug, feature, wish)
+    VALUES (?, ?, ?, ?, ?)
+"""
+
+#Referecen DB:
+SELECT_ALL_REFERENCE = """
+SELECT strftime("%Y-%m-%dT%H:%M:%S", sample_time),
+    critical,
+    major,
+    crash,
+    normal,
+    minor,
+    wishlist
+FROM issues
+ORDER BY sample_time
+"""
\ No newline at end of file
--- a/views/hello_template.tpl	Wed Jul 29 12:27:26 2015 +0200
+++ b/views/hello_template.tpl	Tue Aug 04 14:23:53 2015 +0200
@@ -3,23 +3,25 @@
 License: GNU GPL >= v2. See LICENSE for details. -->
 
 <%
+    import math, os, sys, subprocess, html.parser
 
-    import math
     from datetime import date
 
+    h = html.parser.HTMLParser()
+    PATH = os.path.abspath(os.path.dirname(sys.argv[0]))
+    sys.path.append(PATH + "/modules")
+    import roundup_cc
+
     #################
     # settings      #
     #################
 
-
     show_top_bar = settings["show_top_bar"]
 
-
     #################
     # date and time #
     #################
 
-
     today = date.today()
     weekday = ("Montag", "Dienstag", "Mittwoch", "Donnerstag",
                 "Freitag", "Samstag", "Sonntag")[today.weekday()]
@@ -177,7 +179,6 @@
     % end
 
     <div id = "content">
-
         <%
             for tile in tiles :
             type = ""
@@ -191,13 +192,16 @@
                 elif tile["status"] == "down" :
                     status = "dead"
                 end
-            elif tile["type"] == "d3.js" :
+            elif tile["type"] == "d3js" :
                 type = "chart"
-                text = "place for a chart!"
+                status = ""
+                text = roundup_cc.get_tech_intern_chart()
+                #text = "<div id = KAKAK>HHOHOHOHOH </div>"
             end
         %>
+
         <div class = "tile {{type}} {{status}}">
-            {{text}}
+            {{!text}}
         </div>
 
         % end
This site is hosted by Intevation GmbH (Datenschutzerklärung und Impressum | Privacy Policy and Imprint)