From 3fa2a954297df36d4c33186559c681d4967970b6 Mon Sep 17 00:00:00 2001 From: Puyodead1 Date: Fri, 24 Mar 2023 21:53:59 -0400 Subject: [PATCH] oapi: policies --- assets/openapi.json | Bin 400397 -> 414091 bytes assets/schemas.json | Bin 12400140 -> 13698609 bytes src/api/routes/policies/instance/domains.ts | 41 ++++++++++++------ src/api/routes/policies/instance/index.ts | 20 ++++++--- src/api/routes/policies/instance/limits.ts | 20 ++++++--- src/api/routes/policies/stats.ts | 41 ++++++++++++------ .../subconfigurations/limits/RateLimits.ts | 4 +- .../responses/GeneralConfigurationResponse.ts | 3 ++ .../responses/InstanceDomainsResponse.ts | 6 +++ .../responses/InstanceStatsResponse.ts | 8 ++++ .../responses/LimitsConfigurationResponse.ts | 3 ++ src/util/schemas/responses/index.ts | 4 ++ 12 files changed, 110 insertions(+), 40 deletions(-) create mode 100644 src/util/schemas/responses/GeneralConfigurationResponse.ts create mode 100644 src/util/schemas/responses/InstanceDomainsResponse.ts create mode 100644 src/util/schemas/responses/InstanceStatsResponse.ts create mode 100644 src/util/schemas/responses/LimitsConfigurationResponse.ts diff --git a/assets/openapi.json b/assets/openapi.json index 51a35079ccd02490d843381d3353ee08c7ae1f9c..d2953a042d21350c2ea3f072581dd3964b9c22b0 100644 GIT binary patch delta 2768 zcmaJ@ZERCj7|yxp-nJ`lbPQ;_v924)mu$4%x-Pnh7{cz>%XX!`x88Pu zD9P#%@dI#h!e0M?8^j+bisDCRf{`uoM}rZfCJ;q8zlf1QmuMm;sOQ|f-mZu??T>rj z=ly!#_dK_UKXko(+CBI_`r$g6e1+#X$uXHseCmXTW2n^{6Zf?a$WdtA#VscdMT^Pg zM|P{%vibVfNro+!+K4YlpJ3i^!dp2$4(d;N3D4oNCX<& zQL)v?WjtUS7Dk`rLc;}E$SsPc?1YqzR%UWyzaF)UmD>_ipCqZ2SuGA2Hs-bYcsE*= zak2(zE%Zansba<^IQs@?wjtC8gVjO3lljcpFDi-@O|&UZVp8f;H7LBwd5EvFka(Vd za0dL;i~Jgr-d|xvYhQ-TitghIS8fPyp@Ldkps)s)>V?6XW!S^Y?^L4_T(#vG*Vb5qxt6Aa6xl1x=4CumM_0=h67g3cB!Xd zRd@$$$mN`hj|izsw02JC{XoR$agy7b0LM-v&;P{oAI9DNZv&*OCQT0C51=aAiRm(f~Hc(Y;SY2 zHL<;O>#{-|2g^xVu7~cIP&dCPPMh*W>0n7~{E9?)UHUES0X=vSlm>qAsVB{NthxA?a7^J5J z0p`EQF9aVY1j_ax7t3#foqLeeNOjAB{rNgK85T`d6*Q?&PC(;1t{g@Hd2(R}*@O8m zAt5P|%}~ApH5RnyL^9_w6KVP_zF4SWa0tJE+{1;q%${|a#nHGIRhx@iHJf=|$1K&g z8AUW!F#hVJ#uzel$5A;3;Y+A^W*l&<9@icG^*S2+^*VRUSrBbfm0fb*fF>qoRRQ!6 zj*x~Cm+zRV9x^l@)KYU-HH^sZygFAtoemM0^^ij&O^>yBG@)-h%5ayEIiv zh6zfqAmIb6cx50OCDWgl4D;MtKB*@DZGo_zt1nPBO-jU7B_h#$E#%AzKP~D((_IG@ z<$$&&B(1HPpso$|wl!c)AlFeuaIDaqO05@T6sO~$;vmz<;P)4rf<>li$PmlZc!p} zRX#4_<>6lqyC5xp2XWG#x=35#VGSUOhIw65sp) z28;PW9+*8NNZk?kgQG)e9lLy$R}gehU=Mu$J??-nr|>oy`d+v*?>;p7&+#Ws>}$|a vE8GEfiWBbDiyT}BNI&Ao^&-qg(U%k^eilZ|a194Xf5P;~kB$B$L~H*6|B&*q delta 112 zcmeBPEZMt5qG1c;D+vS=t^pK?pp2+o!bMRO<)Rd|ig&A{W&;tTkVF#4%XCDmb$8TS zbW{I2)ec&nPRFsuTVF>zidB@lyx?kk9M`lKU2|Ng9%r;Yvu4hjR(p05QQNxaW8N>1 z%MX(5OLlEe8?6$SS4jPC z45l`lGE1A2Usy0~C`FEZDNBB02AytHW|D2kv@AL}PMxJ|6qb)`a@d`8x==aLw??M2 zAcsn>4Ud;BGk&J;eY%!P@{1FFTc$00M&^Dl#%sjc&7gqX@(XQX>s(Z_OdELRkCxk#(7MUD%Q9NCJJ#~7HE!-VCI(*Alsb$5V4kO| z|D#OS%4|uBb~KevA5v!d4@R9UujD_LaAA3g*DKW2H`<-vX|$wPWtH3;)Ac#S@`mMG3v=`R zON9!{OP4k*F1I(>$vVt9^U-@6DQ|UbW3|1u+_lWv;1X&dZ(xA7AU8j^u#ifIMZX#$ zFZT3Kz8aU;Crp0q@g}cM*Cd9@5A?q9o2J-4&)Bway}*IooNcg#%PTx}uwMzPJhF+= zKYY8?!tyEyP3cL_k&kPDqTuoOb~-H?VhH?*sB#`1r~I=ui-c^2|688*_$N>!?@Hdt z&3>9b8hNKKH*I-6&i{&M*{kbauEi92Ol8$gm46hT{1&vBUl>jIjs5bey)tw**$ny= z>YhE%9Pwx=?_{^v;c}AjU;1oyU4yHdBKO2tp1FwPvO7oWSg9uIvLfHuyPKysplWh0 zr8R>U{e0`khb{HmdzX@gd1mTZ$Fw6N{exjQj5LA3t-jB`Qa? z)LT!dZ;XhemZNEQYKw_bONVBg={2dsvTd~@$+t}%Jy&XoB-7WXlyLcQg@)c^d*sv! zO|hoQUgz*oNn`S`h>Gtm<9p*?@5xP6I%~1*Cq@2Oa9&Kbvi@J~6 zW0#lTon?@ZS>A2vlTAMLMl4yQ%k%w~`F|FD?`S@)9-zy3^jk&k2`jbaPS$5jRbPzu z3Ha!dPe;h#HAf>wt~Dk4-)7NvN5O1&l!c#yU=R#~K`;moGQl#xiY}vQyP{&YE9xDc zfEW-1Vn7UtIY9iOQ9Q9%!%png-Z~420Wly3#DJI�yr0umvl0`?~-!AO^&M7!Y%T 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 delta 1706 zcmYk6ZBSHY6vwAUSr>u}0)a&V$(vY$pdzI#q68HrNr;LPlq4#lEMPBy0!}=#t*iui z6Bb0V04Ws`{|d74vb!v@3p7v+qtmD}i;W|LPBMKcn4Z0RFT3Xgf~hZ>%h zPsLC^UDm3%FiY8*3{OcgJY{oOyVz))w1si<#h>>xJS|0%Fc%|NDh_=!72 z_0~2=w6-m;74)%2CyX^ZpVHuH`YSqyOjo;Ly85MyI-b4cuJDq(X*u1%kmCg_aJ=AU z-yuT%sgL`y33EC$a?YVwk#p#^@JXJ-vpo==?U|+HIV{}^Vd<|wzlHIUhcKxVs6CDfpHZXIgp)}Nto9C(Y~*EzER zoim|V2FyIn5RqvkM5eHd8bX=c-rhcLR%qn7!A*!8+-ys$#qreba7^8nN`#vVu128X z>XwdSIFxT2WY|@5*R$kE{Wct_kNT^hP$LzhqQ}iL4QEom1Cug(y@u!J;utg+zk7%0 z(%koM$2(1jeT3<-#D7M~HUFKs=AR@Qr{A44jfj92oNWvepXW75O=~B=Ou4B%V8Zs^8L_EN9G~pWXi_7av1M^8z}gf8x<%wo~}3Y{%UxCk(j|g|t?nlEx%~hd&?. */ -import { Router, Request, Response } from "express"; import { route } from "@spacebar/api"; import { Config } from "@spacebar/util"; +import { Request, Response, Router } from "express"; const router = Router(); -router.get("/", route({}), async (req: Request, res: Response) => { - const { cdn, gateway, api } = Config.get(); +router.get( + "/", + route({ + responses: { + 200: { + body: "InstanceDomainsResponse", + }, + }, + }), + async (req: Request, res: Response) => { + const { cdn, gateway, api } = Config.get(); - const IdentityForm = { - cdn: cdn.endpointPublic || process.env.CDN || "http://localhost:3001", - gateway: - gateway.endpointPublic || - process.env.GATEWAY || - "ws://localhost:3001", - defaultApiVersion: api.defaultVersion ?? 9, - apiEndpoint: api.endpointPublic ?? "http://localhost:3001/api/", - }; + const IdentityForm = { + cdn: + cdn.endpointPublic || + process.env.CDN || + "http://localhost:3001", + gateway: + gateway.endpointPublic || + process.env.GATEWAY || + "ws://localhost:3001", + defaultApiVersion: api.defaultVersion ?? 9, + apiEndpoint: api.endpointPublic ?? "http://localhost:3001/api/", + }; - res.json(IdentityForm); -}); + res.json(IdentityForm); + }, +); export default router; diff --git a/src/api/routes/policies/instance/index.ts b/src/api/routes/policies/instance/index.ts index 68ce3b42..4b4bc194 100644 --- a/src/api/routes/policies/instance/index.ts +++ b/src/api/routes/policies/instance/index.ts @@ -16,14 +16,24 @@ along with this program. If not, see . */ -import { Router, Request, Response } from "express"; import { route } from "@spacebar/api"; import { Config } from "@spacebar/util"; +import { Request, Response, Router } from "express"; const router = Router(); -router.get("/", route({}), async (req: Request, res: Response) => { - const { general } = Config.get(); - res.json(general); -}); +router.get( + "/", + route({ + responses: { + 200: { + body: "GeneralConfigurationResponse", + }, + }, + }), + async (req: Request, res: Response) => { + const { general } = Config.get(); + res.json(general); + }, +); export default router; diff --git a/src/api/routes/policies/instance/limits.ts b/src/api/routes/policies/instance/limits.ts index a6f13170..e144a5bc 100644 --- a/src/api/routes/policies/instance/limits.ts +++ b/src/api/routes/policies/instance/limits.ts @@ -16,14 +16,24 @@ along with this program. If not, see . */ -import { Router, Request, Response } from "express"; import { route } from "@spacebar/api"; import { Config } from "@spacebar/util"; +import { Request, Response, Router } from "express"; const router = Router(); -router.get("/", route({}), async (req: Request, res: Response) => { - const { limits } = Config.get(); - res.json(limits); -}); +router.get( + "/", + route({ + responses: { + 200: { + body: "LimitsConfigurationResponse", + }, + }, + }), + async (req: Request, res: Response) => { + const { limits } = Config.get(); + res.json(limits); + }, +); export default router; diff --git a/src/api/routes/policies/stats.ts b/src/api/routes/policies/stats.ts index 3939e1e8..b2cd3d5a 100644 --- a/src/api/routes/policies/stats.ts +++ b/src/api/routes/policies/stats.ts @@ -28,20 +28,33 @@ import { import { Request, Response, Router } from "express"; const router = Router(); -router.get("/", route({}), async (req: Request, res: Response) => { - if (!Config.get().security.statsWorldReadable) { - const rights = await getRights(req.user_id); - rights.hasThrow("VIEW_SERVER_STATS"); - } - - res.json({ - counts: { - user: await User.count(), - guild: await Guild.count(), - message: await Message.count(), - members: await Member.count(), +router.get( + "/", + route({ + responses: { + 200: { + body: "InstanceStatsResponse", + }, + 403: { + body: "APIErrorResponse", + }, }, - }); -}); + }), + async (req: Request, res: Response) => { + if (!Config.get().security.statsWorldReadable) { + const rights = await getRights(req.user_id); + rights.hasThrow("VIEW_SERVER_STATS"); + } + + res.json({ + counts: { + user: await User.count(), + guild: await Guild.count(), + message: await Message.count(), + members: await Member.count(), + }, + }); + }, +); export default router; diff --git a/src/util/config/types/subconfigurations/limits/RateLimits.ts b/src/util/config/types/subconfigurations/limits/RateLimits.ts index caba740b..0ce0827c 100644 --- a/src/util/config/types/subconfigurations/limits/RateLimits.ts +++ b/src/util/config/types/subconfigurations/limits/RateLimits.ts @@ -16,11 +16,11 @@ along with this program. If not, see . */ -import { RouteRateLimit, RateLimitOptions } from "."; +import { RateLimitOptions, RouteRateLimit } from "."; export class RateLimits { enabled: boolean = false; - ip: Omit = { + ip: RateLimitOptions = { count: 500, window: 5, }; diff --git a/src/util/schemas/responses/GeneralConfigurationResponse.ts b/src/util/schemas/responses/GeneralConfigurationResponse.ts new file mode 100644 index 00000000..4feaa32d --- /dev/null +++ b/src/util/schemas/responses/GeneralConfigurationResponse.ts @@ -0,0 +1,3 @@ +import { GeneralConfiguration } from "../../config"; + +export type GeneralConfigurationResponse = GeneralConfiguration; diff --git a/src/util/schemas/responses/InstanceDomainsResponse.ts b/src/util/schemas/responses/InstanceDomainsResponse.ts new file mode 100644 index 00000000..60367492 --- /dev/null +++ b/src/util/schemas/responses/InstanceDomainsResponse.ts @@ -0,0 +1,6 @@ +export interface InstanceDomainsResponse { + cdn: string; + gateway: string; + defaultApiVersion: string; + apiEndpoint: string; +} diff --git a/src/util/schemas/responses/InstanceStatsResponse.ts b/src/util/schemas/responses/InstanceStatsResponse.ts new file mode 100644 index 00000000..d24fd434 --- /dev/null +++ b/src/util/schemas/responses/InstanceStatsResponse.ts @@ -0,0 +1,8 @@ +export interface InstanceStatsResponse { + counts: { + user: number; + guild: number; + message: number; + members: number; + }; +} diff --git a/src/util/schemas/responses/LimitsConfigurationResponse.ts b/src/util/schemas/responses/LimitsConfigurationResponse.ts new file mode 100644 index 00000000..f40ab918 --- /dev/null +++ b/src/util/schemas/responses/LimitsConfigurationResponse.ts @@ -0,0 +1,3 @@ +import { LimitsConfiguration } from "../../config"; + +export type LimitsConfigurationResponse = LimitsConfiguration; diff --git a/src/util/schemas/responses/index.ts b/src/util/schemas/responses/index.ts index c5e18406..1e4f30cb 100644 --- a/src/util/schemas/responses/index.ts +++ b/src/util/schemas/responses/index.ts @@ -11,6 +11,7 @@ export * from "./ChannelPinsResponse"; export * from "./ChannelWebhooksResponse"; export * from "./GatewayBotResponse"; export * from "./GatewayResponse"; +export * from "./GeneralConfigurationResponse"; export * from "./GenerateRegistrationTokensResponse"; export * from "./GuildBansResponse"; export * from "./GuildChannelsResponse"; @@ -29,6 +30,9 @@ export * from "./GuildVanityUrl"; export * from "./GuildVoiceRegionsResponse"; export * from "./GuildWidgetJsonResponse"; export * from "./GuildWidgetSettingsResponse"; +export * from "./InstanceDomainsResponse"; +export * from "./InstanceStatsResponse"; +export * from "./LimitsConfigurationResponse"; export * from "./LocationMetadataResponse"; export * from "./MemberJoinGuildResponse"; export * from "./OAuthAuthorizeResponse";