Some doc added

This commit is contained in:
Phyks 2014-01-24 18:55:06 +01:00
parent 7bed5dd258
commit c6c08563ce
3 changed files with 143 additions and 20 deletions

View File

@ -3,4 +3,51 @@ DefiVelib
A website to compare travel times in Velib at Paris.
Currently working on…
DefiVelib est un script PHP permettant de noter et de partager des durées de
trajet entre des stations de vélib. C'est un script tenant en un seul fichier,
que vous pouvez donc héberger facilement sur votre serveur pour avoir une
instance perso.
Il récupère la liste des stations de Vélib sur l'API REST disponible et permet
de sélectionner une station de départ et d'arrivée avec une durée de trajet
associée. Ceci permet ainsi de prévoir a priori la durée estimée du parcours,
mais également de montrer qu'on est bien souvent plus rapide à vélo qu'on ne le
pense.
Une instance de démonstration pleinement fonctionnelle est disponible à
l'adresse http://defivelib.phyks.me.
## Disclaimer
Les temps disponibles sont rentrés par les usagers du service et ne reflètent
pas forcément les temps réels de parcours. De plus, les conditions de
circulation sont variables au cours de la journée.
Le code de la route s'applique également aux vélos, et l'obtention d'un
meilleur temps ne doit pas se faire au détriment du respect du code de la
route.
## Données personnelles
Sur l'instance de démonstration, les logs de connexion au service sont
conservés. Aucune autre donnée personnelle n'est conservée et vous êtes libres
de spécifier un pseudo vous identifiant si vous le souhaitez.
## Installation
Pour l'installer sur son serveur, il suffit de cloner le dépôt Git dans un dossier accessible par votre serveur web. Au premier lancement, l'application récupère la liste des stations de vélib disponibles. Comme pour le script [BikeInParis](https://github.com/phyks/bikeinparis), la mise à jour se fait par une tâche cron à lancer sur votre serveur, en appelant le script avec un bon code de synchronisation.
Pour mettre à jour automatiquement la liste des stations, vous pouvez utiliser une tâche cron comme suit :
<code>sudo crontab -e</code>
puis insérer la ligne
<code>* * * * * wget -q -O adresse_de_base_de_DefiVelib/index.php?update=1&code=code_synchro #Commande de mise a jour des stations de velib</code>
en remplaçant code_synchro par votre code de synchronisation et en définissant * conformément à la fréquence de mises à jour souhaitée.
Toutes les données sont sauvegardées dans des fichiers, dans le dossier `data/`. Ce dossier est automatiquement créé au premier lancement de l'application, aussi assurez-vous que le serveur web ait des permissions suffisantes pour écrire des fichiers (chmod…).
Le code de synchronisation vous permet également d'accéder à l'administration, à l'adresse `adresse_de_base_de_DefiVelib/?code=code_synchro`. Cette interface vous permet notamment de retirer des temps.
## TODO
* Gestion des tickets de Velib ? => scan comme preuve + OCR ?

1
TODO
View File

@ -1 +0,0 @@
* Envoi de photo

113
index.php
View File

@ -7,6 +7,40 @@
return in_array($_POST['start_search'], $array) && in_array($_POST['end_search'], $array);
}
// Generates a token against CSRF
// ==============================
function generate_token($name = '') {
if(session_id() == '')
session_start();
$token = uniqid(rand(), true);
$_SESSION[$name.'_token'] = $token;
$_SESSION[$name.'_token_time'] = time();
return $token;
}
// Checks that the anti-CSRF token is correct
// ==========================================
function check_token($time, $name = '') {
if(session_id() == '')
session_start();
if(isset($_SESSION[$name.'_token']) && isset($_SESSION[$name.'_token_time']) && (isset($_POST['token']) || isset($_GET['token']))) {
if(!empty($_POST['token']))
$token = $_POST['token'];
else
$token = $_GET['token'];
if($_SESSION[$name.'_token'] == $token) {
if($_SESSION[$name.'_token_time'] >= (time() - (int) $time))
return true;
}
}
return false;
}
if(is_file('data/data')) {
$data = unserialize(gzinflate(base64_decode(file_get_contents('data/data'))));
}
@ -14,8 +48,13 @@
$data = array();
}
if(!empty($_GET['suppr']) && !empty($_SESSION['admin'])) {
unlink($data[$_GET['suppr']]);
if(!empty($_GET['suppr']) && !empty($_SESSION['admin']) && !empty($_GET['token'])) {
if(check_token(600, 'defivelib')) {
unlink($data[$_GET['suppr']]);
}
else {
exit("Mauvais token, veuillez réessayer.");
}
}
if(!empty($_GET['deco'])) {
@ -31,24 +70,36 @@
}
$search = false;
if(!empty($_POST['start_search']) && !empty($_POST['end_search'])) {
$search = true;
$data = array_filter($data, "search");
if(!empty($_POST['start_search']) && !empty($_POST['end_search']) & !empty($_POST['token'])) {
if(check_token(600, 'defivelib')) {
$search = true;
$data = array_filter($data, "search");
}
else {
exit("Mauvais token, veuillez réessayer.");
}
}
if((!empty($_POST['time_min']) || !empty($_POST['time_sec'])) && !empty($_POST['start']) && !empty($_POST['end'])) {
$min = (!empty($_POST['time_min'])) ? (int) $_POST['time_min'] : 0;
$sec = (!empty($_POST['time_sec'])) ? (int) $_POST['time_sec'] : 0;
$pseudo = (!empty($_POST['pseudo'])) ? $_POST['pseudo'] : "Anonyme";
if(check_token(600, 'defivelib')) {
$min = (!empty($_POST['time_min'])) ? (int) $_POST['time_min'] : 0;
$sec = (!empty($_POST['time_sec'])) ? (int) $_POST['time_sec'] : 0;
$pseudo = (!empty($_POST['pseudo'])) ? $_POST['pseudo'] : "Anonyme";
$data[] = array("date"=>time(), "start"=>(int) $_POST['start'], "end"=>(int) $_POST['end'], "min"=>$min, "sec"=>$sec, "pseudo"=>$pseudo);
$data[] = array("date"=>time(), "start"=>(int) $_POST['start'], "end"=>(int) $_POST['end'], "min"=>$min, "sec"=>$sec, "pseudo"=>$pseudo);
// TODO : Upload + taille max de l'upload
// TODO : Upload + taille max de l'upload
if(count($data) == 1 || $min != $data[count($data)-2]['min'] || $sec != $data[count($data)-2]['sec'] || $_POST['start'] != $data[count($data)-2]['start'] || $_POST['end'] != $data[count($data)-2]['end'] || $pseudo != $data[count($data)-2]['pseudo']) {
file_put_contents('data/data', base64_encode(gzdeflate(serialize($data))));
if(count($data) == 1 || $min != $data[count($data)-2]['min'] || $sec != $data[count($data)-2]['sec'] || $_POST['start'] != $data[count($data)-2]['start'] || $_POST['end'] != $data[count($data)-2]['end'] || $pseudo != $data[count($data)-2]['pseudo']) {
file_put_contents('data/data', base64_encode(gzdeflate(serialize($data))));
}
}
else {
exit("Mauvais token, veuillez réessayer.");
}
}
$token = generate_token('defivelib');
?>
<!DOCTYPE html>
<html lang="fr">
@ -110,6 +161,14 @@ table {
fieldset {
background-color: rgba(17, 78, 121, 0.1);
}
#disclaimer {
font-size: 0.75em;
}
#disclaimer p {
text-align: left;
}
</style>
</head>
<body>
@ -170,6 +229,12 @@ fieldset {
}
$liste_stations = unserialize(gzinflate(base64_decode(file_get_contents('data/stations'))));
?>
<div id="disclaimer">
<h2>Disclaimer</h2>
<p>Les temps rentrés sur cette page ne sont qu'indicatifs et sont fournis par les internautes eux-mêmes. Ils peuvent donc ne pas refléter les temps réels de parcours. En particulier, il est important de rappeler que le code de la route s'applique aussi aux vélos et que l'obtention d'un meilleur temps ne doit pas se faire au détriment du respect du code de la route.</p>
<p>Le respect des données personnelles étant particulièrement important, ce script ne conserve aucune information particulière si vous ne souhaitez pas en renseigner. Votre adresse IP est néanmoins stockée dans les logs de connexion au serveur, comme pour tout serveur web, conformément à l'article 6 de la LCEN.</p>
<p><a href="README.md">Plus d'informations sur DefiVelib</a></p>
</div>
<h2>Ajouter un trajet</h2>
<form method="post" action="index.php"> <!-- enctype="multipart/form-data"-->
<fieldset>
@ -178,7 +243,12 @@ fieldset {
<select name="start" id="start">
<?php
foreach($liste_stations as $key=>$station) {
echo "<option value=\"".$key."\">".$station['name']."</option>";
if(!empty($_POST['start_search']) && $_POST['start_search'] == $key)
$selected = "selected";
else
$selected = "";
echo "<option value=\"".$key."\" ".$selected.">".$station['name']."</option>";
}
?>
</select>
@ -187,7 +257,12 @@ fieldset {
<select name="end" id="end">
<?php
foreach($liste_stations as $key=>$station) {
echo "<option value=\"".$key."\">".$station['name']."</option>";
if(!empty($_POST['end_search']) && $_POST['end_search'] == $key)
$selected = "selected";
else
$selected = "";
echo "<option value=\"".$key."\" ".$selected.">".$station['name']."</option>";
}
?>
</select>
@ -200,7 +275,8 @@ fieldset {
<!-- <p><label for="photo">Photo du ticket (? max) : </label><input type="file" name="photo" id="photo"></p>-->
</fieldset>
<p>
<input type="submit" value="Envoyer">
<input type="submit" value="Envoyer"/>
<input type="hidden" name="token" value="<?php echo $token; ?>"/>
<!-- <input type="hidden" name="MAX_FILE_SIZE" value="2097152">-->
</p>
</form>
@ -235,7 +311,7 @@ fieldset {
foreach($data as $key=>$result) {
if(!empty($_SESSION['admin'])) {
$delete = "<td><a href=\"?suppr=".$key."\">Supprimer</a></td>";
$delete = "<td><a href=\"?suppr=".$key."&token=".$token."\">Supprimer</a></td>";
}
else {
$delete = "";
@ -247,7 +323,7 @@ fieldset {
else {
for($i = count($data) - 1; $i >= max(count($data) - 10, 0); $i--) {
if(!empty($_SESSION['admin'])) {
$delete = "<td><a href=\"?suppr=".$i."\">Supprimer</a></td>";
$delete = "<td><a href=\"?suppr=".$i."&token=".$token."\">Supprimer</a></td>";
}
else {
$delete = "";
@ -299,7 +375,8 @@ fieldset {
</p>
</fieldset>
<p>
<input type="submit" value="Rechercher">
<input type="submit" value="Rechercher"/>
<input type="hidden" name="token" value="<?php echo $token; ?>"/>
</p>
</form>
<?php