rhombus-node-mcp
Version:
MCP server for Rhombus API
127 lines (126 loc) • 4.83 kB
JavaScript
import { postApi } from "../network/network.js";
export async function listUsers(requestModifiers, sessionId) {
const res = await postApi({
route: "/user/getUsersInOrg",
body: {},
modifiers: requestModifiers,
sessionId,
});
if (res.error) {
throw new Error(JSON.stringify(res));
}
return (res.users?.map(user => ({
uuid: user.uuid ?? undefined,
email: user.email ?? undefined,
firstName: user.firstName ?? undefined,
lastName: user.lastName ?? undefined,
})) ?? []);
}
export async function findUserByEmail(email, requestModifiers, sessionId) {
const res = await postApi({
route: "/user/findUserByEmail",
body: { email },
modifiers: requestModifiers,
sessionId,
});
if (res.error) {
throw new Error(JSON.stringify(res));
}
const user = res.user;
if (!user)
return undefined;
return {
uuid: user.uuid ?? undefined,
email: user.email ?? undefined,
firstName: user.firstName ?? undefined,
lastName: user.lastName ?? undefined,
role: user.roleUuid ?? undefined,
orgUuid: user.orgUuid ?? undefined,
lastLoginMs: user.lastLoginMs ?? undefined,
enabled: user.enabled ?? undefined,
mfaEnabled: user.mfaEnabled ?? undefined,
};
}
export async function getPermissionsForCurrentUser(requestModifiers, sessionId) {
const res = await postApi({
route: "/permission/getPermissionsForCurrentUser",
body: {},
modifiers: requestModifiers,
sessionId,
});
if (res.error) {
throw new Error(JSON.stringify(res));
}
return {
role: res.role ?? undefined,
functionalityAccessMap: res.functionalityAccessMap
? Object.fromEntries(Object.entries(res.functionalityAccessMap).map(([k, v]) => [k, String(v)]))
: undefined,
};
}
/**
* Keep only non-null string entries from a nullable string[] coming back from
* the generated schema types.
*/
function cleanStringArray(arr) {
if (!arr)
return undefined;
const cleaned = arr.filter((v) => typeof v === "string");
return cleaned.length > 0 ? cleaned : undefined;
}
/**
* Map a `{ [k]: PermissionEnum }` to a `Record<string, string>` dropping null
* values. Returns undefined when the input is nullish so the field is omitted
* from the JSON payload entirely (and the filtering proxy's `includeFields`
* can omit it without ambiguity).
*/
function toStringMap(map) {
if (!map)
return undefined;
const entries = Object.entries(map).filter((pair) => typeof pair[1] === "string");
return entries.length > 0 ? Object.fromEntries(entries) : undefined;
}
function toNestedStringMap(map) {
if (!map)
return undefined;
const result = {};
for (const [outer, inner] of Object.entries(map)) {
const cleanedInner = toStringMap(inner);
if (cleanedInner)
result[outer] = cleanedInner;
}
return Object.keys(result).length > 0 ? result : undefined;
}
export async function getPermissionGroups(requestModifiers, sessionId) {
const res = await postApi({
route: "/permission/getPermissionGroupsForOrg",
body: {},
modifiers: requestModifiers,
sessionId,
});
if (res.error) {
throw new Error(JSON.stringify(res));
}
return (res.permissionGroups?.map(group => ({
uuid: group.uuid ?? undefined,
name: group.name ?? undefined,
description: group.description ?? undefined,
orgUuid: group.orgUuid ?? undefined,
mutable: group.mutable ?? undefined,
superAdmin: group.superAdmin ?? undefined,
installer: group.installer ?? undefined,
inLine: group.inLine ?? undefined,
storedInS3: group.storedInS3 ?? undefined,
defaultPermissionForNewLocations: group.defaultPermissionForNewLocations ?? undefined,
defaultAccessControlPermissionForNewLocations: group.defaultAccessControlPermissionForNewLocations ?? undefined,
functionalityList: group.functionalityList ?? undefined,
accessibleLocations: cleanStringArray(group.accessibleLocations),
assignablePermissionGroups: cleanStringArray(group.assignablePermissionGroups),
// Heavy maps — callers should typically prune these out via includeFields.
locationAccessMap: toStringMap(group.locationAccessMap),
accessControlLocationAccessMap: toStringMap(group.accessControlLocationAccessMap),
deviceAccessMap: toStringMap(group.deviceAccessMap),
userPermissionGroupAccessMap: toStringMap(group.userPermissionGroupAccessMap),
locationGranularAccessMap: toNestedStringMap(group.locationGranularAccessMap),
})) ?? []);
}