functioning bot invites
This commit is contained in:
@@ -13,7 +13,7 @@
|
|||||||
<link href="/themes.css" rel="stylesheet" id="lightcss">
|
<link href="/themes.css" rel="stylesheet" id="lightcss">
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body class="Dark-theme">
|
<body class="Dark-theme" style="overflow-y: scroll;">
|
||||||
<div id="titleDiv">
|
<div id="titleDiv">
|
||||||
<img src="/logo.svg" width="40">
|
<img src="/logo.svg" width="40">
|
||||||
<h1 id="pageTitle">Jank Client</h1>
|
<h1 id="pageTitle">Jank Client</h1>
|
||||||
@@ -58,4 +58,4 @@
|
|||||||
</body>
|
</body>
|
||||||
<script src="/home.js" type="module"></script>
|
<script src="/home.js" type="module"></script>
|
||||||
|
|
||||||
</html>
|
</html>
|
||||||
|
@@ -291,7 +291,7 @@ async function getapiurls(str: string): Promise<
|
|||||||
gateway: info.gateway,
|
gateway: info.gateway,
|
||||||
cdn: info.cdn,
|
cdn: info.cdn,
|
||||||
wellknown: str,
|
wellknown: str,
|
||||||
login: url.toString(),
|
login: info.apiEndpoint,
|
||||||
};
|
};
|
||||||
}catch{
|
}catch{
|
||||||
const val = stringURLsMap.get(str);
|
const val = stringURLsMap.get(str);
|
||||||
|
243
src/webpage/oauth2/auth.ts
Normal file
243
src/webpage/oauth2/auth.ts
Normal file
@@ -0,0 +1,243 @@
|
|||||||
|
import{ getBulkUsers, Specialuser, getapiurls }from"../login.js";
|
||||||
|
import { Permissions } from "../permissions.js";
|
||||||
|
type botjsonfetch={
|
||||||
|
guilds:{
|
||||||
|
id: string,
|
||||||
|
name: string,
|
||||||
|
icon: string,
|
||||||
|
mfa_level: number,
|
||||||
|
permissions: string
|
||||||
|
}[],
|
||||||
|
"user": {
|
||||||
|
id: string,
|
||||||
|
username: string,
|
||||||
|
avatar: string,
|
||||||
|
avatar_decoration?: string,
|
||||||
|
discriminator: string,
|
||||||
|
public_flags: number
|
||||||
|
},
|
||||||
|
application: {
|
||||||
|
id: string,
|
||||||
|
name: string,
|
||||||
|
icon: string|null,
|
||||||
|
description: string,
|
||||||
|
summary: string,
|
||||||
|
type: null,//not sure what this means :P
|
||||||
|
hook: boolean,
|
||||||
|
guild_id: null|string,
|
||||||
|
bot_public: boolean,
|
||||||
|
bot_require_code_grant: boolean,
|
||||||
|
verify_key: "IMPLEMENTME",//no clue what this is meant to be :P
|
||||||
|
flags: number
|
||||||
|
},
|
||||||
|
bot: {
|
||||||
|
id: string,
|
||||||
|
username: string,
|
||||||
|
avatar: string|null,
|
||||||
|
avatar_decoration: null|string,
|
||||||
|
discriminator: string,
|
||||||
|
public_flags: number,
|
||||||
|
bot: boolean,
|
||||||
|
approximated_guild_count: number
|
||||||
|
},
|
||||||
|
authorized: boolean
|
||||||
|
}
|
||||||
|
(async ()=>{
|
||||||
|
const users = getBulkUsers();
|
||||||
|
const params=new URLSearchParams(window.location.search);
|
||||||
|
const well = params.get("instance");
|
||||||
|
const permstr=params.get("permissions");
|
||||||
|
const joinable: Specialuser[] = [];
|
||||||
|
|
||||||
|
for(const key in users.users){
|
||||||
|
if(Object.prototype.hasOwnProperty.call(users.users, key)){
|
||||||
|
const user: Specialuser = users.users[key];
|
||||||
|
if(well && user.serverurls.wellknown.includes(well)){
|
||||||
|
joinable.push(user);
|
||||||
|
}
|
||||||
|
console.log(user);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let urls: { api: string; cdn: string } | undefined;
|
||||||
|
|
||||||
|
if(!joinable.length && well){
|
||||||
|
const out = await getapiurls(well);
|
||||||
|
if(out){
|
||||||
|
urls = out;
|
||||||
|
for(const key in users.users){
|
||||||
|
if(Object.prototype.hasOwnProperty.call(users.users, key)){
|
||||||
|
const user: Specialuser = users.users[key];
|
||||||
|
if(user.serverurls.api.includes(out.api)){
|
||||||
|
joinable.push(user);
|
||||||
|
}
|
||||||
|
console.log(user);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}else{
|
||||||
|
throw new Error(
|
||||||
|
"Someone needs to handle the case where the servers don't exist"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}else{
|
||||||
|
urls = joinable[0].serverurls;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!joinable.length){
|
||||||
|
document.getElementById("AcceptInvite")!.textContent = "Create an account to invite the bot";
|
||||||
|
}
|
||||||
|
|
||||||
|
function showGuilds(user:Specialuser){
|
||||||
|
if(!urls) return;
|
||||||
|
fetch(urls.api+"/oauth2/authorize/"+window.location.search,{
|
||||||
|
headers:{
|
||||||
|
Authorization:user.token
|
||||||
|
}
|
||||||
|
}).then(_=>_.json()).then((json:botjsonfetch)=>{
|
||||||
|
const guilds:botjsonfetch["guilds"]=[];
|
||||||
|
for(const guild of json.guilds){
|
||||||
|
const permisions=new Permissions(guild.permissions)
|
||||||
|
if(permisions.hasPermission("MANAGE_GUILD")){
|
||||||
|
guilds.push(guild);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const dialog=document.createElement("dialog");
|
||||||
|
dialog.classList.add("accountSwitcher");
|
||||||
|
const h1=document.createElement("h1");
|
||||||
|
dialog.append(h1);
|
||||||
|
h1.textContent="Invite to server:";
|
||||||
|
const select=document.createElement("select");
|
||||||
|
for(const guild of guilds){
|
||||||
|
const option=document.createElement("option");
|
||||||
|
option.textContent=guild.name;
|
||||||
|
option.value=guild.id;
|
||||||
|
select.append(option);
|
||||||
|
}
|
||||||
|
dialog.append(select);
|
||||||
|
const button=document.createElement("button");
|
||||||
|
button.textContent="Invite";
|
||||||
|
dialog.append(button);
|
||||||
|
button.onclick=()=>{
|
||||||
|
const id=select.value;
|
||||||
|
const params2=new URLSearchParams("");
|
||||||
|
params2.set("client_id",params.get("client_id") as string)
|
||||||
|
fetch(urls.api+"/oauth2/authorize?"+params2.toString(),{
|
||||||
|
method:"POST",
|
||||||
|
body:JSON.stringify({
|
||||||
|
authorize:true,
|
||||||
|
guild_id:id,
|
||||||
|
permissions:permstr
|
||||||
|
}),
|
||||||
|
headers:{
|
||||||
|
"Content-type": "application/json; charset=UTF-8",
|
||||||
|
Authorization:user.token,
|
||||||
|
}
|
||||||
|
}).then(req=>{
|
||||||
|
if(req.ok){
|
||||||
|
alert("Bot added successfully");
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
document.body.append(dialog);
|
||||||
|
})
|
||||||
|
}
|
||||||
|
function showAccounts(): void{
|
||||||
|
const table = document.createElement("dialog");
|
||||||
|
for(const user of joinable){
|
||||||
|
console.log(user.pfpsrc);
|
||||||
|
|
||||||
|
const userinfo = document.createElement("div");
|
||||||
|
userinfo.classList.add("flexltr", "switchtable");
|
||||||
|
|
||||||
|
const pfp = document.createElement("img");
|
||||||
|
pfp.src = user.pfpsrc;
|
||||||
|
pfp.classList.add("pfp");
|
||||||
|
userinfo.append(pfp);
|
||||||
|
|
||||||
|
const userDiv = document.createElement("div");
|
||||||
|
userDiv.classList.add("userinfo");
|
||||||
|
userDiv.textContent = user.username;
|
||||||
|
userDiv.append(document.createElement("br"));
|
||||||
|
|
||||||
|
const span = document.createElement("span");
|
||||||
|
span.textContent = user.serverurls.wellknown
|
||||||
|
.replace("https://", "")
|
||||||
|
.replace("http://", "");
|
||||||
|
span.classList.add("serverURL");
|
||||||
|
userDiv.append(span);
|
||||||
|
|
||||||
|
userinfo.append(userDiv);
|
||||||
|
table.append(userinfo);
|
||||||
|
|
||||||
|
userinfo.addEventListener("click", ()=>{
|
||||||
|
table.remove();
|
||||||
|
showGuilds(user);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
const td = document.createElement("div");
|
||||||
|
td.classList.add("switchtable");
|
||||||
|
td.textContent = "Login or create an account ⇌";
|
||||||
|
td.addEventListener("click", ()=>{
|
||||||
|
const l = new URLSearchParams("?");
|
||||||
|
l.set("goback", window.location.href);
|
||||||
|
l.set("instance", well!);
|
||||||
|
window.location.href = "/login?" + l.toString();
|
||||||
|
});
|
||||||
|
|
||||||
|
if(!joinable.length){
|
||||||
|
const l = new URLSearchParams("?");
|
||||||
|
l.set("goback", window.location.href);
|
||||||
|
l.set("instance", well!);
|
||||||
|
window.location.href = "/login?" + l.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
table.append(td);
|
||||||
|
table.classList.add("accountSwitcher");
|
||||||
|
console.log(table);
|
||||||
|
document.body.append(table);
|
||||||
|
}
|
||||||
|
const user=joinable[0];
|
||||||
|
if(!user){
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
fetch(urls.api+"/oauth2/authorize/"+window.location.search,{
|
||||||
|
headers:{
|
||||||
|
Authorization:user.token
|
||||||
|
}
|
||||||
|
}).then(_=>_.json()).then((json:botjsonfetch)=>{
|
||||||
|
const title=document.getElementById("invitename");
|
||||||
|
if(title){
|
||||||
|
title.textContent=`Invite ${json.bot.username} to your servers`
|
||||||
|
}
|
||||||
|
const desc=document.getElementById("invitedescription");
|
||||||
|
if(desc){
|
||||||
|
desc.textContent=json.application.description;
|
||||||
|
}
|
||||||
|
const pfp=document.getElementById("inviteimg") as HTMLImageElement;
|
||||||
|
if(json.bot.avatar !== null){
|
||||||
|
pfp.src=`${urls.cdn}/avatars/${json.bot.id}/${json.bot.avatar}.png`;
|
||||||
|
}else{
|
||||||
|
const int = Number((BigInt(json.bot.id) >> 22n) % 6n);
|
||||||
|
pfp.src=`${urls.cdn}/embed/avatars/${int}.png`;
|
||||||
|
}
|
||||||
|
const perms=document.getElementById("permsions") as HTMLDivElement;
|
||||||
|
|
||||||
|
if(perms&&permstr){
|
||||||
|
const permisions=new Permissions(permstr)
|
||||||
|
for(const perm of Permissions.info){
|
||||||
|
if(permisions.hasPermission(perm.name,false)){
|
||||||
|
const div=document.createElement("div");
|
||||||
|
const h2=document.createElement("h2");
|
||||||
|
h2.textContent=perm.readableName;
|
||||||
|
div.append(h2,perm.description);
|
||||||
|
div.classList.add("flexttb");
|
||||||
|
perms.append(div);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
document
|
||||||
|
.getElementById("AcceptInvite")!
|
||||||
|
.addEventListener("click", showAccounts);
|
||||||
|
})();
|
23
src/webpage/oauth2/authorize.html
Normal file
23
src/webpage/oauth2/authorize.html
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
<body class="Dark-theme">
|
||||||
|
<head>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
|
<title>Jank Client</title>
|
||||||
|
<meta content="Bot Invite" property="og:title">
|
||||||
|
<meta name="description" content="Invite this bot to your server!">
|
||||||
|
<meta content="/logo.webp" property="og:image">
|
||||||
|
<meta content="#4b458c" data-react-helmet="true" name="theme-color">
|
||||||
|
<link href="/style.css" rel="stylesheet">
|
||||||
|
<link href="/themes.css" rel="stylesheet" id="lightcss">
|
||||||
|
</head>
|
||||||
|
<div>
|
||||||
|
<div id="invitebody">
|
||||||
|
<img id="inviteimg" class="pfp"/>
|
||||||
|
<h1 id="invitename">Bot Name</h1>
|
||||||
|
<p id="invitedescription">Add Bot</p>
|
||||||
|
<div id="permsions"><h1>This will allow the bot to:</h1></div>
|
||||||
|
<button id="AcceptInvite">Add to server</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<script type="module" src="/oauth2/auth.js"></script>
|
||||||
|
</body>
|
@@ -309,7 +309,7 @@ class Permissions{
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
hasPermission(name: string): boolean{
|
hasPermission(name: string,adminOverride=true): boolean{
|
||||||
if(this.deny){
|
if(this.deny){
|
||||||
console.warn(
|
console.warn(
|
||||||
"This function may of been used in error, think about using getPermision instead"
|
"This function may of been used in error, think about using getPermision instead"
|
||||||
@@ -317,7 +317,7 @@ class Permissions{
|
|||||||
}
|
}
|
||||||
if(this.getPermissionbit(Permissions.map[name] as number, this.allow))
|
if(this.getPermissionbit(Permissions.map[name] as number, this.allow))
|
||||||
return true;
|
return true;
|
||||||
if(name != "ADMINISTRATOR")return this.hasPermission("ADMINISTRATOR");
|
if(name != "ADMINISTRATOR"&&adminOverride)return this.hasPermission("ADMINISTRATOR");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
setPermission(name: string, setto: number): void{
|
setPermission(name: string, setto: number): void{
|
||||||
|
@@ -21,6 +21,9 @@ body {
|
|||||||
box-shadow: inset .03in .35in .2in var(--accent_color);
|
box-shadow: inset .03in .35in .2in var(--accent_color);
|
||||||
min-height: 3.6in;
|
min-height: 3.6in;
|
||||||
min-width: 7.5cm;
|
min-width: 7.5cm;
|
||||||
|
.banner{
|
||||||
|
position:absolute;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
video{
|
video{
|
||||||
max-width: 3in;
|
max-width: 3in;
|
||||||
@@ -1810,11 +1813,13 @@ form div{
|
|||||||
box-sizing:border-box;
|
box-sizing:border-box;
|
||||||
display:flex;
|
display:flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
padding: .5in .2in;
|
padding: .5in .2in;
|
||||||
gap: .1in;
|
gap: .1in;
|
||||||
width: 5in;
|
width: 5in;
|
||||||
|
max-height: 80dvh;
|
||||||
|
overflow-y: auto;
|
||||||
|
overflow-x:clip;
|
||||||
|
align-items: center;
|
||||||
}
|
}
|
||||||
#AcceptInvite{
|
#AcceptInvite{
|
||||||
padding: .1in .2in;
|
padding: .1in .2in;
|
||||||
|
Reference in New Issue
Block a user