add /admin/chat and dont store profile_url in chat dict

pull/90/head
Aevann 2023-01-20 06:10:25 +02:00
parent 1919fc822a
commit acc71d4cae
6 changed files with 69 additions and 56 deletions

View File

@ -32931,7 +32931,6 @@
themeColor,
siteName,
nameColor,
avatar,
hat
},
setContext
@ -32943,7 +32942,6 @@
themeColor: "#ff66ac",
siteName: "",
nameColor: "",
avatar: "",
hat: ""
});
(0, import_react13.useEffect)(() => {
@ -32956,7 +32954,6 @@
themeColor: root2.dataset.themecolor,
siteName: root2.dataset.sitename,
nameColor: root2.dataset.namecolor,
avatar: root2.dataset.avatar,
hat: root2.dataset.hat
});
}, []);
@ -32968,7 +32965,6 @@
themeColor,
siteName,
nameColor,
avatar,
hat
};
}
@ -33014,7 +33010,7 @@
var DIRECT_MESSAGE_ID = "DIRECT_MESSAGE";
var OPTIMISTIC_MESSAGE_ID = "OPTIMISTIC";
function ChatProvider({ children }) {
const { username, id, siteName, hat, avatar, nameColor } = useRootContext();
const { username, id, siteName, hat, nameColor } = useRootContext();
const socket = (0, import_react15.useRef)(null);
const [online, setOnline] = (0, import_react15.useState)([]);
const [typing, setTyping] = (0, import_react15.useState)([]);
@ -33054,7 +33050,6 @@
id: DIRECT_MESSAGE_ID,
username,
user_id: id,
avatar,
hat,
namecolor: nameColor,
text: directMessage,
@ -33070,7 +33065,6 @@
id: OPTIMISTIC_MESSAGE_ID,
username,
user_id: id,
avatar,
hat,
namecolor: nameColor,
text: draft,
@ -33485,14 +33479,14 @@
// src/features/chat/Username.tsx
var import_react20 = __toESM(require_react());
function Username({ avatar, color, name, hat = "" }) {
function Username({ id, color, name, hat = "" }) {
return /* @__PURE__ */ import_react20.default.createElement("div", {
className: "Username"
}, /* @__PURE__ */ import_react20.default.createElement("div", {
className: "profile-pic-20-wrapper"
}, /* @__PURE__ */ import_react20.default.createElement("img", {
alt: name,
src: avatar,
src: `/pp/${id}`,
className: "pp20"
}), hat && /* @__PURE__ */ import_react20.default.createElement("img", {
className: "avatar-hat profile-pic-20-hat hat",
@ -33559,7 +33553,6 @@
const {
id,
user_id,
avatar,
namecolor,
username,
hat,
@ -33676,10 +33669,10 @@
}, /* @__PURE__ */ import_react22.default.createElement("i", null, "X"), " Close")), showUser && /* @__PURE__ */ import_react22.default.createElement("div", {
className: "ChatMessage-top"
}, /* @__PURE__ */ import_react22.default.createElement(Username, {
avatar,
id: user_id,
name: username,
color: namecolor,
hat
hat,
}), /* @__PURE__ */ import_react22.default.createElement("div", {
className: "ChatMessage-timestamp"
}, timestamp)), quotes && quotedMessage && /* @__PURE__ */ import_react22.default.createElement("div", {

View File

@ -2,7 +2,7 @@ import atexit
import time
import uuid
from flask_socketio import SocketIO, emit
from flask_socketio import SocketIO, emit, join_room, leave_room
from files.helpers.actions import *
from files.helpers.alerts import *
@ -28,12 +28,20 @@ else:
async_mode='gevent',
)
typing = []
online = []
typing = {
f'{SITE_FULL}/chat': [],
f'{SITE_FULL}/admin/chat': []
}
online = []
cache.set(CHAT_ONLINE_CACHE_KEY, len(online), timeout=0)
muted = cache.get(f'{SITE}_muted') or {}
messages = cache.get(f'{SITE}_chat') or []
total = cache.get(f'{SITE}_total') or 0
muted = cache.get(f'muted') or {
f'{SITE_FULL}/chat': {},
f'{SITE_FULL}/admin/chat': {}
}
messages = cache.get(f'messages') or {
f'{SITE_FULL}/chat': [],
f'{SITE_FULL}/admin/chat': []
}
socket_ids_to_user_ids = {}
user_ids_to_socket_ids = {}
@ -42,8 +50,12 @@ user_ids_to_socket_ids = {}
def chat(v):
if not v.admin_level and TRUESCORE_CHAT_MINIMUM and v.truescore < TRUESCORE_CHAT_MINIMUM:
abort(403, f"Need at least {TRUESCORE_CHAT_MINIMUM} truescore for access to chat.")
return render_template("chat.html", v=v, messages=messages)
return render_template("chat.html", v=v)
@app.get("/admin/chat")
@admin_level_required(2)
def admin_chat(v):
return render_template("chat.html", v=v)
@socketio.on('speak')
@limiter.limit("3/second;10/minute")
@ -56,11 +68,11 @@ def speak(data, v):
return '', 403
vname = v.username.lower()
if vname in muted and not v.admin_level >= PERMS['CHAT_BYPASS_MUTE']:
if time.time() < muted[vname]: return '', 403
else: del muted[vname]
if vname in muted[request.referrer] and not v.admin_level >= PERMS['CHAT_BYPASS_MUTE']:
if time.time() < muted[request.referrer][vname]: return '', 403
else: del muted[request.referrer][vname]
global messages, total
global messages
text = sanitize_raw_body(data['message'], False)[:CHAT_LENGTH_LIMIT]
if not text: return '', 400
@ -71,7 +83,6 @@ def speak(data, v):
data = {
"id": str(uuid.uuid4()),
"quotes": quotes,
"avatar": v.profile_url,
"hat": v.hat_active(v)[0],
"user_id": v.id,
"dm": bool(recipient and recipient != ""),
@ -91,50 +102,50 @@ def speak(data, v):
recipient_sid = user_ids_to_socket_ids[recipient]
emit('speak', data, broadcast=False, to=recipient_sid)
else:
emit('speak', data, broadcast=True)
messages.append(data)
messages = messages[-500:]
total += 1
emit('speak', data, room=request.referrer, broadcast=True)
messages[request.referrer].append(data)
messages[request.referrer] = messages[request.referrer][-500:]
if v.admin_level >= PERMS['USER_BAN']:
text = text.lower()
for i in mute_regex.finditer(text):
username = i.group(1).lower()
duration = int(int(i.group(2)) * 60 + time.time())
muted[username] = duration
muted[request.referrer][username] = duration
typing = []
# if SITE == 'rdrama.net':
# title = f'New chat message from @{v.username}'
# notifbody = text
# url = f'{SITE_FULL}/chat'
if request.referrer == f'{SITE_FULL}/admin/chat':
title = f'New message in admin chat from @{v.username}'
notifbody = text
url = f'{SITE_FULL}/admin/chat'
# admin_ids = [x[0] for x in g.db.query(User.id).filter(
# User.id != v.id,
# User.admin_level >= PERMS['CHAT'],
# ).all()]
admin_ids = [x[0] for x in g.db.query(User.id).filter(
User.id != v.id,
User.admin_level >= PERMS['CHAT'],
).all()]
# push_notif(admin_ids, title, notifbody, url)
push_notif(admin_ids, title, notifbody, url)
return '', 204
@socketio.on('connect')
@admin_level_required(PERMS['CHAT'])
def connect(v):
join_room(request.referrer)
if v.username not in online:
online.append(v.username)
emit("online", online, broadcast=True)
emit("online", online, room=request.referrer, broadcast=True)
cache.set(CHAT_ONLINE_CACHE_KEY, len(online), timeout=0)
if not socket_ids_to_user_ids.get(request.sid):
socket_ids_to_user_ids[request.sid] = v.id
user_ids_to_socket_ids[v.id] = request.sid
emit('online', online)
emit('catchup', messages)
emit('typing', typing)
emit('online', online, room=request.referrer)
emit('catchup', messages[request.referrer], room=request.referrer)
emit('typing', typing[request.referrer], room=request.referrer)
return '', 204
@socketio.on('disconnect')
@ -142,26 +153,31 @@ def connect(v):
def disconnect(v):
if v.username in online:
online.remove(v.username)
emit("online", online, broadcast=True)
emit("online", online, room=request.referrer, broadcast=True)
cache.set(CHAT_ONLINE_CACHE_KEY, len(online), timeout=0)
if v.username in typing: typing.remove(v.username)
if v.username in typing[request.referrer]:
typing[request.referrer].remove(v.username)
if socket_ids_to_user_ids.get(request.sid):
del socket_ids_to_user_ids[request.sid]
del user_ids_to_socket_ids[v.id]
emit('typing', typing, broadcast=True)
emit('typing', typing[request.referrer], room=request.referrer, broadcast=True)
leave_room(request.referrer)
return '', 204
@socketio.on('typing')
@admin_level_required(PERMS['CHAT'])
def typing_indicator(data, v):
if data and v.username not in typing: typing.append(v.username)
elif not data and v.username in typing: typing.remove(v.username)
if data and v.username not in typing[request.referrer]:
typing[request.referrer].append(v.username)
elif not data and v.username in typing[request.referrer]:
typing[request.referrer].remove(v.username)
emit('typing', typing, broadcast=True)
emit('typing', typing[request.referrer], room=request.referrer, broadcast=True)
return '', 204
@ -171,15 +187,14 @@ def delete(text, v):
for message in messages:
if message['text'] == text:
messages.remove(message)
messages[request.referrer].remove(message)
emit('delete', text, broadcast=True)
emit('delete', text, room=request.referrer, broadcast=True)
return '', 204
def close_running_threads():
cache.set(f'{SITE}_chat', messages)
cache.set(f'{SITE}_total', total)
cache.set(f'{SITE}_muted', muted)
cache.set(f'messages', messages)
cache.set(f'muted', muted)
atexit.register(close_running_threads)

View File

@ -116,6 +116,8 @@ def admin_level_required(x):
if v.admin_level < x: abort(403)
if x and SITE != 'devrama.net' and not IS_LOCALHOST and not v.mfa_secret:
abort(403, "You need to enable 2FA to use admin features!")
if request.referrer == f'{SITE_FULL}/admin/chat' and v.admin_level < PERMS['CHAT']:
abort(403)
return make_response(f(*args, v=v, **kwargs))
wrapper.__name__ = f.__name__

View File

@ -14,7 +14,6 @@
data-sitename="{{SITE_NAME}}"
data-themecolor="{{v.themecolor}}"
data-namecolor="{{v.namecolor}}"
data-avatar="{{v.profile_url}}"
data-hat="{{v.hat_active(v)[0]}}">
</div>
<script defer src="{{'js/chat.js' | asset}}"></script>

View File

@ -134,7 +134,7 @@
{% endif %}
{% endif %}
{% if request.path == '/chat' %}
{% if request.path.endswith('/chat') %}
<link rel="stylesheet" href="{{'css/chat_done.css' | asset}}">
{% endif %}
{% endmacro %}

View File

@ -23,6 +23,10 @@ server {
proxy_pass http://localhost:5001/chat;
include includes/headers;
}
location /admin/chat {
proxy_pass http://localhost:5001/admin/chat;
include includes/headers;
}
location =/offline.html {
alias /rDrama/files/assets/offline.html;
include includes/headers;