@internetderdinge/api 1.229.3 → 1.229.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@internetderdinge/api",
3
- "version": "1.229.3",
3
+ "version": "1.229.4",
4
4
  "description": "Shared OpenIoT API modules",
5
5
  "main": "dist/src/index.js",
6
6
  "type": "module",
@@ -36,7 +36,7 @@ const getAccountById = catchAsync(
36
36
  throw new ApiError(httpStatus.NOT_FOUND, "Account not found");
37
37
  }
38
38
  res.send({
39
- ...account.data,
39
+ ...account,
40
40
  notification: entryDeviceNotifications?.settings,
41
41
  });
42
42
  },
@@ -46,7 +46,7 @@ const setDeviceToken = catchAsync(
46
46
  async (req: AuthenticatedRequest, res: Response): Promise<void> => {
47
47
  const account = await accountsService.getAccountById(req.auth.sub);
48
48
 
49
- const devices: Device[] = account.data.app_metadata.devices || [];
49
+ const devices: Device[] = account.app_metadata.devices || [];
50
50
  const alreadyExisting = devices.find((d) => d.fck === req.body.token);
51
51
  if (!alreadyExisting) {
52
52
  devices.push({ fck: req.body.token });
@@ -74,7 +74,9 @@ const updateEntry = catchAsync(
74
74
  async (req: AuthenticatedRequest, res: Response): Promise<void> => {
75
75
  const account = await accountsService.getAccountById(req.auth.sub);
76
76
 
77
- const { isSocial } = account?.data.identities[0];
77
+ console.log("account", account);
78
+
79
+ const { isSocial } = account.identities[0];
78
80
 
79
81
  const {
80
82
  given_name,
@@ -93,7 +95,7 @@ const updateEntry = catchAsync(
93
95
 
94
96
  const update = isSocial
95
97
  ? {
96
- ...account.data.app_metadata,
98
+ ...account.app_metadata,
97
99
  ...updateBody,
98
100
  ...(hasGivenName ? { first_name: trimmedGivenName } : {}),
99
101
  ...(hasFamilyName ? { last_name: trimmedFamilyName } : {}),
@@ -136,7 +138,8 @@ const deleteCurrent = catchAsync(
136
138
  const current = catchAsync(
137
139
  async (req: AuthenticatedRequest, res: Response): Promise<void> => {
138
140
  const user = await accountsService.getAccountById(req.auth.sub);
139
- res.send(user.data);
141
+ console.log("user", user);
142
+ res.send(user);
140
143
  },
141
144
  );
142
145
 
@@ -35,25 +35,21 @@ export const getUsersSchema = zPagination;
35
35
 
36
36
  export const getAccountSchema = {
37
37
  params: z.object({
38
- accountId: z
39
- .string()
40
- .openapi({
41
- example:
42
- process.env.SCHEMA_EXAMPLE_ACCOUNT_ID || "auth0|60452f4c0dc85b0062326",
43
- description: "Auth Account ID",
44
- }),
38
+ accountId: z.string().openapi({
39
+ example:
40
+ process.env.SCHEMA_EXAMPLE_ACCOUNT_ID || "auth0|60452f4c0dc85b0062326",
41
+ description: "Auth Account ID",
42
+ }),
45
43
  }),
46
44
  };
47
45
 
48
46
  export const updateAccountSchema = {
49
47
  params: z.object({
50
- accountId: z
51
- .string()
52
- .openapi({
53
- example:
54
- process.env.SCHEMA_EXAMPLE_ACCOUNT_ID || "auth0|60452f4c0dc85b0062326",
55
- description: "Auth Account ID",
56
- }),
48
+ accountId: z.string().openapi({
49
+ example:
50
+ process.env.SCHEMA_EXAMPLE_ACCOUNT_ID || "auth0|60452f4c0dc85b0062326",
51
+ description: "Auth Account ID",
52
+ }),
57
53
  }),
58
54
  body: zPatchBody({
59
55
  language: z
@@ -67,9 +63,10 @@ export const updateAccountSchema = {
67
63
  .optional()
68
64
  .openapi({ example: "female", description: "Gender" }),
69
65
  email: z
70
- .string()
71
- .email()
72
- .optional()
66
+ .preprocess(
67
+ (value) => (value === "" ? undefined : value),
68
+ z.string().email().optional(),
69
+ )
73
70
  .openapi({ description: "User email address" }),
74
71
  given_name: z
75
72
  .string()
@@ -90,13 +87,11 @@ export const updateAccountSchema = {
90
87
 
91
88
  export const deleteEntrySchema = {
92
89
  params: z.object({
93
- accountId: z
94
- .string()
95
- .openapi({
96
- example:
97
- process.env.SCHEMA_EXAMPLE_ACCOUNT_ID || "auth0|60452f4c0dc85b0062326",
98
- description: "Auth Account ID",
99
- }),
90
+ accountId: z.string().openapi({
91
+ example:
92
+ process.env.SCHEMA_EXAMPLE_ACCOUNT_ID || "auth0|60452f4c0dc85b0062326",
93
+ description: "Auth Account ID",
94
+ }),
100
95
  }),
101
96
  };
102
97
 
@@ -21,6 +21,7 @@ let tokenManagementClient: TokenManagementClient = {
21
21
  };
22
22
 
23
23
  //if (config.env !== 'production') {
24
+ /*
24
25
  try {
25
26
  console.warn("Auth0 client: use local token from cache try");
26
27
  const token = readFileSync("./token.txt", "utf8");
@@ -28,7 +29,7 @@ try {
28
29
  tokenManagementClient = { token };
29
30
  } catch (error) {
30
31
  console.log("Auth0 Client: use new token");
31
- }
32
+ } */
32
33
  //}
33
34
 
34
35
  // IoT Api
@@ -123,12 +124,12 @@ export const getAuth0Token = async (): Promise<string> => {
123
124
  pendingTokenPromise = null;
124
125
  return cachedToken;
125
126
  }
126
- //}
127
127
 
128
+ console.warn("Auth0 Client: Requesting new token from Auth0");
128
129
  const tokenResponse =
129
130
  await auth0AuthClient.oauth.clientCredentialsGrant(grantOpts);
130
- const expiresIn = tokenResponse.data.expires_in || 3600;
131
- cachedToken = tokenResponse.data.access_token;
131
+ const expiresIn = tokenResponse.expires_in || 3600;
132
+ cachedToken = tokenResponse.access_token;
132
133
  tokenExpiresAt = now + expiresIn;
133
134
 
134
135
  // if (process.env.NODE_ENV !== 'production') {
@@ -159,6 +160,7 @@ export const getAuth0ManagementToken = async (): Promise<string> => {
159
160
 
160
161
  pendingManagementTokenPromise = (async () => {
161
162
  const fileToken = await loadTokenFromFile(MANAGEMENT_TOKEN_FILE_PATH);
163
+
162
164
  if (fileToken && fileToken.expiresAt > now + TOKEN_BUFFER_SECONDS) {
163
165
  cachedManagementToken = fileToken.token;
164
166
  managementTokenExpiresAt = fileToken.expiresAt;
@@ -166,8 +168,10 @@ export const getAuth0ManagementToken = async (): Promise<string> => {
166
168
  return cachedManagementToken;
167
169
  }
168
170
 
171
+ console.warn("Auth0 Management Client: Requesting new token from Auth0");
169
172
  const tokenResponse =
170
173
  await auth0AuthClient.oauth.clientCredentialsGrant(grantOpts);
174
+
171
175
  const expiresIn = tokenResponse.data.expires_in || 3600;
172
176
  cachedManagementToken = tokenResponse.data.access_token;
173
177
  managementTokenExpiresAt = now + expiresIn;
@@ -238,7 +242,7 @@ export const getUsersByIds = async (postIDs: string[]): Promise<User[]> => {
238
242
  };
239
243
 
240
244
  const page = await auth0.users.list(params);
241
- return page.data || [];
245
+ return page || [];
242
246
  };
243
247
 
244
248
  export default {
@@ -94,6 +94,17 @@ export const devicesRouteSpecs: RouteSpec[] = [
94
94
  {
95
95
  method: "post",
96
96
  path: "/:deviceId",
97
+ validate: [auth("manageUsers"), validateDevice, validateOrganizationUpdate],
98
+ requestSchema: updateDeviceSchema,
99
+ responseSchema: deviceResponseSchema,
100
+ handler: devicesController.updateEntry,
101
+ summary: "Update a device",
102
+ description:
103
+ "Modify the properties of an existing device identified by its ID.",
104
+ },
105
+ {
106
+ method: "delete",
107
+ path: "/:deviceId",
97
108
  handler: devicesController.deleteEntry,
98
109
  summary: "Delete a device",
99
110
  description: "Remove the specified device from the system.",
@@ -22,6 +22,8 @@ export const setDeviceToken = catchAsync(
22
22
  user: res.req.auth.sub,
23
23
  body: req.body,
24
24
  });
25
+
26
+ console.log("Setting device tokenddddd for user:", res.req.auth.sub);
25
27
  res.status(httpStatus.CREATED).send(user);
26
28
  },
27
29
  );
@@ -36,17 +36,18 @@ const verifyCallback: VerifyCallback =
36
36
  return reject(new ApiError(httpStatus.FORBIDDEN, "Forbidden"));
37
37
  }
38
38
  }
39
-
40
39
  resolve();
41
40
  };
42
41
 
43
42
  const auth = function authFactory(...requiredRights: string[]) {
43
+ console.log("Creating auth middleware with required rights:", requiredRights);
44
44
  return async function authMiddleware(
45
45
  req: AuthRequest,
46
46
  res: Response,
47
47
  next: NextFunction,
48
48
  ): Promise<void> {
49
49
  try {
50
+ console.log("Authenticating request:");
50
51
  // Check for custom token in X-API-Key header
51
52
  const apiKey = req.headers["x-api-key"] as string | undefined;
52
53
  if (apiKey && apiKey.length === 64) {
@@ -93,6 +94,7 @@ const auth = function authFactory(...requiredRights: string[]) {
93
94
  err.message || "Sorry we were unable to process your request.";
94
95
  return res.status(status).send({ message });
95
96
  }
97
+
96
98
  next();
97
99
  });
98
100
  } catch (error) {
@@ -1,20 +1,31 @@
1
- import httpStatus from 'http-status';
2
- import ApiError from '../utils/ApiError';
3
- import type { Request, Response, NextFunction } from 'express';
1
+ import httpStatus from "http-status";
2
+ import ApiError from "../utils/ApiError";
3
+ import type { Request, Response, NextFunction } from "express";
4
4
 
5
5
  const isAdmin = (user: Record<string, any> | undefined): boolean => {
6
- //return false;
6
+ return false;
7
7
  if (!user) return false;
8
8
 
9
9
  // return false; // TODO: Remove this line when the user object is properly defined
10
- return user['https://memo.wirewire.de/roles'] ? user['https://memo.wirewire.de/roles'].includes('admin') : false;
10
+ return user["https://memo.wirewire.de/roles"]
11
+ ? user["https://memo.wirewire.de/roles"].includes("admin")
12
+ : false;
11
13
  };
12
14
 
13
- const validateAdmin = async (req: Request, res: Response, next: NextFunction): Promise<void> => {
15
+ const validateAdmin = async (
16
+ req: Request,
17
+ res: Response,
18
+ next: NextFunction,
19
+ ): Promise<void> => {
14
20
  if (isAdmin(req.auth)) {
15
21
  next();
16
22
  } else {
17
- next(new ApiError(httpStatus.FORBIDDEN, 'User is not part of the admin group (validateAdmin)'));
23
+ next(
24
+ new ApiError(
25
+ httpStatus.FORBIDDEN,
26
+ "User is not part of the admin group (validateAdmin)",
27
+ ),
28
+ );
18
29
  }
19
30
  };
20
31
 
@@ -138,7 +138,6 @@ export const userRouteSpecs: RouteSpec[] = [
138
138
  handler: userController.updateUser,
139
139
  summary: "Update a user by ID",
140
140
  description: "Replaces a user’s full record with the provided data.",
141
- memoOnly: true,
142
141
  },
143
142
  {
144
143
  method: "patch",
@@ -149,7 +148,6 @@ export const userRouteSpecs: RouteSpec[] = [
149
148
  handler: userController.updateUser,
150
149
  summary: "Partially update a user by ID",
151
150
  description: "Applies partial updates to a user’s record by ID.",
152
- memoOnly: true,
153
151
  },
154
152
  {
155
153
  method: "delete",
@@ -149,7 +149,21 @@ export const getUserByOwner = async (
149
149
  ): Promise<any | null> => {
150
150
  const user = await User.findOne({ owner, organization });
151
151
  if (!user) return null;
152
+
153
+ console.log(
154
+ "Found user for owner and organization:",
155
+ owner,
156
+ organization,
157
+ user,
158
+ );
152
159
  const auth0User = await populateAuth0User(user);
160
+
161
+ console.log(
162
+ "Found user for owner and organizationddddddd:",
163
+ owner,
164
+ organization,
165
+ user,
166
+ );
153
167
  const json = user.toJSON();
154
168
  json.auth0User = auth0User;
155
169
  return json;
@@ -71,21 +71,6 @@ export const getCurrentUserSchema = {
71
71
  export const updateUserSchema = {
72
72
  ...zUpdate("userId"),
73
73
  body: zPatchBody({
74
- password: z
75
- .string()
76
- .refine(
77
- (val) => {
78
- try {
79
- password(val);
80
- return true;
81
- } catch {
82
- return false;
83
- }
84
- },
85
- { message: "Invalid password format" },
86
- )
87
- .optional()
88
- .openapi({ description: "New user password" }),
89
74
  name: z.string().optional().openapi({ description: "User full name" }),
90
75
  timezone: z.string().optional().openapi({ description: "IANA timezone" }),
91
76
  avatar: z.string().optional().openapi({ description: "Avatar URL" }),
@@ -107,7 +92,11 @@ export const updateUserSchema = {
107
92
  .enum(["user", "admin", "patient", "onlyself"])
108
93
  .optional()
109
94
  .openapi({ description: "User role" }),
110
- inviteCode: z.string().optional().openapi({ description: "Invite code" }),
95
+ inviteCode: z
96
+ .string()
97
+ .nullable()
98
+ .optional()
99
+ .openapi({ description: "Invite code" }),
111
100
  organization: zObjectId
112
101
  .optional()
113
102
  .openapi({ description: "Organization ObjectId" }),
@@ -128,7 +117,11 @@ export const updateInviteSchema = {
128
117
  body: z.object({
129
118
  organization: zObjectId.openapi({ description: "Organization ObjectId" }),
130
119
  status: z.enum(["accepted"]).openapi({ description: "Invite status" }),
131
- inviteCode: z.string().optional().openapi({ description: "Invite code" }),
120
+ inviteCode: z
121
+ .string()
122
+ .nullable()
123
+ .optional()
124
+ .openapi({ description: "Invite code" }),
132
125
  }),
133
126
  };
134
127
 
@@ -5,7 +5,7 @@ import type { Patient } from "../types/patient"; // Assuming a `Patient` type ex
5
5
  const generateUserName = async (patient: Patient): Promise<string | null> => {
6
6
  if (patient.owner) {
7
7
  const auth0UserById = await getUserById(patient.owner);
8
- patient.auth0User = auth0UserById.data;
8
+ patient.auth0User = auth0UserById;
9
9
  }
10
10
 
11
11
  if (patient?.auth0User?.app_metadata?.first_name) {