Skip to content
This repository has been archived by the owner on Jan 2, 2023. It is now read-only.

Commit

Permalink
add ban/unban ip and maybe fix hcaptcha
Browse files Browse the repository at this point in the history
  • Loading branch information
akisblack committed Dec 17, 2022
1 parent b2ff479 commit d0f43f8
Show file tree
Hide file tree
Showing 4 changed files with 134 additions and 8 deletions.
15 changes: 8 additions & 7 deletions src/apis/form.ts
Original file line number Diff line number Diff line change
Expand Up @@ -56,23 +56,22 @@ interface BodyType {
commentType: string;
message: string;
"h-captcha-response": string;
"g-recaptcha-response": string;
"g-recaptcha-response"?: string;
}

const BodyTypeSchema = Joi.object({
email: Joi.string().email().required(),
commentType: Joi.string().required(),
message: Joi.string().required(),
"h-captcha-response": Joi.string().required(),
"g-recaptcha-response": Joi.string().required()
"g-recaptcha-response": Joi.string().optional().allow("")
});

const handleForm = (
request: FastifyRequest<{ Body: BodyType }>,
reply: FastifyReply
) => {
if (BodyTypeSchema.validate(request.body).error) {
console.log(request.body)
reply.badRequest(
`${BodyTypeSchema.validate(request.body).error}`
);
Expand All @@ -82,7 +81,7 @@ const handleForm = (
verify(config.app.hcaptcha.secret, request.body["h-captcha-response"])
.then((data) => {
const hook = new Webhook(config.app.webhook);
if (data.success === true) {
if (data.success) {
const embed = new MessageBuilder()
.setAuthor(
`${ip}, ${request.body.email}, https://abuseipdb.com/check/${ip}`
Expand All @@ -92,13 +91,15 @@ const handleForm = (
.setTimestamp();

reply.send(
"Thanks for your message, and thanks for doing the captcha!\nPlease ignore how different this page looks to the page you were on earlier. I'll figure it out eventually!"
"Thanks for your message, we will get back to you as soon as possible."
);

hook.send(embed);
} else {
reply.send(
"Seems like captcha failed, you didn't complete the captcha or you are a bot. Please try again.\nPlease note that your IP has been logged in our systems for manual review to check if you're an abusive user. If you're seen as abusive, you will be blacklisted.\nYour message has not been sent."
(data);
reply.unauthorized(
"Captcha failed or expired, please try again. If this keeps happening, assume the captcha is broken and contact us on Matrix." +
" Error: " + data["error-codes"]
);

hook.send(
Expand Down
90 changes: 90 additions & 0 deletions src/apis/user.ts
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,18 @@ const userApi = (fastify: FastifyInstance) => {
changeUsername(request, reply);
}
);
fastify.post(
"/api/v1/user/banip",
(request: FastifyRequest<{ Body: BanIpType }>, reply: FastifyReply) => {
banIp(request, reply);
}
);
fastify.post(
"/api/v1/user/unbanip",
(request: FastifyRequest<{ Body: UnbanIpType }>, reply: FastifyReply) => {
unbanIp(request, reply);
}
);
};

interface BodyType {
Expand Down Expand Up @@ -326,4 +338,82 @@ const changeUsername = async (
}
};

interface BanIpType {
ip: string;
reason: string;
bannedBy: string;
}

const BanIpTypeSchema = Joi.object({
ip: Joi.string().ip().required(),
reason: Joi.string().required(),
bannedBy: Joi.string().required()
});

const banIp = async (request: FastifyRequest<{ Body: BanIpType }>, reply: FastifyReply) => {
if (userMap.get("isAdmin")) {
if (BanIpTypeSchema.validate(request.body).error) {
reply.badRequest(`${BanIpTypeSchema.validate(request.body).error}`);
} else {
const collection = db.collection("banned");

if (await collection.findOne({ ip: request.body.ip })) {
reply.conflict("IP already banned.");
} else {
await collection.insertOne({ ...request.body, time: Math.floor(Date.now() / 1000) }).then((result) => {
if (result.insertedId !== undefined) {
reply.send("IP banned.");
} else {
reply.internalServerError("An error occurred while writing to MongoDB.");
}
});
}
}
} else {
reply.unauthorized("You need to be an admin to ban IPs.");
}
}

interface UnbanIpType {
ip: string;
reason: string;
unbannedBy: string;
}

const UnbanIpTypeSchema = Joi.object({
ip: Joi.string().ip().required(),
reason: Joi.string().required(),
unbannedBy: Joi.string().required()
});

const unbanIp = async (request: FastifyRequest<{ Body: UnbanIpType }>, reply: FastifyReply) => {
if (userMap.get("isAdmin")) {
if (UnbanIpTypeSchema.validate(request.body).error) {
reply.badRequest(`${UnbanIpTypeSchema.validate(request.body).error}`);
} else {
const collection = db.collection("blocklist");

const unbannedCollection = db.collection("unbanned");

await collection.deleteOne({ ip: request.body.ip }).then((result) => {
if (result.deletedCount === 1) {
reply.send("IP unbanned.");
} else {
reply.notFound("IP is not banned.");
}
});

await unbannedCollection.insertOne({ ...request.body, time: Math.floor(Date.now() / 1000) }).then((result) => {
if (result.insertedId !== undefined) {
reply.send("Wrote unban to unbanned database.");
} else {
reply.internalServerError("An error occurred while writing to MongoDB.");
}
});
}
} else {
reply.unauthorized("You need to be an admin to ban IPs.");
}
}

export default userApi;
11 changes: 10 additions & 1 deletion src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@ import log from "./utils/logUtil";
import { join, dirname } from "path";
import { fileURLToPath } from "url";
import config from "./utils/config";
import { initializeDb, dbCleanUp } from "./utils/db";
import { initializeDb, dbCleanUp, db } from "./utils/db";
import getIp from "./utils/getIp";

const __dirname = dirname(fileURLToPath(import.meta.url));

Expand All @@ -40,6 +41,14 @@ fastify.register(pointOfView, {
viewExt: "hbs"
});

fastify.addHook("preHandler", async (request: FastifyRequest, reply: FastifyReply) => {
const collection = db.collection("banned");

if (getIp(request) === await collection.findOne({ ip: getIp(request) }).then((doc) => doc?.["ip"])) {
reply.unauthorized("You are banned.");
}
});

fastify.get("/", (request: FastifyRequest, reply: FastifyReply) => {
reply.view("index", {
port: config.app.port,
Expand Down
26 changes: 26 additions & 0 deletions src/templates/user.hbs
Original file line number Diff line number Diff line change
Expand Up @@ -77,4 +77,30 @@
<input type="text" name="newusername" placeholder="New username" />
<button type="submit">Submit</button>
</form>

<h1>Ban IP</h1>
<form
action="/api/v1/user/banip"
method="POST"
target="_blank"
class="col"
>
<input type="text" name="ip" placeholder="IP to ban" />
<input type="text" name="reason" placeholder="Reason for ban">
<input type="text" name="bannedBy" placeholder="Banned by">
<button type="submit">Submit</button>
</form>

<h1>Unban IP</h1>
<form
action="/api/v1/user/unbanip"
method="POST"
target="_blank"
class="col"
>
<input type="text" name="ip" placeholder="IP to unban" />
<input type="text" name="reason" placeholder="Reason for unban">
<input type="text" name="unbannedBy" placeholder="Unbanned by">
<button type="submit">Submit</button>
</form>
</div>

0 comments on commit d0f43f8

Please sign in to comment.