mirror of
https://github.com/tgbot-collection/YYeTsBot.git
synced 2025-11-25 19:37:34 +08:00
ban user with cloudflare
This commit is contained in:
@@ -328,15 +328,15 @@ def approve_spam(call):
|
||||
bot.delete_message(call.message.chat.id, call.message.message_id)
|
||||
|
||||
|
||||
@bot.callback_query_handler(func=lambda call: re.findall(r"deny", call.data))
|
||||
def deny_spam(call):
|
||||
obj_id = re.findall(r"deny(\S*)", call.data)[0]
|
||||
@bot.callback_query_handler(func=lambda call: re.findall(r"ban", call.data))
|
||||
def ban_spam(call):
|
||||
obj_id = re.findall(r"ban(\S*)", call.data)[0]
|
||||
data = {
|
||||
"obj_id": obj_id,
|
||||
"token": TOKEN
|
||||
}
|
||||
requests.delete(f"{DOMAIN}api/admin/spam", json=data)
|
||||
bot.answer_callback_query(call.id, 'Denied')
|
||||
bot.answer_callback_query(call.id, 'Banned')
|
||||
bot.delete_message(call.message.chat.id, call.message.message_id)
|
||||
|
||||
|
||||
|
||||
@@ -37,7 +37,7 @@ from database import (AnnouncementResource, BlacklistResource, CaptchaResource,
|
||||
NameResource, NotificationResource, OtherResource, Redis,
|
||||
ResourceLatestResource, ResourceResource, TopResource,
|
||||
UserEmailResource, UserResource)
|
||||
from utils import check_spam, send_mail, ts_date
|
||||
from utils import check_spam, send_mail, ts_date, Cloudflare
|
||||
|
||||
lib_path = pathlib.Path(__file__).parent.parent.joinpath("yyetsbot").resolve().as_posix()
|
||||
sys.path.append(lib_path)
|
||||
@@ -46,6 +46,7 @@ from fansub import BD2020, XL720, NewzmzOnline, ZhuixinfanOnline, ZimuxiaOnline
|
||||
mongo_host = os.getenv("mongo") or "localhost"
|
||||
DOUBAN_SEARCH = "https://www.douban.com/search?cat=1002&q={}"
|
||||
DOUBAN_DETAIL = "https://movie.douban.com/subject/{}/"
|
||||
cf = Cloudflare()
|
||||
|
||||
|
||||
class Mongo:
|
||||
@@ -93,6 +94,7 @@ class OtherMongoResource(OtherResource, Mongo):
|
||||
self.db["yyets"].update_many({}, {"$set": {"data.info.views": 0}})
|
||||
|
||||
def import_ban_user(self):
|
||||
# TODO ban IP as well?
|
||||
usernames = self.db["users"].find({"status.disable": True}, projection={"username": True})
|
||||
r = Redis().r
|
||||
r.delete("user_blacklist")
|
||||
@@ -1091,10 +1093,15 @@ class ResourceLatestMongoResource(ResourceLatestResource, Mongo):
|
||||
|
||||
class SpamProcessMongoResource(Mongo):
|
||||
|
||||
def delete_spam(self, obj_id: "str"):
|
||||
def ban_spam(self, obj_id: "str"):
|
||||
obj_id = ObjectId(obj_id)
|
||||
logging.info("Deleting spam %s", obj_id)
|
||||
self.db["spam"].delete_one({"_id": obj_id})
|
||||
spam = self.db["spam"].find_one({"_id": obj_id})
|
||||
username = spam["username"]
|
||||
self.db["spam"].delete_many({"username": username})
|
||||
# TODO disable it for now
|
||||
# self.db["comment"].delete_many({"username": username})
|
||||
cf.ban_new_ip(spam["ip"])
|
||||
return {"status": True}
|
||||
|
||||
def restore_spam(self, obj_id: "str"):
|
||||
@@ -1121,8 +1128,8 @@ class SpamProcessMongoResource(Mongo):
|
||||
"callback_data": f"approve{obj_id}"
|
||||
},
|
||||
{
|
||||
"text": "deny",
|
||||
"callback_data": f"deny{obj_id}"
|
||||
"text": "ban",
|
||||
"callback_data": f"ban{obj_id}"
|
||||
}
|
||||
]
|
||||
]
|
||||
|
||||
@@ -28,11 +28,11 @@ from tornado import escape, gen, web
|
||||
from tornado.concurrent import run_on_executor
|
||||
|
||||
from database import CaptchaResource, Redis
|
||||
from utils import add_cf_blacklist
|
||||
from utils import Cloudflare
|
||||
|
||||
escape.json_encode = lambda value: json.dumps(value, ensure_ascii=False)
|
||||
logging.basicConfig(level=logging.INFO)
|
||||
|
||||
cf = Cloudflare()
|
||||
if getattr(sys, '_MEIPASS', None):
|
||||
adapter = "SQLite"
|
||||
else:
|
||||
@@ -82,7 +82,7 @@ class SecurityHandler(web.RequestHandler):
|
||||
else:
|
||||
ex = (count - 10) * 600
|
||||
if count >= 30:
|
||||
add_cf_blacklist(ip)
|
||||
cf.ban_new_ip(ip)
|
||||
self.r.set(ip, count, ex)
|
||||
user = self.get_current_user()
|
||||
if user:
|
||||
@@ -991,7 +991,7 @@ class SpamProcessHandler(BaseHandler):
|
||||
return getattr(self.instance, method)(obj_id)
|
||||
else:
|
||||
self.set_status(HTTPStatus.FORBIDDEN)
|
||||
return {"status": False, "message": "this token is not allowed to access this API"}
|
||||
return {"status": False, "message": "This token is not allowed to access this API"}
|
||||
|
||||
@gen.coroutine
|
||||
def post(self):
|
||||
@@ -999,4 +999,4 @@ class SpamProcessHandler(BaseHandler):
|
||||
|
||||
@gen.coroutine
|
||||
def delete(self):
|
||||
self.write(self.process("delete_spam"))
|
||||
self.write(self.process("ban_spam"))
|
||||
|
||||
@@ -32,9 +32,10 @@ from handler import (AnnouncementHandler, BlacklistHandler, CaptchaHandler,
|
||||
UserEmailHandler, UserHandler)
|
||||
from migration.douban_sync import sync_douban
|
||||
from Mongo import OtherMongoResource, ResourceLatestMongoResource
|
||||
from utils import Cloudflare
|
||||
|
||||
enable_pretty_logging()
|
||||
|
||||
cf = Cloudflare()
|
||||
if os.getenv("debug"):
|
||||
logging.basicConfig(level=logging.DEBUG)
|
||||
|
||||
@@ -106,6 +107,7 @@ if __name__ == "__main__":
|
||||
scheduler.add_job(entry_dump, trigger=CronTrigger.from_crontab("2 2 1 * *"))
|
||||
scheduler.add_job(ResourceLatestMongoResource().refresh_latest_resource, 'interval', hours=1)
|
||||
scheduler.add_job(OtherMongoResource().import_ban_user, 'interval', seconds=300)
|
||||
scheduler.add_job(cf.clear_fw, trigger=CronTrigger.from_crontab("0 0 */5 * *"))
|
||||
scheduler.start()
|
||||
|
||||
options.define("p", default=8888, help="running port", type=int)
|
||||
|
||||
@@ -66,23 +66,40 @@ def check_spam(ip, ua, author, content) -> int:
|
||||
return 0
|
||||
|
||||
|
||||
def add_cf_blacklist(ip):
|
||||
logging.warning("Cloudflare: Blacklisting %s", ip)
|
||||
zone_id = "b8e2d2fa75c6f7dc3c2e478e27f3061b"
|
||||
filter_id = "cc6c810f7f2941d28a672bfb6ac6bebe"
|
||||
api = f"https://api.cloudflare.com/client/v4/zones/{zone_id}/filters/{filter_id}"
|
||||
s = requests.Session()
|
||||
s.headers.update({"Authorization": "Bearer %s" % os.getenv("CF_TOKEN")})
|
||||
expr = s.get(api).json()["result"]["expression"]
|
||||
if ip not in expr:
|
||||
class Cloudflare:
|
||||
def __init__(self):
|
||||
self.zone_id = "b8e2d2fa75c6f7dc3c2e478e27f3061b"
|
||||
self.filter_id = "9e1e9139bcbe400c8b2620ac117a77d8"
|
||||
self.endpoint = f"https://api.cloudflare.com/client/v4/zones/{self.zone_id}/filters/{self.filter_id}"
|
||||
self.session = requests.Session()
|
||||
self.session.headers.update({"Authorization": "Bearer %s" % os.getenv("CF_TOKEN")})
|
||||
|
||||
def get_old_expr(self):
|
||||
return self.session.get(self.endpoint).json()["result"]["expression"]
|
||||
|
||||
def ban_new_ip(self, ip):
|
||||
logging.info("Blacklisting IP %s", ip)
|
||||
expr = self.get_old_expr()
|
||||
if ip not in expr:
|
||||
body = {
|
||||
"id": self.filter_id,
|
||||
"paused": False,
|
||||
"expression": f"{expr} or (ip.src eq {ip})"
|
||||
}
|
||||
resp = self.session.put(self.endpoint, json=body)
|
||||
logging.info(resp.json())
|
||||
|
||||
def clear_fw(self):
|
||||
logging.info("Clearing firewall rules")
|
||||
body = {
|
||||
"id": filter_id,
|
||||
"id": self.filter_id,
|
||||
"paused": False,
|
||||
"expression": f"{expr} or (ip.src eq {ip})"
|
||||
"expression": "(ip.src eq 192.168.2.1)"
|
||||
}
|
||||
resp = s.put(api, json=body)
|
||||
print(resp.json())
|
||||
self.session.put(self.endpoint, json=body)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
add_cf_blacklist("192.168.2.1")
|
||||
cf = Cloudflare()
|
||||
cf.clear_fw()
|
||||
cf.ban_new_ip("3.3.3.3")
|
||||
|
||||
Reference in New Issue
Block a user