Ajout du projet
This commit is contained in:
parent
a9291727f5
commit
1a13ed504d
1
res/css/bulma/bulma.min.css
vendored
Normal file
1
res/css/bulma/bulma.min.css
vendored
Normal file
File diff suppressed because one or more lines are too long
151
server.py
Normal file
151
server.py
Normal file
@ -0,0 +1,151 @@
|
|||||||
|
from flask import Flask, render_template, request, json
|
||||||
|
import subprocess
|
||||||
|
import os
|
||||||
|
import time
|
||||||
|
|
||||||
|
DUMPS_DIR = "DumpDir"
|
||||||
|
KEYFILE = "key-file.txt"
|
||||||
|
HOST = "localhost"
|
||||||
|
PORT = "5000"
|
||||||
|
|
||||||
|
|
||||||
|
def runCommand(command):
|
||||||
|
process = subprocess.Popen(
|
||||||
|
command,
|
||||||
|
stdout=subprocess.PIPE,
|
||||||
|
stderr=subprocess.PIPE,
|
||||||
|
shell=True)
|
||||||
|
stdout, stderr = process.communicate()
|
||||||
|
return stdout, stderr, process.returncode
|
||||||
|
|
||||||
|
|
||||||
|
### Partie Flask (Serveur Web)
|
||||||
|
app = Flask('__name__', static_folder="res")
|
||||||
|
app.config['DEBUG'] = False
|
||||||
|
|
||||||
|
|
||||||
|
# Page principal
|
||||||
|
@app.route('/')
|
||||||
|
def root():
|
||||||
|
if request.args.get("error"): # On affiche l'erreur si il y en a une.
|
||||||
|
error = request.args.get("error")
|
||||||
|
return render_template('index.html', error=error)
|
||||||
|
else :
|
||||||
|
return render_template('index.html')
|
||||||
|
|
||||||
|
|
||||||
|
# Page d'attente du badge du client
|
||||||
|
@app.route('/waitingBadge')
|
||||||
|
def waitingBadge():
|
||||||
|
nbBadge = request.args.get('nbBadge', default=1, type=int)
|
||||||
|
return render_template('waitingBadge.html', nbBadge=nbBadge)
|
||||||
|
|
||||||
|
# Une fois que le badge est détecté
|
||||||
|
@app.route('/detectBadge')
|
||||||
|
def detectBadge():
|
||||||
|
while True: # Boucle infinie tant que le badge n'est pas detecté.
|
||||||
|
result = {'Error': '1'}
|
||||||
|
stdout, stderr, return_code = runCommand('nfc-list')
|
||||||
|
stdout = stdout.decode("utf-8")
|
||||||
|
lines = stdout.split('\n')
|
||||||
|
if "Interface opened" in lines[1]:
|
||||||
|
if len(lines) > 6:
|
||||||
|
badge_type = lines[4].replace(' ', ' ')
|
||||||
|
if '00 04' in badge_type:
|
||||||
|
result = {'status': 'OK'}
|
||||||
|
break
|
||||||
|
else: # Si le badge n'est pas compatble avec le badge cloner.
|
||||||
|
result = {'status': 'ERROR', 'message': 'Badge non compatible !'}
|
||||||
|
break
|
||||||
|
else :
|
||||||
|
result = {'status': 'ERROR', 'message': 'Lecteur NFC non connecté !'}
|
||||||
|
break
|
||||||
|
return json.dumps(result)
|
||||||
|
|
||||||
|
# Permet de lire et copier le badge du client (Route appellée avec du JS depuis la page waitingBadge.html)
|
||||||
|
@app.route('/readBadge')
|
||||||
|
def readBadge():
|
||||||
|
while True: # Boucle infinie tant que le badge n'est pas detecté.
|
||||||
|
result = {'Error': '1'}
|
||||||
|
stdout, stderr, return_code = runCommand('nfc-list')
|
||||||
|
stdout = stdout.decode("utf-8")
|
||||||
|
lines = stdout.split('\n')
|
||||||
|
if "Interface opened" in lines[1]:
|
||||||
|
if len(lines) > 6:
|
||||||
|
badge_type = lines[4].replace(' ', ' ')
|
||||||
|
if '00 04' in badge_type:
|
||||||
|
badge_UID = lines[5].replace('UID (NFCID1): ', '').replace(' ', '')
|
||||||
|
if os.path.isfile('%s/%s.dmp' %(DUMPS_DIR, badge_UID)) : #Si un dump existe déjà pour cet UID
|
||||||
|
result = {'status': 'OK', 'UID': badge_UID}
|
||||||
|
break
|
||||||
|
else :
|
||||||
|
stdout, stderr, status_code = runCommand('mfoc -f %s -P 500 -O %s/%s.dmp' %(KEYFILE, DUMPS_DIR, badge_UID))
|
||||||
|
if status_code == 0: #Si on a réussi à avoir le dump
|
||||||
|
result = {'status': 'OK', 'UID': badge_UID}
|
||||||
|
break
|
||||||
|
else :
|
||||||
|
result = {'status': 'ERROR', 'message': 'Impossible de cracker le badge !'}
|
||||||
|
break
|
||||||
|
else: # Si le badge n'est pas compatble avec le badge cloner.
|
||||||
|
result = {'status': 'ERROR', 'message': 'Badge non compatible !'}
|
||||||
|
break
|
||||||
|
else :
|
||||||
|
result = {'status': 'ERROR', 'message': 'Lecteur NFC non connecté !'}
|
||||||
|
break
|
||||||
|
return json.dumps(result)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# Page d'attente des badges à cloner
|
||||||
|
@app.route('/writeBadge/<nbBadge>/<uid>')
|
||||||
|
def writeBadge(nbBadge, uid):
|
||||||
|
if request.args.get("error"): # On affiche l'erreur si il y en a une.
|
||||||
|
error = request.args.get("error")
|
||||||
|
return render_template('writeBadge.html', nbBadge=int(nbBadge), uid=uid, error=error)
|
||||||
|
return render_template('writeBadge.html', nbBadge=int(nbBadge), uid=uid)
|
||||||
|
|
||||||
|
#Permet de cloner les badges
|
||||||
|
@app.route('/copyBadge/<uid>')
|
||||||
|
def copyBadge(uid):
|
||||||
|
while True: # Boucle infinie tant que le badge n'est pas detecté.
|
||||||
|
result = {'Error': '1'}
|
||||||
|
stdout, stderr, return_code = runCommand('nfc-list')
|
||||||
|
stdout = stdout.decode("utf-8")
|
||||||
|
lines = stdout.split('\n')
|
||||||
|
if "Interface opened" in lines[1]:
|
||||||
|
if len(lines) > 6:
|
||||||
|
badge_type = lines[4].replace(' ', ' ')
|
||||||
|
if '00 04' in badge_type:
|
||||||
|
stdout, stderr, status_code = runCommand('mfoc -P 500 -O %s/new.dmp' %(DUMPS_DIR))
|
||||||
|
print(stdout)
|
||||||
|
print(status_code)
|
||||||
|
if status_code == 0: #Si on a réussi à avoir le dump
|
||||||
|
stdout, stderr, status_code = runCommand('nfc-mfclassic W a %s/%s.dmp %s/new.dmp' %(DUMPS_DIR, uid, DUMPS_DIR))
|
||||||
|
print(stdout)
|
||||||
|
print(status_code)
|
||||||
|
if status_code == 0: #Si on a réussi à copier
|
||||||
|
result = {'status': 'OK', 'message': 'Badge copié !'}
|
||||||
|
break
|
||||||
|
else :
|
||||||
|
result = {'status': 'ERROR', 'message': 'Avez-vous mis un badge réinscriptible ?'}
|
||||||
|
break
|
||||||
|
else :
|
||||||
|
result = {'status': 'ERROR', 'message': 'Impossible d\'écrire sur ce badge'}
|
||||||
|
break
|
||||||
|
else: # Si le badge n'est pas compatble avec le badge cloner.
|
||||||
|
result = {'status': 'ERROR', 'message': 'Badge non compatible !'}
|
||||||
|
break
|
||||||
|
else :
|
||||||
|
result = {'status': 'ERROR', 'message': 'Lecteur NFC non connecté !'}
|
||||||
|
break
|
||||||
|
return json.dumps(result)
|
||||||
|
|
||||||
|
@app.route('/wait')
|
||||||
|
def wait():
|
||||||
|
raison = request.args.get("raison")
|
||||||
|
redirect = request.args.get("redirect")
|
||||||
|
return render_template('wait.html',raison=raison, redirect=redirect)
|
||||||
|
|
||||||
|
|
||||||
|
app.run(host=HOST, port=PORT)
|
||||||
|
### Fin partie Flask ###
|
||||||
32
templates/index.html
Normal file
32
templates/index.html
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="fr">
|
||||||
|
<head>
|
||||||
|
<title>Badge Cloner</title>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
||||||
|
<meta name="author" content="j4rj4r">
|
||||||
|
<link rel="stylesheet" href="res/css/bulma/bulma.min.css">
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="container is-fluid">
|
||||||
|
<section class="hero">
|
||||||
|
<div class="hero-body">
|
||||||
|
<div class="container has-text-centered">
|
||||||
|
<h1 class="title is-spaced">Badge Cloner</h1>
|
||||||
|
{% if error is defined %}
|
||||||
|
<p class="has-text-danger"> {{ error }}</p>
|
||||||
|
{% endif %}
|
||||||
|
<h2 class="subtitle">Choisir le nombre de badges à cloner :</h2>
|
||||||
|
<div class=" is-centered">
|
||||||
|
<form action="/waitingBadge" method="get">
|
||||||
|
<input name="nbBadge" class="input" min="1" value="1" required type="number"/>
|
||||||
|
<hr>
|
||||||
|
<button class="control button is-primary is-large">Clonage</button>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
22
templates/wait.html
Normal file
22
templates/wait.html
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="fr">
|
||||||
|
<head>
|
||||||
|
<title>Badge Cloner</title>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
||||||
|
<meta name="author" content="j4rj4r">
|
||||||
|
<link rel="stylesheet" href="res/css/bulma/bulma.min.css">
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="container is-fluid">
|
||||||
|
<section class="hero"><div class="hero-body">
|
||||||
|
<div class="container has-text-centered">
|
||||||
|
<h1 class="title is-spaced">Page d'attente</h1>
|
||||||
|
<h2 id="info" class="subtitle">{{raison}}</h2>
|
||||||
|
<a href="{{redirect}}" class="button is-link">Suivant</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
48
templates/waitingBadge.html
Normal file
48
templates/waitingBadge.html
Normal file
@ -0,0 +1,48 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="fr">
|
||||||
|
<head>
|
||||||
|
<title>Badge Cloner</title>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
||||||
|
<meta name="author" content="j4rj4r">
|
||||||
|
<link rel="stylesheet" href="res/css/bulma/bulma.min.css">
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="container is-fluid">
|
||||||
|
<section class="hero"><div class="hero-body">
|
||||||
|
<div class="container has-text-centered">
|
||||||
|
<h1 class="title is-spaced">Badge du client</h1>
|
||||||
|
<h2 id="info" class="subtitle">En attente du badge à copier ...</h2>
|
||||||
|
<a href="/" class="button is-link">Annuler</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
|
<script>
|
||||||
|
var xhr = new XMLHttpRequest();
|
||||||
|
xhr.open('GET', '/detectBadge', true);
|
||||||
|
xhr.onload = function() {
|
||||||
|
var jsonreponse = JSON.parse(xhr.response);
|
||||||
|
if (jsonreponse.status == "OK") {
|
||||||
|
document.getElementById("info").textContent = "Tentative de copie du badge ...";
|
||||||
|
|
||||||
|
var xhr2 = new XMLHttpRequest();
|
||||||
|
xhr2.open('GET', '/readBadge', true);
|
||||||
|
xhr2.onload = function() {
|
||||||
|
var jsonreponse = JSON.parse(xhr2.response);
|
||||||
|
if (jsonreponse.status == "OK") {
|
||||||
|
window.location.href = "/wait?raison=Appuyer%20sur%20le%20bouton%20pour%20commencer%20la%20copie%20des%20badges.&redirect=/writeBadge/{{nbBadge}}/" + jsonreponse.UID;
|
||||||
|
} else {
|
||||||
|
window.location.href = "/?error=" + jsonreponse.message;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
xhr2.send(null);
|
||||||
|
} else {
|
||||||
|
window.location.href = "/?error=" + jsonreponse.message;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
xhr.send(null);
|
||||||
|
</script>
|
||||||
52
templates/writeBadge.html
Normal file
52
templates/writeBadge.html
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="fr">
|
||||||
|
<head>
|
||||||
|
<title>Badge Cloner</title>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
||||||
|
<meta name="author" content="j4rj4r">
|
||||||
|
<link rel="stylesheet" href="/res/css/bulma/bulma.min.css">
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="container is-fluid">
|
||||||
|
<section class="hero"><div class="hero-body">
|
||||||
|
<div class="container has-text-centered">
|
||||||
|
<h1 class="title is-spaced">Vos badges</h1>
|
||||||
|
<h2 class="subtitle">En attente du badge numéro {{nbBadge}}</h2>
|
||||||
|
{% if error is defined %}
|
||||||
|
<p class="has-text-danger"> {{ error }}</p>
|
||||||
|
{% endif %}
|
||||||
|
<a href="/" class="button is-link">Annuler</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
|
<script>
|
||||||
|
if ({{nbBadge}} >= 1) {
|
||||||
|
var xhr = new XMLHttpRequest();
|
||||||
|
xhr.open('GET', '/copyBadge/{{uid}}', true);
|
||||||
|
|
||||||
|
xhr.onload = function() {
|
||||||
|
var jsonreponse = JSON.parse(xhr.response);
|
||||||
|
if (jsonreponse.status == "OK") {
|
||||||
|
//console.log("Badge cloné")
|
||||||
|
if ({{nbBadge-1}} == 0 ){
|
||||||
|
window.location.href = "/wait?raison=Tous%20les%20badges%20sont%20copi%C3%A9s%20%21&redirect=/";
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
window.location.href = "/wait?raison=Badge%20clon%C3%A9%20%21%20Appuyer%20sur%20le%20bouton%20pour%20passer%20au%20badge%20suivant.&redirect=/writeBadge/{{nbBadge-1}}/{{uid}}";
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
window.location.href = "/writeBadge/{{nbBadge}}/{{uid}}" + "?error=" + jsonreponse.message;
|
||||||
|
}
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
xhr.send(null);
|
||||||
|
|
||||||
|
} else {
|
||||||
|
window.location.href = "/"
|
||||||
|
}
|
||||||
|
</script>
|
||||||
Loading…
x
Reference in New Issue
Block a user