changé bcp de truc

This commit is contained in:
Djalim Simaila 2023-12-18 10:55:05 +01:00
parent 5e2fc16cc3
commit f856b77e64
15 changed files with 696 additions and 267 deletions

2
.gitignore vendored
View File

@ -1,2 +1,2 @@
*__pycache
**__pycache__**
.vscode

BIN
Clients/MacOs/macos.db Executable file

Binary file not shown.

View File

@ -0,0 +1,7 @@
import sqlite3
db = '/var/folders/zw/y1xldrn518s3frdh6jhc97900000gn/0/com.apple.notificationcenter/db2/db'
con = sqlite3.connect(db)
cur = con.cursor()
test = cur.execute("tables").fetchall()
print(test)

View File

@ -1,3 +1,3 @@
# BloatProject
# FullSync
Syncro de notification mon phone et mon pc + up checker

View File

@ -0,0 +1,16 @@
import typing
class Clipboard:
"""
Clipboard model
"""
def __init__(self,id:int = 0,timestamp:int = 0 ,device_name:str = "",token:str="",content:str="") -> None:
self.id: int = id
self.timestamp: int = timestamp
self.device_name: str = device_name
self.token: str = token
self.content: str = content
def __str__(self) -> str:
return f"{self.id} {self.timestamp} {self.device_name} {self.token} {self.content}"

View File

@ -0,0 +1,131 @@
from typing import Union,List
from Models.BaseModels.Clipboard import Clipboard
from Models.BaseModels.Notification import Notification
class BaseDb:
"""
DB Model
"""
def first_run()->None:
"""
Dans cette fonction on créé la database ainsi que les différentes collections de celle-ci
"""
...
def authentificate_user(username, password)->Union[bool, str]:
"""
Cette fonction authentifie un user, elle retourne un token si l'authentification a reussi
args:
username: str (le nom d'utilisateur)
password: str (le mot de passe)
return:
Union[bool, str]
"""
...
def register(username, password) -> bool:
"""
Cette fonction register un user, elle retourne True si l'operation a réussi
args:
username: str (le nom d'utilisateur)
password: str (le mot de passe)
return:
bool
"""
...
###
def add_notification(token, title, content, device_name) -> bool:
"""
Cette fonction ajoute une notification dans la DB, elle retourne True si l'operation a réussi
args:
token: str (token d'identification de l'utilisateur)
title: str (titre de la notification)
content: str (contenu de la notification)
device_name: str (nom de l'appareil duquel vient la notification)
return:
bool
"""
...
def get_notification(token)->Union[bool, List[Notification]]:
"""
Trouve les notifications dans la DB
args:
token: str (token d'identification de l'utilisateur)
return:
Union[bool, List[Notification]
"""
...
def get_notification_by_id(token, id) -> Union[bool, Notification]:
"""
Trouve une notification dans la DB, retourne la notification si trouvée, ou False
args:
token: str (token d'identification de l'utilisateur)
id: str (identifiant de la notification)
return:
Union[bool, Notification]
"""
...
###
def add_clipboard(token, content, device_name) -> bool:
"""
Cette fonction ajoute le contenu du clipboard dans la DB, elle retourne True si l'operation a réussi
args:
token: str (token d'identification de l'utilisateur)
content: str (contenu de la copie)
device_name: str (nom de l'appareil duquel vient le clipboard)
return:
bool
"""
...
def get_clipboard(token) -> Union[bool, List[Clipboard]]:
"""
Trouve les clipboard dans la DB
args:
token: str (token d'identification de l'utilisateur)
return:
Union[bool, List[Clipboard]
"""
...
def get_clipboard_by_id(token, id) -> Union[bool, Clipboard]:
"""
Trouve un clipboard dans la DB, retourne le clipboard si trouvé, ou False
args:
token: str (token d'identification de l'utilisateur)
id: str (identifiant du clipboard)
return:
Union[bool, Clipboard]
"""
...

View File

@ -0,0 +1,14 @@
class Notification:
"""
Notification model
"""
def __init__(self,id: int = 0,timestamp: int = 0,device_name: str = "",token: str = "",title: str = "",content: str = "") -> None:
self.id: int = id
self.timestamp: int = timestamp
self.device_name: str = device_name
self.token: str = token
self.title: str = title
self.content: str = content
def __str__(self) -> str:
return f"{self.id} {self.timestamp} {self.device_name} {self.token}"

View File

View File

@ -0,0 +1,151 @@
import sys
import secrets
import time
from typing import Union,List
from pymongo import MongoClient
from Models.BaseModels.Clipboard import Clipboard
from Models.BaseModels.Notification import Notification
from Models.BaseModels.DB import BaseDb
client = MongoClient('simailadjalim.fr:27017',
username='ANOTHER_USER',
password='PASS',
authSource='FullSync',
authMechanism='SCRAM-SHA-256')
try:
client.admin.command('ping')
print("Pinged your deployment. You successfully connected to MongoDB!")
except Exception as e:
print(e)
sys.exit("Could not connect to MongoDB.")
db = client["FullSync"]
class Mongo(BaseDb):
def first_run(self)->None:
db.create_collection("User")
db.create_collection("Clipboard")
db.create_collection("Notification")
###############################################################################
def authentificate_user(self,username, password) -> Union[bool, str]:
user = db.User.find_one({"username": username, "password": password})
if user is None:
return False
else:
return user["token"]
def register(self,username, password) -> bool:
# check for username already existing
user = db.User.find_one({"username": username, "password": password})
if user is not None:
print("username already taken")
return False
# add user in db
token = secrets.token_urlsafe(64)
try:
db.User.insert_one({"username": username, "password": password, "token": token})
return True
except:
return False
###############################################################################
def add_notification(self,token, title, content, device_name) -> bool:
# check if token is valid
user = db.User.find_one({"token": token})
if user is None:
print("no user")
return False
# add notification in db
db.Notification.insert_one({"timestamp": time.time(),
"device_name": device_name,
"token": token,
"title": title,
"content": content})
return True
def get_notification(self,token) -> Union[bool, List[Notification]]:
# check if token is valid
user = db.User.find_one({"token": token})
if user is None:
print("no user")
return False
# get all notification in db for this token
db_notifications = db.Notification.find({"token": token})
notifications = []
for notification in db_notifications:
notifications.append(Notification(0,
notification["timestamp"],
notification["device_name"],
notification["token"],
notification["title"],
notification["content"]))
return notifications
def get_notification_by_id(self,token, id) -> Union[bool, Notification]:
# check if token is valid
user = db.User.find_one({"token": token})
if user is None:
print("no user")
return False
# get notification in db for this token and this notification id
db_notifications = db.Notification.find_one({"_id":id,"token": token})
notification = Notification(0,
db_notifications["timestamp"],
db_notifications["device_name"],
db_notifications["token"],
db_notifications["title"],
db_notifications["content"])
return notification
###############################################################################
def add_clipboard(self,token, content, device_name) -> bool:
user = db.User.find_one({"token": token})
if user is None:
print("no user")
return False
db.Clipboard.insert_one({"timestamp": time.time(),
"device_name": device_name,
"token": token,
"content": content})
return True
def get_clipboard(self,token) -> Union[bool, List[Clipboard]]:
#check if token is valid
user = db.User.find_one({"token": token})
if user is None:
print("no user")
return False
db_clipboards = db.Clipboard.find({"token": token})
clipboards = []
for clipboard in db_clipboards:
clipboards.append(Clipboard(0,
clipboard["timestamp"],
clipboard["device_name"],
clipboard["token"],
clipboard["content"]))
return clipboards
def get_clipboard_by_id(self,token, id) -> Union[bool, Clipboard]:
#check if token is valid
user = db.User.find_one({"token": token})
if user is None:
print("no user")
return False
# get clipboard in db for this token and this clipboard id
db_clipboard = db.ClipBoard.find_one({"_id":id,"token": token})
clipboard = Clipboard(0,
db_clipboard["timestamp"],
db_clipboard["device_name"],
db_clipboard["token"],
db_clipboard["content"])
return clipboard

BIN
Server/Models/SQLite/database.db Executable file

Binary file not shown.

View File

@ -0,0 +1,208 @@
import sqlite3
import secrets
import time
from typing import Union,List
from Models.BaseModels.Clipboard import Clipboard
from Models.BaseModels.Notification import Notification
from Models.BaseModels.DB import BaseDb
class SQLite(BaseDb):
def first_run(self) -> None:
"""
create databases
"""
con = sqlite3.connect("database.db")
cur = con.cursor()
cur.execute("CREATE TABLE USERS(\
username,\
password,\
token)")
cur.execute("CREATE TABLE NOTIFICATION(\
id INTEGER PRIMARY KEY AUTOINCREMENT,\
date,\
machine,\
token,\
title,\
content)")
cur.execute("CREATE TABLE CLIPBOARD(\
id INTEGER PRIMARY KEY AUTOINCREMENT,\
date,\
machine,\
token,\
content)")
con.commit()
con.close()
###############################################################################
def authentificate_user(self,username, password) -> Union[bool, str]:
"""
Authentifie un user, simple, basique, orelsan
"username"
"password"
"""
con = sqlite3.connect("database.db")
cur = con.cursor()
db_user = cur.execute("SELECT token FROM USERS WHERE USERNAME=? AND \
PASSWORD=?", username, password).fetchone()
con.close()
if db_user is None:
return None
else:
return db_user[0]
def register(self,username, password) -> bool:
"""
inscrit un user, simple, basique, orelsan
"username"
"password"
"""
# check for username already existing
con = sqlite3.connect("database.db")
cur = con.cursor()
if cur.execute("SELECT username FROM USERS WHERE username=?", user)\
.fetchone() is not None:
con.close()
return False, "Error, username already taken"
# add user in db
user = (username, password,
secrets.token_urlsafe(64))
try:
cur.execute("INSERT INTO USERS VALUES (?,?,?)", user)
con.commit()
con.close()
return True
except:
con.close()
return False, "Error, most likely username already taken"
###############################################################################
def add_notification(self,token, title, content, device_name) -> bool:
"""
Ajoute une notification dans la DB
"""
date = time.time()
con = sqlite3.connect("database.db")
cur = con.cursor()
if cur.execute("SELECT username FROM USERS WHERE token=?", (token,))\
.fetchone() is None:
return False, "Error, no user"
try:
notification = (date, device_name, token, title, content)
cur.execute("INSERT INTO notification VALUES (null,?,?,?,?,?)",
notification)
con.commit()
con.close()
return True
except:
return False, "error"
def get_notification(self,token) -> Union[bool, List[Notification]]:
"""
Trouve les notifications dans la DB
"""
con = sqlite3.connect("database.db")
cur = con.cursor()
db_notifications = cur.execute("SELECT * \
FROM NOTIFICATION \
WHERE token=?",
(token, )).fetchall()
list_notifications = []
for n in db_notifications:
notif = Notification(*n)
list_notifications.append(notif)
return list_notifications
def get_notification_by_id(self,token, id) -> Union[bool, Notification]:
"""
Trouve la notification dans la DB avec son id
"""
con = sqlite3.connect("database.db")
cur = con.cursor()
if id == -1:
db_notifications = cur.execute("SELECT * \
FROM NOTIFICATION \
WHERE token=?\
ORDER BY id DESC \
LIMIT 1",
(token,)).fetchone()
else:
db_notifications = cur.execute("SELECT * \
FROM NOTIFICATION \
WHERE token=? AND id=?",
(token, id)).fetchone()
list_notifications = []
for n in db_notifications:
notif = Notification(*n)
list_notifications.append(notif)
return list_notifications
###############################################################################
def add_clipboard(self,token, content, device_name) -> bool:
"""
Ajoute un clipboard dans la DB
"""
date = time.time()
con = sqlite3.connect("database.db")
cur = con.cursor()
if cur.execute("SELECT username FROM USERS WHERE token=?", (token,))\
.fetchone() is None:
return False, "Error, no user"
try:
clipboard = (date, device_name, token, content)
cur.execute("INSERT INTO CLIPBOARD VALUES (null,?,?,?,?)", clipboard)
con.commit()
con.close()
return True
except:
return False, "error"
def get_clipboard(self,token) -> Union[bool, List[Clipboard]]:
"""
Trouves les clipboard dans la DB
"""
con = sqlite3.connect("database.db")
cur = con.cursor()
db_clipboard = cur.execute("SELECT * \
FROM CLIPBOARD \
WHERE token=?",
(token, )).fetchall()
list_clipboard = []
for c in db_clipboard:
clip = Clipboard(*c)
list_clipboard.append(clip)
return True, list_clipboard
def get_clipboard_by_id(self,token, id) -> Union[bool, Clipboard]:
"""
Trouve le clipbard dans le DB avec son id
"""
con = sqlite3.connect("database.db")
cur = con.cursor()
if id == -1:
db_clipboard = cur.execute("SELECT * \
FROM CLIPBOARD \
WHERE token=? \
ORDER BY id DESC \
LIMIT 1",
(token,)).fetchone()
else:
db_clipboard = cur.execute("SELECT * \
FROM CLIPBOARD \
WHERE token=? AND id=?",
(token, id)).fetchone()
return True, Clipboard(*db_clipboard)

167
Server/app.py Normal file
View File

@ -0,0 +1,167 @@
#!/bin/python
import hashlib
import sqlite3
import secrets
import time
import flask_socketio
from flask import Flask, request
from Models.BaseModels.DB import BaseDb
# base sock
app = Flask(__name__)
socketio = flask_socketio.SocketIO(app)
db_to_use = "mongodb"
db: BaseDb = None
@app.route("/user", methods=['POST'])
def auth():
"""
Authentifie un user, simple, basique
"username"
"password"
"""
token = db.authentificate_user(request.values.get("username"),
request.values.get("password"))
if token is False:
return {"status": "This user does not exist or the password is \
incorrect"}, 404
else:
return {"status": "ok", "token": token}
@app.route("/user", methods=['PUT'])
def register():
"""
inscrit un user, simple, basique
"username"
"password"
"""
username = request.values.get("username")
password = request.values.get("password")
status = db.register(username, password)
if status is False:
return {"status": "Error, most likely username already taken"}, 500
return {"status": "ok"}, 200
###############################################################################
@app.route("/notification", methods=['PUT'])
def add_notification():
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
token = request.values.get("token")
title = request.values.get('title')
content = request.values.get('content')
device_name = request.values.get('deviceName')
date = time.time()
if db.add_notification(token, title, content, device_name) is False:
return {"status": "Error, no user"}, 500
else:
socketio.emit("NotificationUpdate",
data={"device_name": device_name})
return {"status": "ok"}, 200
@app.route("/notification", methods=['GET'])
def get_notifications():
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
token = request.values.get("token")
notifications = db.get_notification(token)
if notifications is False:
return {"status": "Error, no user"}, 500
data = {"status": "ok"}
notifications = [notif.__dict__ for notif in notifications]
data["notifications"] = notifications
return data, 200
@app.route("/notification/<notifid>", methods=['GET'])
def get_notification_by_id(notifid):
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
notifid = int(notifid)
token = request.values.get("token")
notification = db.get_notification_by_id(token, notifid)
if notification is False:
return {"status": "Error, no user"}, 500
data = {"status": "ok"}
data["notification"] = notification.__dict__
return data, 200
###############################################################################
@app.route("/clipboard", methods=['PUT'])
def add_clipboard():
"""
Le but de cet app se resume a cette fonction, elle recoit une requete http
et renvoie via le websocket le contenu de la requette a tout les clients.
"""
token = request.values.get("token")
content = request.values.get('content')
device_name = request.values.get('deviceName')
if db.add_clipboard(token, content, device_name) is False:
return {"status": "Error, no user"}, 500
else:
socketio.emit("ClipboardUpdate",
data={"device_name": device_name})
return {"status": "ok"}, 200
@app.route("/clipboard", methods=['GET'])
def get_clipboard():
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
token = request.values.get("token")
clipboard = db.get_clipboard(token)
if clipboard is False:
return {"status": "Error, no user"}, 500
clipboard = [clip.__dict__ for clip in clipboard]
return {"status": "ok", "clipboard": clipboard}, 200
@app.route("/clipboard/<clipid>", methods=['GET'])
def get_clipboard_by_id(clipid):
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
clipid = int(clipid)
token = request.values.get("token")
clipboard = db.get_clipboard_by_id(token, clipid)
if clipboard is False:
return {"status": "Error, no user"}, 500
clipboard = clipboard.__dict__
return {"status": "ok", "clipboard": clipboard}, 200
if __name__ == '__main__':
match db_to_use:
case "mongodb":
from Models.MongoDb.mongodb import Mongo
db:BaseDb = Mongo()
case "sqlite":
from Models.SQLite.sqlite import SQLite
db:BaseDb = SQLite()
case _:
print("undefined db")
exit()
socketio.run(app, host="0.0.0.0", port=9564)

View File

@ -1,265 +0,0 @@
#!/bin/python
import hashlib
import sqlite3
import secrets
import time
import flask_socketio
from flask import Flask, request
# base socket
app = Flask(__name__)
socketio = flask_socketio.SocketIO(app)
###############################################################################
def first_run():
"""
create databases
"""
con = sqlite3.connect("database.db")
cur = con.cursor()
cur.execute("CREATE TABLE USERS(\
username,\
password,\
token)")
cur.execute("CREATE TABLE NOTIFICATION(\
id INTEGER PRIMARY KEY AUTOINCREMENT,\
date,\
machine,\
token,\
title,\
content)")
cur.execute("CREATE TABLE CLIPBOARD(\
id INTEGER PRIMARY KEY AUTOINCREMENT,\
date,\
machine,\
token,\
content)")
con.commit()
con.close()
###############################################################################
@app.route("/user", methods=['POST'])
def auth():
"""
Authentifie un user, simple, basique
"username"
"password"
"""
user = (request.values.get("username"), request.values.get("password"))
con = sqlite3.connect("database.db")
cur = con.cursor()
db_user = cur.execute("SELECT token FROM USERS WHERE USERNAME=? AND \
PASSWORD=?", user).fetchone()
con.close()
if db_user is None:
return {"status": "This user does not exist or the password is \
incorrect"}, 404
else:
return {"status": "ok", "token": db_user[0]}
@app.route("/user", methods=['PUT'])
def register():
"""
Authentifie un user, simple, basique
"username"
"password"
"""
con = sqlite3.connect("database.db")
cur = con.cursor()
username = request.values.get("username")
user = (username,)
if cur.execute("SELECT username FROM USERS WHERE username=?", user)\
.fetchone() is not None:
con.close()
return {"status": "Error, username already taken"}, 500
user = (request.values.get("username"), request.values.get("password"),
secrets.token_urlsafe(64))
try:
cur.execute("INSERT INTO USERS VALUES (?,?,?)", user)
con.commit()
con.close()
return {"status": "ok"}
except:
con.close()
return {"status": "Error, most likely username already taken"}, 500
###############################################################################
@app.route("/notification", methods=['PUT'])
def add_notification():
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
token = request.values.get("token")
title = request.values.get('title')
content = request.values.get('content')
device_name = request.values.get('deviceName')
date = time.time()
con = sqlite3.connect("database.db")
cur = con.cursor()
if cur.execute("SELECT username FROM USERS WHERE token=?", (token,))\
.fetchone() is None:
return {"status": "Error, no user"}, 500
try:
notification = (date, device_name, token, title, content)
cur.execute("INSERT INTO notification VALUES (null,?,?,?,?,?)",
notification)
con.commit()
con.close()
socketio.emit("NotificationUpdate",
data={"device_name": device_name},
broadcast=True)
return {"status": "ok"}, 200
except:
return {"status": "error"}, 500
@app.route("/notification", methods=['GET'])
def get_notifications():
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
token = request.values.get("token")
con = sqlite3.connect("database.db")
cur = con.cursor()
notifications = cur.execute("SELECT * \
FROM NOTIFICATION \
WHERE token=?",
(token, )).fetchall()
data = {"status": "ok"}
data["notifications"] = []
for notification in notifications:
data["notifications"].append()
return data, 200
@app.route("/notification/<notifid>", methods=['GET'])
def get_notification_by_id(notifid):
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
notifid = int(notifid)
token = request.values.get("token")
con = sqlite3.connect("database.db")
cur = con.cursor()
if notifid == -1:
notifications = cur.execute("SELECT * \
FROM NOTIFICATION \
WHERE token=?\
ORDER BY id DESC \
LIMIT 1",
(token,)).fetchone()
else:
notifications = cur.execute("SELECT * \
FROM NOTIFICATION \
WHERE token=? AND id=?",
(token, notifid)).fetchone()
return {"status": "ok",
"notifications": notifications
}, 200
###############################################################################
def clipFromArray(clip):
return {"id": clip[0],
"timestamp": clip[1],
"deviceName": clip[2],
"token": clip[3],
"content": clip[3]}
@app.route("/clipboard", methods=['PUT'])
def add_clipboard():
"""
Le but de cet app se resume a cette fonction, elle recoit une requete http
et renvoie via le websocket le contenu de la requette a tout les clients.
"""
token = request.values.get("token")
content = request.values.get('content')
device_name = request.values.get('deviceName')
date = time.time()
con = sqlite3.connect("database.db")
cur = con.cursor()
if cur.execute("SELECT username FROM USERS WHERE token=?", (token,))\
.fetchone() is None:
return {"status": "Error, no user"}, 500
try:
clipboard = (date, device_name, token, content)
cur.execute("INSERT INTO CLIPBOARD VALUES (null,?,?,?,?)", clipboard)
con.commit()
con.close()
socketio.emit("ClipboardUpdate",
data={"device_name": device_name},
broadcast=True)
return {"status": "ok"}, 200
except:
return {"status": "error"}, 500
@app.route("/clipboard", methods=['GET'])
def get_clipboard():
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
token = request.values.get("token")
con = sqlite3.connect("database.db")
cur = con.cursor()
clipboard = cur.execute("SELECT * \
FROM CLIPBOARD \
WHERE token=?",
(token, )).fetchall()
clipboard = [clipFromArray(clip) for clip in clipboard]
return {"status": "ok", "clipboard": clipboard}, 200
@app.route("/clipboard/<clipid>", methods=['GET'])
def get_clipboard_by_id(clipid):
"""
Le but de cet app se resume a cette fonction, elle recoit une requete
http et renvoie via le websocket le contenu de la requette a tout les
client.
"""
clipid = int(clipid)
token = request.values.get("token")
con = sqlite3.connect("database.db")
cur = con.cursor()
if clipid == -1:
clipboard = cur.execute("SELECT * \
FROM CLIPBOARD \
WHERE token=? \
ORDER BY id DESC \
LIMIT 1",
(token,)).fetchone()
else:
clipboard = cur.execute("SELECT * \
FROM CLIPBOARD \
WHERE token=? AND id=?",
(token, clipid)).fetchone()
return {"status": "ok", "clipboard": clipFromArray(clipboard)}, 200
if __name__ == '__main__':
try:
f=open("database.db","r")
f.close()
except :
first_run()
socketio.run(app, host="0.0.0.0", port=9564)