Skip to content

Commit a9b552e

Browse files
committed
Metadata post route
1 parent ecfdf40 commit a9b552e

File tree

2 files changed

+67
-4
lines changed

2 files changed

+67
-4
lines changed

src/api/routes/organizations.ts

Lines changed: 64 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,26 @@
11
import { FastifyPluginAsync } from "fastify";
22
import { AllOrganizationList } from "@acm-uiuc/js-shared";
33
import rateLimiter from "api/plugins/rateLimiter.js";
4-
import { withTags } from "api/components/index.js";
4+
import { withRoles, withTags } from "api/components/index.js";
55
import { z } from "zod/v4";
6-
import { getOrganizationInfoResponse } from "common/types/organizations.js";
6+
import {
7+
getOrganizationInfoResponse,
8+
setOrganizationMetaBody,
9+
} from "common/types/organizations.js";
710
import { FastifyZodOpenApiTypeProvider } from "fastify-zod-openapi";
8-
import { BaseError, DatabaseFetchError } from "common/errors/index.js";
11+
import {
12+
BaseError,
13+
DatabaseFetchError,
14+
DatabaseInsertError,
15+
} from "common/errors/index.js";
916
import { getOrgInfo } from "api/functions/organizations.js";
17+
import { AppRoles } from "common/roles.js";
18+
import {
19+
PutItemCommand,
20+
TransactWriteItemsCommand,
21+
} from "@aws-sdk/client-dynamodb";
22+
import { genericConfig } from "common/config.js";
23+
import { marshall } from "@aws-sdk/util-dynamodb";
1024

1125
export const ORG_DATA_CACHED_DURATION = 300;
1226
export const CLIENT_HTTP_CACHE_POLICY = `public, max-age=${ORG_DATA_CACHED_DURATION}, stale-while-revalidate=${Math.floor(ORG_DATA_CACHED_DURATION * 1.1)}, stale-if-error=3600`;
@@ -23,7 +37,7 @@ const organizationsPlugin: FastifyPluginAsync = async (fastify, _options) => {
2337
}
2438
return payload;
2539
});
26-
fastify.get(
40+
fastify.withTypeProvider<FastifyZodOpenApiTypeProvider>().get(
2741
"",
2842
{
2943
schema: withTags(["Organizations"], {
@@ -102,6 +116,52 @@ const organizationsPlugin: FastifyPluginAsync = async (fastify, _options) => {
102116
return reply.send(response);
103117
},
104118
);
119+
fastify.withTypeProvider<FastifyZodOpenApiTypeProvider>().post(
120+
"/:id/meta",
121+
{
122+
schema: withRoles(
123+
[AppRoles.ALL_ORG_MANAGER],
124+
withTags(["Organizations"], {
125+
summary: "Set metadata for an ACM @ UIUC sub-organization.",
126+
params: z.object({
127+
id: z
128+
.enum(AllOrganizationList)
129+
.meta({ description: "ACM @ UIUC organization to modify." }),
130+
}),
131+
body: setOrganizationMetaBody,
132+
response: {
133+
201: {
134+
description: "The information was saved.",
135+
content: {
136+
"application/json": {
137+
schema: z.null(),
138+
},
139+
},
140+
},
141+
},
142+
}),
143+
),
144+
onRequest: fastify.authorizeFromSchema,
145+
},
146+
async (request, reply) => {
147+
try {
148+
const command = new PutItemCommand({
149+
TableName: genericConfig.SigInfoTableName,
150+
Item: marshall(request.body, { removeUndefinedValues: true }),
151+
});
152+
await fastify.dynamoClient.send(command);
153+
} catch (e) {
154+
if (e instanceof BaseError) {
155+
throw e;
156+
}
157+
request.log.error(e);
158+
throw new DatabaseInsertError({
159+
message: "Failed to set org information.",
160+
});
161+
}
162+
reply.status(201).send();
163+
},
164+
);
105165
};
106166

107167
export default organizationsPlugin;

src/common/types/organizations.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,13 @@ export const orgLinkEntry = z.object({
1515
url: z.url()
1616
})
1717

18+
1819
export const getOrganizationInfoResponse = z.object({
1920
id: z.enum(AllOrganizationList),
2021
description: z.optional(z.string()),
2122
website: z.optional(z.url()),
2223
leads: z.optional(z.array(orgLeadEntry)),
2324
links: z.optional(z.array(orgLinkEntry))
2425
})
26+
27+
export const setOrganizationMetaBody = getOrganizationInfoResponse.omit({ id: true, leads: true });

0 commit comments

Comments
 (0)