scimgateway 4.2.12 → 4.2.14

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/README.md CHANGED
@@ -124,7 +124,7 @@ If internet connection is blocked, we could install on another machine and copy
124
124
 
125
125
  node c:\my-scimgateway
126
126
 
127
- Start a browser
127
+ Start a browser (note, Edge do not pop-up logon dialog box when using http)
128
128
 
129
129
  http://localhost:8880/ping
130
130
  => Health check with a "hello" response
@@ -1170,6 +1170,18 @@ MIT © [Jarle Elshaug](https://www.elshaug.xyz)
1170
1170
 
1171
1171
  ## Change log
1172
1172
 
1173
+ ### v4.2.14
1174
+
1175
+ [Fixed]
1176
+
1177
+ - PUT now returning 404 instead of 500 when trying to update a user/group that does not exist
1178
+
1179
+ ### v4.2.13
1180
+
1181
+ [Fixed]
1182
+
1183
+ - `/ping` now excluded from info logs. If we want ping logging, use something else than lowercase e.g., `/Ping` or `/PING`
1184
+
1173
1185
  ### v4.2.12
1174
1186
 
1175
1187
  [Added]
@@ -317,7 +317,8 @@ const ScimGateway = function () {
317
317
 
318
318
  const logResult = async (ctx, next) => {
319
319
  const started = Date.now()
320
- await next() // once all middleware below completes, this continues
320
+ await next() // once all middleware completes, below continues
321
+ if (ctx.request.url === '/ping' || ctx.request.url === '/favicon.ico') return
321
322
  const ellapsed = (Date.now() - started) + 'ms' // ctx.set('X-ResponseTime', ellapsed)
322
323
  const res = {
323
324
  statusCode: ctx.response.status,
@@ -328,41 +329,39 @@ const ScimGateway = function () {
328
329
  const [authType, authToken] = (ctx.request.header.authorization || '').split(' ') // [0] = 'Basic' or 'Bearer'
329
330
  if (authType === 'Basic') [userName] = (Buffer.from(authToken, 'base64').toString() || '').split(':')
330
331
  if (!userName && authType === 'Bearer') userName = 'token'
331
- if (ctx.request.url !== '/favicon.ico') {
332
- if (ctx.response.status < 200 || ctx.response.status > 299) {
333
- // statusCode check in logResult method...
334
- // "statusCode":xxx in error messages let plugin set error statusCode returned by scimgateway
335
- let pluginStatusCode = 0
336
- const reJson = '^.*"(statusCode)" *: *([0-9][0-9][0-9]).*'
337
- const rePattern = new RegExp(reJson, 'i')
338
- if (res.body.detail) {
339
- const arrMatches = res.body.detail.match(rePattern)
332
+ if (ctx.response.status < 200 || ctx.response.status > 299) {
333
+ // statusCode check in logResult method...
334
+ // "statusCode":xxx in error messages let plugin set error statusCode returned by scimgateway
335
+ let pluginStatusCode = 0
336
+ const reJson = '^.*"(statusCode)" *: *([0-9][0-9][0-9]).*'
337
+ const rePattern = new RegExp(reJson, 'i')
338
+ if (res.body.detail) {
339
+ const arrMatches = res.body.detail.match(rePattern)
340
+ if (Array.isArray(arrMatches) && arrMatches.length === 3) {
341
+ pluginStatusCode = parseInt(arrMatches[2])
342
+ }
343
+ } else if (res.body.Errors) {
344
+ if (Array.isArray(res.body.Errors) && res.body.Errors[0].description && res.body.Errors[0].description) {
345
+ const arrMatches = res.body.Errors[0].description.match(rePattern)
340
346
  if (Array.isArray(arrMatches) && arrMatches.length === 3) {
341
347
  pluginStatusCode = parseInt(arrMatches[2])
342
348
  }
343
- } else if (res.body.Errors) {
344
- if (Array.isArray(res.body.Errors) && res.body.Errors[0].description && res.body.Errors[0].description) {
345
- const arrMatches = res.body.Errors[0].description.match(rePattern)
346
- if (Array.isArray(arrMatches) && arrMatches.length === 3) {
347
- pluginStatusCode = parseInt(arrMatches[2])
348
- }
349
- }
350
349
  }
351
- if (pluginStatusCode > 0) {
352
- ctx.response.status = pluginStatusCode // auto change ctx.response.message
353
- res.statusCode = ctx.response.status
354
- res.statusMessage = ctx.response.message
355
- if (pluginStatusCode === 401 || pluginStatusCode === 403) { // don't reveal original SCIM error message details related to access denied (e.g. using Auth PassThrough)
356
- ctx.response.set('Content-Type', 'application/json; charset=utf-8')
357
- ctx.response.body = { error: 'Access denied' }
358
- res.body = ctx.response.body
359
- }
350
+ }
351
+ if (pluginStatusCode > 0) {
352
+ ctx.response.status = pluginStatusCode // auto change ctx.response.message
353
+ res.statusCode = ctx.response.status
354
+ res.statusMessage = ctx.response.message
355
+ if (pluginStatusCode === 401 || pluginStatusCode === 403) { // don't reveal original SCIM error message details related to access denied (e.g. using Auth PassThrough)
356
+ ctx.response.set('Content-Type', 'application/json; charset=utf-8')
357
+ ctx.response.body = { error: 'Access denied' }
358
+ res.body = ctx.response.body
360
359
  }
361
- // back to logResult...
362
- logger.error(`${gwName}[${pluginName}] ${ellapsed} ${ctx.request.ipcli} ${userName} ${ctx.request.method} ${ctx.request.href} Inbound = ${JSON.stringify(ctx.request.body)} Outbound = ${JSON.stringify(res)}${(config.log.loglevel.file === 'debug' && ctx.request.url !== '/ping') ? '\n' : ''}`)
363
- } else logger.info(`${gwName}[${pluginName}] ${ellapsed} ${ctx.request.ipcli} ${userName} ${ctx.request.method} ${ctx.request.href} Inbound = ${JSON.stringify(ctx.request.body)} Outbound = ${JSON.stringify(res)}${(config.log.loglevel.file === 'debug' && ctx.request.url !== '/ping') ? '\n' : ''}`)
364
- requestCounter += 1 // logged on exit (not win process termination)
365
- }
360
+ }
361
+ // back to logResult...
362
+ logger.error(`${gwName}[${pluginName}] ${ellapsed} ${ctx.request.ipcli} ${userName} ${ctx.request.method} ${ctx.request.href} Inbound = ${JSON.stringify(ctx.request.body)} Outbound = ${JSON.stringify(res)}${(config.log.loglevel.file === 'debug' && ctx.request.url !== '/ping') ? '\n' : ''}`)
363
+ } else logger.info(`${gwName}[${pluginName}] ${ellapsed} ${ctx.request.ipcli} ${userName} ${ctx.request.method} ${ctx.request.href} Inbound = ${JSON.stringify(ctx.request.body)} Outbound = ${JSON.stringify(res)}${(config.log.loglevel.file === 'debug' && ctx.request.url !== '/ping') ? '\n' : ''}`)
364
+ requestCounter += 1 // logged on exit (not win process termination)
366
365
  if (ctx.response.body && typeof ctx.response.body === 'object' && ctx.response.status !== 401) ctx.set('Content-Type', 'application/scim+json; charset=utf-8')
367
366
  }
368
367
 
@@ -1371,11 +1370,21 @@ const ScimGateway = function () {
1371
1370
  logger.debug(`${gwName}[${pluginName}] calling "${handle.getMethod}" and awaiting result`)
1372
1371
  let res = await this[handle.getMethod](ctx.params.baseEntity, { attribute: 'id', operator: 'eq', value: id }, [], ctx.ctxCopy)
1373
1372
 
1374
- let currentObj = {}
1375
- if (res && res.Resources && Array.isArray(res.Resources) && res.Resources.length === 1) currentObj = res.Resources[0]
1376
- else if (Array.isArray(res) && res.length === 1) currentObj = res[0]
1373
+ let currentObj
1374
+ if (res && res.Resources && Array.isArray(res.Resources)) {
1375
+ if (res.Resources.length === 1) currentObj = res.Resources[0]
1376
+ else currentObj = {}
1377
+ } else if (Array.isArray(res) && res.length === 1) currentObj = res[0]
1377
1378
  else if (res && typeof (res) === 'object' && Object.keys(res).length > 0) currentObj = res
1378
- else throw Error(`put using method ${handle.getMethod} got unexpected response: ${JSON.stringify(res)}`)
1379
+ else currentObj = {}
1380
+
1381
+ if (typeof (currentObj) !== 'object' || Object.keys(currentObj).length === 0) {
1382
+ ctx.status = 404
1383
+ let err = new Error(`put using method ${handle.getMethod} error: ${handle.description.toLowerCase()} id=${id} does not exist`)
1384
+ err = jsonErr(config.scim.version, pluginName, ctx.status, err)
1385
+ ctx.body = err
1386
+ return
1387
+ }
1379
1388
 
1380
1389
  const clearedObj = clearObjectValues(currentObj)
1381
1390
  delete clearedObj.active
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "scimgateway",
3
- "version": "4.2.12",
3
+ "version": "4.2.14",
4
4
  "description": "Using SCIM protocol as a gateway for user provisioning to other endpoints",
5
5
  "author": "Jarle Elshaug <jarle.elshaug@gmail.com> (https://elshaug.xyz)",
6
6
  "homepage": "https://elshaug.xyz",