22
Évaluation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

Évaluation de codes Python en ligne - Innovation valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

  • Upload
    ledat

  • View
    224

  • Download
    3

Embed Size (px)

Citation preview

Page 1: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

Évaluation de codes Python en ligne

F. Kany. ISEN-Brest & La Croix-Rouge

17 avril 2016

Page 2: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

Table des matières

1 Utilisation en local 21.1 Installation de Python 2.7 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21.2 Création d’un environnement virtuel . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21.3 Installation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 31.4 Utilisation en local . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3

2 Déploiement sur un VPS 42.1 Fournisseur d’accès Internet . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 42.2 Installation de Debian/Postgre/Python/Django . . . . . . . . . . . . . . . . . . . . . . . . 4

2.2.1 Debian . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 42.2.2 Postgresql . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 52.2.3 User . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 52.2.4 Python . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 52.2.5 Gunicorn . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6

2.3 Transfert de fichiers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 72.4 Supervisor/Nginx . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8

2.4.1 Test gunicorn . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 82.4.2 Supervisor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 82.4.3 Nginx . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9

2.5 Installation et chargement de la base de données . . . . . . . . . . . . . . . . . . . . . . . 102.6 Utilisation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 102.7 Opérations de maintenance . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11

2.7.1 Environnement virtuel . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 112.7.2 Relancer l’application et le serveur . . . . . . . . . . . . . . . . . . . . . . . . . . . 112.7.3 La base de données . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 112.7.4 Super-utilisateur . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 122.7.5 Zipper l’ensemble du site . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 122.7.6 Installer une nouvelle version de l’application . . . . . . . . . . . . . . . . . . . . . 13

2.8 Modification du bandeau . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 132.9 Pour l’application Bomberman . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13

3 Mode d’emploi 143.1 Soumission de code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 143.2 Le suivi des élèves . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 143.3 Créer des exercices . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14

3.3.1 Énoncé . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 143.3.2 Question/réponse . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 15

3.4 S’échanger des énoncés d’exercice entre profs . . . . . . . . . . . . . . . . . . . . . . . . . 153.5 Problèmes connus . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 15

4 Annexe : architecture et contenu de la base de données 17

1

Page 3: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

Chapitre 1

Utilisation en local

1.1 Installation de Python 2.7Installer une distribution Python 2.7 de son choix. Par exemple : https://sourceforge.net/projects/

winpython/files/WinPython_2.7/2.7.10.3/WinPython-64bit-2.7.10.3.exe/downloadN.B. Python 2.7 est obligatoire car PySandBox ne fonctionne pas sous Python 3.

1.2 Création d’un environnement virtuelEn ligne de commande (touche Windows+R : cmd) :

cd c:\WinPython-64bit-2.7.10.3\python-2.7.10.amd64\Scriptspip install virtualenvcd c:\mkdir venvdjangovirtualenv --no-site-packages venvdjangocd venvdjangocd Scriptsactivatepip install Django==1.8.2pip install django-appconf==1.0.1pip install django-geoip==0.5.2pip install django-user-sessions==1.2.0pip install geoip2==2.2.0#pip install ipaddr==2.1.11#pip install maxminddb==1.2.0pip install pygeoip==0.3.2pip install pysandbox==1.5.1pip install pytz==2015.7#pip install requests==2.9.1#pip install six==1.10.0pip install wheel==0.24.0deactivate

N.B. Les lignes commençant par # n’ont pas besoin d’être tapées ; normalement les packages ont déjàété installés par les librairies précédentes.

N.B. On peut, alternativement, copier-coller la liste des packages ci-dessous dans un fichier requirements.txtet faire pip install requirements.txt

Django==1.8.2

2

Page 4: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

django-appconf==1.0.1django-geoip==0.5.2django-user-sessions==1.2.0geoip2==2.2.0ipaddr==2.1.11maxminddb==1.2.0pygeoip==0.3.2pysandbox==1.5.1pytz==2015.7requests==2.9.1six==1.10.0wheel==0.24.0

1.3 InstallationTélécharger hello.zip à l’adresse http://vps99063.ovh.net/static/fichiers-perso/hello.zipDécompacter à la racine c:\Lorsqu’on utilise l’application en local, Django utilise une base de données SQLite pré-remplie. Il n’est

pas nécessaire d’importer les fichiers du répertoire hello/BASE_DE_DONNES.

cd c:\venvdjango\Scriptsactivatepython c:\hello\manage.py createsuperuserUsername: ...Email address: ...Password: ...Password (again): ...deactivate

1.4 Utilisation en localcd c:\venvdjango\Scriptsactivatepython c:\hello\manage.py runserver

Dans la barre d’url d’un navigateur : 127.0.0.1:8000

Se loggeridentifiant: guestmot de passe: 1234Page d’accueil

guest est un compte élève.

Pour administrer le site, aller dans la partie Backoffice : 127.0.0.1:8000/admin dans la barre d’urldu navigateur, puis :

— se logger avec le compte superuser défini dans la partie installation.— aller dans Userprofile/User profile— sélectionner l’utilisateur superuser, cocher est enseignant— enregistrer

On peut maintenant utiliser ce compte comme professeur.

3

Page 5: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

Chapitre 2

Déploiement sur un VPS

2.1 Fournisseur d’accès InternetChoisir un fournisseur d’accès.Exemple : https://www.ovh.com/fr/vps/, choisir SSD à 3 euros HT/mois.VPS SSD 1 / Commander

Catégorie: Virtual Private Server SSDProduit: VPS 2016 SSD1 (1vCore/2Go/10Go)Quantité: 1Localisation: GravelinesDistribution: LinuxVersion: Debian 8 (Jessie) 64 bitsLangue: Français

Noter le mot de passe.Payer, aller dans sa boîte électronique pour récupérer l’identifiant : subject: Votre identifiant

clientAller sur https://www.ovh.com/manager/ et entrer l’identifiant et le mot de passe.Au bout de quelques minutes, aller dans sa boîte électronique pour récupérer l’adresse du serveur et

le mot de passe root. subject: installation de votre VPS

2.2 Installation de Debian/Postgre/Python/DjangoSource : http://michal.karzynski.pl/blog/2013/06/09/django-nginx-gunicorn-virtualenv-supervisor/

Sur son PC, installer PuTTY http://www.chiark.greenend.org.uk/~sgtatham/putty/download.html

Lancer PuTTYHost name: vpsxxxxxx.ovh.net; Port 22; Connection.

Dans la fenêtre PuTTY :

login as: [email protected]’s password: celui envoyé par courrier électronique

2.2.1 DebianDans la fenêtre PuTTY (ne pas taper les instructions après #)

apt-get updateapt-get upgrade

4

Page 6: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

dpkg-reconfigure localesexport LANG=fr_FR.UTF-8export LANGUAGE=fr_FR.UTF-8export LC_ALL=fr_FR.UTF-8

apt-get install nanoapt-get install apt-utilsapt-get install postgresql postgresql-contrib postgresql-client nginx git supervisorapt-get install build-essential mysql-server mysql-client libmysqlclient-devapt-get install gcc #pour pouvoir compiler pysandboxapt-get install libpq-dev #pour pouvoir installer psycopg2apt-get install python-dev #pour avoir "python.h"

wget https://bootstrap.pypa.io/get-pip.py --no-check-certificatewget https://pypi.python.org/packages/source/s/setuptools/setuptools-18.2.zip --no-check-certificateapt-get install unzipunzip setuptools-18.2.zipcd setuptools-18.2python setup.py installcd ..python get-pip.py

2.2.2 PostgresqlToujours dans la fenêtre PuTTYOn crée un utilisateur et une base de données pour notre projet hello_django

su - postgrespostgres@xxx:~$ createuser --interactive -PEnter name of role to add: hello_djangoEnter password for new role:Enter it again:Shall the new role be a superuser? (y/n) nShall the new role be allowed to create databases? (y/n) nShall the new role be allowed to create more new roles? (y/n) npostgres@xxx:~$postgres@django:~$ createdb --owner hello_django hellopostgres@django:~$ logout

Noter le mot de passe.

2.2.3 UserToujours dans la fenêtre PuTTYOn crée un utilisateur pour Django

groupadd --system webappsuseradd --system --gid webapps --shell /bin/bash --home /webapps/hello_django hello

2.2.4 PythonToujours dans la fenêtre PuTTYOn crée un environnement virtuel pour Python

apt-get install python-virtualenvmkdir -p /webapps/hello_django/chown hello /webapps/hello_django/

5

Page 7: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

su - hellohello@xxx:~$ cd /webapps/hello_django/hello@xxx:~$ virtualenv .hello@xxx:~$ source bin/activate(hello_django)hello@xxx:~$pip install Django==1.8.2pip install Fabric==1.10.2pip install MySQL-python==1.2.5pip install PyYAML==3.11pip install argparse==1.2.1pip install django-appconf==1.0.1pip install django-geoip==0.5.2pip install django-user-sessions==1.2.0pip install ecdsa==0.13pip install email==4.0.2pip install geoip2==2.2.0pip install gunicorn==19.3.0pip install ipaddr==2.1.11pip install maxminddb==1.2.0pip install ordereddict==1.1pip install paramiko==1.15.2pip install psycopg2==2.6.1pip install pycrypto==2.6.1pip install pygeoip==0.3.2pip install pysandbox==1.5.1pip install pytz==2015.7pip install requests==2.9.1pip install setproctitle==1.1.9pip install six==1.10.0pip install subprocess32==3.2.6pip install wheel==0.24.0pip install wsgiref==0.1.2

pip freeze

Vérifier que pip freeze a bien installé tous les packages.

(hello_django)hello@xxx:~$ exitchown -R hello:users /webapps/hello_djangochmod -R g+w /webapps/hello_django

2.2.5 GunicornToujours dans la fenêtre PuTTY

cd /webapps/hello_django/binnano gunicorn_start

Copier ce code :

#!/bin/sh

NAME="hello_app" # Name of the applicationDJANGODIR=/webapps/hello_django/hello # Django project directorySOCKFILE=/webapps/hello_django/run/gunicorn.sock # we will communicte using this unix socket

6

Page 8: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

USER=hello # the user to run asGROUP=webapps # the group to run asNUM_WORKERS=3 # how many worker processes should Gunicorn spawnDJANGO_SETTINGS_MODULE=Projet.settings # which settings file should Django useDJANGO_WSGI_MODULE=Projet.wsgi # WSGI module name

echo "Starting $NAME as ‘whoami‘"

# Activate the virtual environmentcd $DJANGODIRsource ../bin/activateexport DJANGO_SETTINGS_MODULE=$DJANGO_SETTINGS_MODULEexport PYTHONPATH=$DJANGODIR:$PYTHONPATH

# Create the run directory if it doesn’t existRUNDIR=$(dirname $SOCKFILE)test -d $RUNDIR || mkdir -p $RUNDIR

# Start your Django Unicorn# Programs meant to be run under supervisor should not daemonize themselves (do not use --daemon)exec ../bin/gunicorn ${DJANGO_WSGI_MODULE}:application \--name $NAME \--workers $NUM_WORKERS \--user=$USER --group=$GROUP \--bind=unix:$SOCKFILE \--log-level=debug \--log-file=-

Coller le dans gunicorn_start (clic droit) ; sauver (Ctrl-O) et quitter (Ctrl-X)

Rendre le fichier exécutable

chmod u+x gunicorn_startcd ..

2.3 Transfert de fichiersTélécharger l’archive : hello.zip à l’adresse http://vps99063.ovh.net/static/fichiers-perso/

hello.zip

Sur son PC, installer WinSCP https://winscp.net/Nouveau site SFTP ; nom d’hôte : vpsxxxxx.ovh.net ; port 22 ; nom d’utilisateur : root ; mot de passe :

celui envoyé par courrier électronique par OVH.Dans la partie droite (côté serveur), se déplacer dans l’arborescence /webapps/hello_djangoDans la partie gauche (côté PC), se déplacer dans le répertoire où se trouve hello.zipFaire glisser hello.zip de la partie gauche à la partie droite (donc dans /webapps/hello_django).

Dans la fenêtre PuTTY

cd /webapps/hello_djangounzip hello.zipmkdir staticcd staticln -s /webapps/hello_django/lib/python2.7/site-packages/django/contrib/admin/static/admin adminln -s /webapps/hello_django/hello/Projet/static/js js

7

Page 9: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

ln -s /webapps/hello_django/hello/Projet/static/css cssln -s /webapps/hello_django/hello/Projet/static/media medialn -s /webapps/hello_django/hello/fort/static/fort fortln -s /webapps/hello_django/hello/frog/static/frog frogln -s /webapps/hello_django/hello/gomoku/static/gomoku gomokuln -s /webapps/hello_django/hello/bomberman/static/bomberman bombermanln -s /webapps/hello_django/hello/tron/static/tron troncd /webapps/hello_django/hello/Projet/nano settings.py

Mettre DEBUG à False (ligne 27) et PRODUCTION à True (ligne 28).Modifier ALLOWED_HOST=[’vpsxxx.ovh.net’] (ligne 32)Modifier le mot de passe de DATABASES (ligne 123) en mettant celui du §2.2.2Modifier l’adresse e-mail (se créer un compte Gmail spécifique) pour que le serveur puisse envoyer

automatiquement des mails 1 à ceux qui ont oublié leur mot de passe (lignes 177 et 178).Ctrl-O (sauver) Ctrl-X (quitter)

cd /

2.4 Supervisor/Nginx

2.4.1 Test gunicornDans la fenêtre PuTTY

su - hellohello@xxx:~$ bin/gunicorn_start

Le serveur doit démarrer ; exemple :

[2016-03-29 23:28:57 +0000] [23696] [INFO] Starting gunicorn 19.3.0[2016-03-29 23:28:57 +0000] [23696] [DEBUG] Arbiter booted[2016-03-29 23:28:57 +0000] [23696] [INFO] Listening at: unix:/webapps/hello_django/run/gunicorn.sock (23696)[2016-03-29 23:28:57 +0000] [23696] [INFO] Using worker: sync[2016-03-29 23:28:57 +0000] [23703] [INFO] Booting worker with pid: 23703[2016-03-29 23:28:58 +0000] [23706] [INFO] Booting worker with pid: 23706[2016-03-29 23:28:58 +0000] [23707] [INFO] Booting worker with pid: 23707[2016-03-29 23:28:58 +0000] [23696] [DEBUG] 3 workers[2016-03-29 23:28:59 +0000] [23696] [DEBUG] 3 workers

On arrête avec : Ctrl-C

exit

2.4.2 SupervisorDans la fenêtre PuTTY

cd /cd /etc/supervisor/conf.dnano hello.conf

Copier ce code :

1. Pour empêcher Gmail de bloquer le serveur : http://www.google.com/accounts/DisplayUnlockCaptcha and clickcontinue (this will grant access for 10 minutes for registering new apps). After this my app in production started sendingemails

8

Page 10: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

[program:hello]command = /webapps/hello_django/bin/gunicorn_start ; Command to start appuser = hello ; User to run asstdout_logfile = /webapps/hello_django/logs/gunicorn_supervisor.log ; Where to write log messagesredirect_stderr = true ; Save stderr in the same logenvironment=LANG=fr_FR.UTF-8,LC_ALL=fr_FR.UTF-8 ; Set UTF-8 as default encoding

Coller le dans hello.conf (clic droit) ; sauver (Ctrl-O) et quitter (Ctrl-X)

Puis (sans les commentaires après #)

cd /mkdir -p /webapps/hello_django/logs/touch /webapps/hello_django/logs/gunicorn_supervisor.logsupervisorctl reread #hello: availablesupervisorctl update #hello: added process groupsupervisorctl start hello #hello: started

2.4.3 NginxDans la fenêtre PuTTY

service nginx startcd /etc/nginx/sites-availablemkdir hellocd hellonano nginx.conf

Copier ce code :

upstream hello_app_server {server unix:/webapps/hello_django/run/gunicorn.sock fail_timeout=0;

}

server {

listen 80;server_name vpsxxxx.ovh.net;#mettre le nom du serveur

client_max_body_size 4G;

access_log /webapps/hello_django/logs/nginx-access.log;error_log /webapps/hello_django/logs/nginx-error.log;

location /static/ {alias /webapps/hello_django/static/;

}

location /media/ {alias /webapps/hello_django/media/;

}

location / {proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;proxy_set_header Host $http_host;

9

Page 11: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

proxy_redirect off;if (!-f $request_filename) {

proxy_pass http://hello_app_server;break;

}}

# Error pageserror_page 500 502 503 504 /500.html;location = /500.html {

root /webapps/hello_django/static/;}

}

Coller le dans nginx.conf (clic droit) ; modifier server_name (ligne 8) ; sauver (Ctrl-O) et quitter(Ctrl-X)

ln -s /etc/nginx/sites-available/hello/nginx.conf /etc/nginx/sites-enabled/helloservice nginx restart

Dans la barre d’url d’un navigateur vpsxxx.ovh.net. Ça y est !

2.5 Installation et chargement de la base de donnéesLorsque l’on utilise l’application sur un serveur, Django utilise une base de données Postgresql, ini-

tialement vierge. Il faut la créer et, éventuellement, la remplir.

su - hellosource bin/activatecd /webapps/hello_django/hellopython manage.py makemigrationspython manage.py migratepython manage.py loaddata ./BASE_DE_DONNEES/dump_mini_auth_user_foreign_primary.jsonpython manage.py loaddata ./BASE_DE_DONNEES/dump_mini_userprofile_foreign_primary.jsonpython manage.py loaddata ./BASE_DE_DONNEES/dump_eval_code_td_foreign_primary_2016_04_07.jsonpython manage.py loaddata ./BASE_DE_DONNEES/eval_code_exercice_foreign_primary_2016_04_07.jsonpython manage.py loaddata ./BASE_DE_DONNEES/eval_code_question_foreign_primary_2016_04_07.jsonexitsupervisorctl restart hello

3 profils sont créés :

identifiant mot de passe super-utilisateur est_enseignantadmin 1234 oui nonprof1 1234 oui ouieleve1 1234 non non

ainsi qu’une centaine d’exercices et environ 4 questions par exercice.

2.6 UtilisationDans la barre d’url d’un navigateur vpsxxxx.ovh.net ; puis : se logger

identifiant: prof1mot de passe: 1234

puis page d’accueil.

10

Page 12: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

2.7 Opérations de maintenance

2.7.1 Environnement virtuelPour accéder à l’environnement virtuel de Python

su - hellosource bin/activate

puis, pour quitter :

exit

2.7.2 Relancer l’application et le serveurEn cas de modifications sur le code source (en particulier settings.py), dans une console PuTTY :

supervisorctl restart helloservice nginx restart

2.7.3 La base de donnéesPour sauver les bases de données :

su - hellosource bin/activatecd /webapps/hello_django/hellopython manage.py dumpdata auth.user --natural-foreign --natural-primary --indent 4 >

./BASE_DE_DONNEES/auth_user.jsonpython manage.py dumpdata userprofile --natural-foreign --natural-primary --indent 4 >

./BASE_DE_DONNEES/userprofile.jsonpython manage.py dumpdata eval_code.td --natural-foreign --natural-primary --indent 4 >

./BASE_DE_DONNEES/eval_code_td.jsonpython manage.py dumpdata eval_code.exercice --natural-foreign --natural-primary --indent 4 >

./BASE_DE_DONNEES/eval_code_exercice.jsonpython manage.py dumpdata eval_code.question --natural-foreign --natural-primary --indent 4 >

./BASE_DE_DONNEES/eval_code_question.jsonpython manage.py dumpdata eval_code.soumission_code --natural-foreign --natural-primary --indent 4 >

./BASE_DE_DONNEES/eval_code_soummission.json

ou bien tout en même temps (si ça se passe bien)

python manage.py dumpdata auth.user userprofile eval_code --natural-foreign --natural-primary--exclude auth.permission --exclude contenttypes --indent 4 > ./BASE_DE_DONNEES/all.json

Pour charger les bases de données :

su - hellosource bin/activatecd /webapps/hello_django/hellopython manage.py loaddata ./BASE_DE_DONNEES/auth_user.jsonpython manage.py loaddata ./BASE_DE_DONNEES/userprofile.jsonpython manage.py loaddata ./BASE_DE_DONNEES/eval_code_td.jsonpython manage.py loaddata ./BASE_DE_DONNEES/eval_code_exercice.jsonpython manage.py loaddata ./BASE_DE_DONNEES/eval_code_questionl.jsonpython manage.py loaddata ./BASE_DE_DONNEES/eval_code_soummission.json

ou bien tout en même temps

python manage.py loaddata ./BASE_DE_DONNEES/all.json

11

Page 13: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

En cas de problème pour charger l’une des tables de l’application app_name (où app_name=userprofileou eval_code), il faut effacer les tables et les migrations (construction de la base) et retenter les dumps(remplissage de la base).

su - hellosource bin/activatecd /webapps/hello_django/hellocd app_name/migrationsrm *touch __init__.py

cd /webapps/hello_django/hellopython manage.py sqlclear app_name | python manage.py dbshell

python manage.py makemigrationspython manage.py migrate

Si ça ne suffit pas, il faut également effacer l’historique des migrations dans la base de données dedjango.

su - hellosource bin/activatecd /webapps/hello_django/hellopython manage.py dbshell\d #all tablesselect * from django_migrations where app = ’app_name’;delete * from django_migrations where app = ’app_name’;\q #quit

cd app_name/migrationsrm *touch __init__.py

cd /webapps/hello_django/hellopython manage.py sqlclear app_name | python manage.py dbshell

python manage.py makemigrationspython manage.py migrate

2.7.4 Super-utilisateurPour créer un nouveau super-utilisateur :

su - hellosource bin/activatecd /webapps/hello_django/hellopython manage.py createsuperuserUsername: adminPassword: ...Password again:...

ou bien directement depuis l’interface administrateur.

2.7.5 Zipper l’ensemble du sitecompresser: tar -zcvf archive.tar.gz directory/decompresser: tar -zxvf archive.tar.gz

12

Page 14: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

2.7.6 Installer une nouvelle version de l’applicationSauver la base de données (cf §2.7.3).

Dans une fenêtre PuTTY

cd /webapps/hello_djangomv hello hello_old

Refaire toutes les opérations du paragraphe “Transfert de fichiers” (cf §2.3), puis :

chown -R hello:users /webapps/hello_djangochmod -R g+w /webapps/hello_djangosupervisorctl restart helloservice nginx restart

Enfin, recharger la base de données (cf §2.7.3).

2.8 Modification du bandeauLes images dans le bandeau en haut du site sont définies ici : hello\Projet\static\media. On peut

soit insérer ses propres images en les renommant logo_croix_rouge.jpg et logo_isen.jpg, soit modifierle code hello\Projet\templates\Projet\base.html (lignes 6 et 7) pour changer le nom des images.

2.9 Pour l’application Bombermanapt-get install ocamlcd /webapps/hello_django/hello/bombermanmv utils.py utils_windows.pymv utils_debian.py utils.pysupervisorctl restart hello

13

Page 15: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

Chapitre 3

Mode d’emploi

3.1 Soumission de codeLorsqu’il soumet son code, l’utilisateur avec le statut est_enseignant voit les questions posées, les

solutions attendues et les réponses calculées (ou les messages d’erreur).L’utilisateur qui n’a pas le statut est_enseignant voit seulement les messages d’erreurs.

3.2 Le suivi des élèvesLes comptes avec le statut est_enseignant permettent d’accéder à la partie réservée :— Appel— Bilans (par nom)— Bilans (par total)— Bilans (par date)— Backoffice (vpsxxx.ovh.net/admin)

3.3 Créer des exercicesDans la partie backoffice vpsxxx.ovh.net/admin

3.3.1 ÉnoncéPour entrer un énoncé dans la base de données :— On peut insérer des balises HTML dans les énoncés.— Pour insérer des images ou des équations dans les énoncés, utiliser le format SVG <svg> ... </svg>

et copier-coller le code généré par InkScape ou LaTeXPour que l’insertion soit dans une ligne de texte, utiliser <img><svg> ... </svg></img>

— Dans Exercice.bibliotheques_autorisees :Les bibliothèques doivent être séparées par des virgules. Exemple : math,future.Il est important d’autoriser future dans tous les exercices (à cause du problème de la divisionentière).On ne peut pas autoriser numpy et scipy.Dans le code, on ne peut pas écrire "from module import *"mais on peut écrire "from module import __all__" lorsque ’__all__’ est défini(N.B. ’__all__’ n’est pas défini dans le module : math)

— Dans Exercice.enonce, s’il y a des fonctions à passer en argument de la fonction principale,celles-ci doivent être en premier argument.Exemple : fonction_principale(fonction_argument1,argument_2,argument3)et non fonction_principale(argument1,fonction_argument_2,argument3)

14

Page 16: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

Si l’on ne veut pas qu’un exercice soit visible pour les élèves : créer une liste de TD, ne pas cocherest visible. À la création de l’exercice, affecter le numéro au TD précédent. Si, par la suite, on veutrendre cet exercice visible aux élèves, affecter le numéro à une liste de TD visible.

3.3.2 Question/réponsePour entrer une question dans la base de données :— Dans Question.question et Question.reponse : les chaines de caractères doivent être explicite-

ment délimitées par des apostrophes ’...’ ou bien des guillemets "..."— Dans Question.question : il faut au minimum un argument ; lorsqu’il n’y a qu’un seul argument,

terminer par une virgule ","— Dans Question.question : les fonctions à passer en arguments doivent :

— être en premier argument (cf § précédent)— être des chaines de caractères séparées par des virgules— être des lambda fonctions— avoir un nom d’une seule lettre— donc de la forme : ’f=lambda x:x**2’,’g=lambda x:x**3’

3.4 S’échanger des énoncés d’exercice entre profsIl est difficile de faire un dump partiel de la base de données pour exporter un seul exercice (on peut

faire un dump total et faire un copier-coller de la partie du .json que l’on souhaite).Le plus simple est d’aller dans la partie administrateur et de sauver la page de l’exercice (et des

questions) au format HTML.Il suffit alors au destinataire de faire un copier-coller dans sa propre partie administrateur.

3.5 Problèmes connus1. Race condition

Si on clique très rapidement plusieurs fois au moment où l’on entame un nouvel exercice, deuxsoumissions sont créées avec le même exercice et le même utilisateur. Le serveur ne sait pas quellesoumission afficher et renvoie une page 404.Le problème arrive très rarement (3 fois sur plus de 5 000 soumissions).Si c’est le cas, aller dans la partie backoffice, eval_code/soumission, rechercher le doublon (entriant par date) et supprimer les soumissions correspondantes.

2. Si un élève quitte le site VPS sans se délogger, sa session expire automatiquement au bout de 24heures. Néanmoins, il reste des traces de sa session dans la base de données (ce qui l’encombreinutilement).Pour effacer les sessions qui ont expiré : aller dans le backoffice, sélectionner les sessions et lessupprimer.Sinon python manage.py clearsessions.On peut faire un cron pour automatiser cette tache.

3. Dans Projet/settings.py, laisser USER_SESSION à False.En utilisation locale, cette option fonctionne ; elle permet, dans la partie backoffice, d’avoir desinformations supplémentaires sur les sessions (OS de l’utilisateur, navigateur, adresse IP,...).[L’idée était de banir pendant 3 minutes les adresses IP des élèves qui soumettent des bouclesinfinies]Sur un serveur Nginx (avec la configuration actuelle), on ne peut pas récupérer l’adresse IP(IP=null) ce qui fait crasher le serveur.

4. Dans un dump de toutes les tables (cf. > dump_all), si un utilisateur ne s’est jamais logé, ily a un champ ’last_login’: null (à chercher par Ctrl-F) à remplacer par ’last_login’:"2000-01-01 00:00". Si on trouve ”null” dans les autres applications (bomberman,tron,...), onle remplace par 0.

15

Page 17: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

5. Ne pas créer deux exercices avec le même numéro de TD et le même ordre dans le TD. (C’estpossible, mais si on efface ensuite un des exercices, il y a des risques d’effacer le mauvais exercice[Bug non reproductible, probablement lié à une modification la structure de la base de donnéesentre 2 dumps] ; de plus cela peut créer des conflits lorsqu’on exporte/importe les questions relativesà ces exercices [avec l’option natural-foreign]).

6. ...

16

Page 18: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

Chapitre 4

Annexe : architecture et contenu de labase de données

auth_user

id int

password varcharis_superuser boolusername varcharfirst_name varcharemail varcharis_staff boolis_active booldate_joined datetimelast_login datetime

userprofile_userprofile

id int

est_enseignant booluser_id intclasse_principale_id int

userprofile_classe

id int

classe varchar

eval_code_question

id int

question textreponse textexercice_id inttemps_max real

eval_code_submission_code

id int

date_creation datetimedate_modification datetimeprogramme textlog textnote intauteur_id intexercice_id inttemps real

eval_code_exercice

id int

numero_TD intordre_dans_TD inttitre varcharenonce textnom_fonction varcharnbre_fonct_en_papametre intsolution textbibliotheques_autorisees text

eval_code_TD

id int

numero inttitre varcharvisible bool

17

Page 19: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

n◦ TD Titre110 Première année : les variables120 Première année : les tests130 Première année : les boucles140 Première année : les listes150 Première année : les chaînes de caractères210 Deuxième année : révisions220 Deuxième année : algorithmes numériques230 Deuxième année : algorithmes récursifs240 Deuxième année : algorithmes de tri310 Arithmétique320 Probabilités330 Algèbre linéaire404 Liste cachée410 Electricité420 Mécanique490 Chimie500 Algorithmique : divers510 Algorithmique : rendu de la monnaie520 Algorithmique : labyrinthes et graphes530 Programmation objet

18

Page 20: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

n◦ TD n◦ ex Exercice Nbre ques110 10 Marches 2110 20 TTC 3110 30 Rectangle 2110 40 Perimetre 2110 50 Equation second degre 3110 60 Augmentation des taxes 3120 10 Divisible par 7 4120 20 Calcul remise 5120 30 Equation second degre (suite) 4120 40 Année bissextile 4120 50 Impots 5120 60 Intervalle - 1 4120 80 Intersection 3130 10 Somme - 1 4130 20 Produit 4130 30 Somme - 2 4130 40 Nenuphar 3130 50 Somme carré 3130 60 Epidémie 3130 70 Euclide 4130 80 Syracuse 4130 90 Babylone 4140 10 Intervalle - 2 3140 20 Multiples 3140 30 Table de multiplication 3140 40 Crible 2140 50 Conversion base 10 -> base b 4140 60 Perimetre rectangle 4140 70 Dans le rectangle 4140 80 Denivelé 3140 90 Liste de courses 3140 100 Variation de stocks 3140 110 Médian 3140 120 Retour à l’entrée d’un labyrinthe 3140 130 Les petits avec les grands 3140 140 Participants à une fête 4140 150 Allonger une liste 3140 160 Tournoi 1 2140 170 Tournoi 2 2150 10 Minuscule 2150 15 Compter les mots 4150 17 Nombre associé 4150 18 Palindrome 4150 20 Rectangle plein 2150 30 Rectangle creux 2150 40 Triangle rectangle 2150 50 Triangle isocèle 2150 55 Celsius-Farenheit 4150 56 Liste 3150 60 Labyrinthe 5150 70 Cible 3

19

Page 21: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

n◦ TD n◦ ex Exercice Nbre ques210 10 Hello World ! 3210 20 Recherche du maximum dans une liste de nombres 4210 30 Calcul de la moyenne et de la variance 7210 40 Compte à rebours multiple 11210 50 Somme de polynômes 10210 60 Recherche d’une sous-liste dans une liste de nombres 11210 70 Numération romaine 18210 80 Recherche par dichotomie dans une liste triée 23210 90 Recherche par dichotomie du zéro d’une fonction 5210 100 Addition binaire 8210 110 Évaluation d’une expression postfixée (version chaine) 4210 120 Évaluation d’une expression postfixée (version liste) 4210 130 Encodage 9210 140 Attaque par force brute 2210 150 Détermination des fréquences 4210 160 Recherche de la fréquence maximale 5210 170 Décodage par analyse fréquentielle 3210 180 Question subsidiaire 1210 190 Recherche de l’intersection de 2 fonctions 2220 10 Horner - 1 5220 20 Horner - 2 3220 30 Secante 4220 40 Newton 5220 50 Gauss - 1 4220 60 Gauss - 2 6220 70 Dérivée 4220 80 Lagrange - 1 4220 90 Lagrange - 2 4220 100 Régression linéaire 5220 102 Régression parabolique 3220 105 Plan 3220 110 Intégrale par la méthode des trapèzes 3220 120 Intégrale par la méthode de Simpson 3220 130 Euler 3220 140 Fourier 3220 150 FFT 3230 10 Zéros 5230 20 Hanoï 3230 25 Générateur avec répétition 3230 26 Générateur sans répétition 3230 30 Casse-tête 3230 40 Sudoku 4240 10 Tri par sélection 4240 20 Tri à bulles 4240 30 Tri par insertion 4240 40 Tri rapide 4240 50 Tri fusion 5

20

Page 22: Évaluation de codes Python en ligne - Innovation  valuation de codes Python en ligne F. Kany. ISEN-Brest & La Croix-Rouge 17 avril 2016

n◦ TD n◦ ex Exercice Nbre ques310 10 Diophante 5310 20 Diviseurs 4310 25 Diviseurs premiers 4310 30 McNugget 4310 40 Partition - 1 4310 50 Partition - 2 5310 60 Décomposition en somme de carrés 4310 70 Fraction continue 4310 80 Fraction rationnelle 4320 10 Chasseurs 4320 20 Anniversaires 4320 30 Avion 3320 40 Jeu de dé 4330 10 Vecteur 4330 20 Matrice 4330 30 Gram-Schmidt 4404 0 Decomposition QR [OK, à passer en visible] 4404 0 Vecteur [à effacer] 0404 10 Rebond [OK, à passer en visible] 4404 100 Demineur (old) [à effacer] 0404 120 Atteindre la cible [OK, à passer en visible] 5404 130 Le compte est bon [OK, à passer en visible] 4410 10 Association série 3410 20 Association parallèle 3410 30 Signal sinusoidal 4410 40 Signal carré 4410 50 Signal triangle 4410 100 Bode 5420 10 Tir balistique 4420 20 Tir balistique (2) 4420 30 Cycloide 4420 40 Cycloide (2) 4490 10 Klechkowski 5500 10 13/04/16 5500 20 Puce 4500 30 Chapeaux 1500 40 Mastermind 7500 50 Démineur 4510 10 Rendu de la monnaie (force brute, avec itertools) 5510 20 Rendu de la monnaie (force brute, sans itertools) 5510 30 Rendu de la monnaie (glouton) 5510 40 Rendu de la monnaie (programmation dynamique) 5510 50 Nombre de rendus de la monnaie 6520 10 Pledge 5520 20 BFS (Breadth First Search) 3520 30 DFS (Depth First Search) 3520 40 Cavalier 4520 50 Dijkstra 5520 60 Vers la sortie 5530 10 Parcours d’un arbre 4530 20 Arbre de recherche 4

613

21