dce-reactkit 3.9.1 → 3.9.3
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/dist/cjs/index.js +100 -26
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/types/helpers/genRouteHandler.d.ts +8 -0
- package/dist/cjs/types/types/ReactKitErrorCode.d.ts +2 -0
- package/dist/esm/index.js +100 -26
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/types/helpers/genRouteHandler.d.ts +8 -0
- package/dist/esm/types/types/ReactKitErrorCode.d.ts +2 -0
- package/dist/index.d.ts +10 -0
- package/package.json +1 -1
- package/src/helpers/genRouteHandler.ts +109 -10
- package/src/types/ReactKitErrorCode.tsx +3 -1
package/dist/cjs/index.js
CHANGED
|
@@ -59,7 +59,7 @@ function __awaiter(thisArg, _arguments, P, generator) {
|
|
|
59
59
|
});
|
|
60
60
|
}
|
|
61
61
|
|
|
62
|
-
// Highest error code =
|
|
62
|
+
// Highest error code = DRK18
|
|
63
63
|
/**
|
|
64
64
|
* List of error codes built into the react kit
|
|
65
65
|
* @author Gabe Abrams
|
|
@@ -71,6 +71,8 @@ var ReactKitErrorCode;
|
|
|
71
71
|
ReactKitErrorCode["SessionExpired"] = "DRK3";
|
|
72
72
|
ReactKitErrorCode["MissingParameter"] = "DRK4";
|
|
73
73
|
ReactKitErrorCode["InvalidParameter"] = "DRK5";
|
|
74
|
+
ReactKitErrorCode["HostNotAllowed"] = "DRK17";
|
|
75
|
+
ReactKitErrorCode["HostBanned"] = "DRK18";
|
|
74
76
|
ReactKitErrorCode["WrongCourse"] = "DRK6";
|
|
75
77
|
ReactKitErrorCode["NoCACCLSendRequestFunction"] = "DRK7";
|
|
76
78
|
ReactKitErrorCode["NoCACCLGetLaunchInfoFunction"] = "DRK8";
|
|
@@ -14469,6 +14471,12 @@ const parseUserAgent = (userAgent) => {
|
|
|
14469
14471
|
* @param opts.handler function that processes the request
|
|
14470
14472
|
* @param [opts.skipSessionCheck] if true, skip the session check (allow users
|
|
14471
14473
|
* to not be logged in and launched via LTI)
|
|
14474
|
+
* @param [opts.allowedHosts] if included, only allow requests from these hosts
|
|
14475
|
+
* (start a hostname with a "*" to only check the end of the hostname)
|
|
14476
|
+
* you can include just one string instead of an array
|
|
14477
|
+
* @param [opts.bannedHosts] if included, do not allow requests from these hosts
|
|
14478
|
+
* (start a hostname with a "*" to only check the end of the hostname)
|
|
14479
|
+
* you can include just one string instead of an array
|
|
14472
14480
|
* @param [opts.unhandledErrorMessagePrefix] if included, when an error that
|
|
14473
14481
|
* is not of type ErrorWithCode is thrown, the client will receive an error
|
|
14474
14482
|
* where the error message is prefixed with this string. For example,
|
|
@@ -14496,10 +14504,76 @@ const parseUserAgent = (userAgent) => {
|
|
|
14496
14504
|
const genRouteHandler = (opts) => {
|
|
14497
14505
|
// Return a route handler
|
|
14498
14506
|
return (req, res, next) => __awaiter(void 0, void 0, void 0, function* () {
|
|
14499
|
-
var _a, _b, _c;
|
|
14507
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o;
|
|
14500
14508
|
// Output params
|
|
14501
14509
|
const output = {};
|
|
14502
14510
|
/*----------------------------------------*/
|
|
14511
|
+
/* ----------- Hostname Check ----------- */
|
|
14512
|
+
/*----------------------------------------*/
|
|
14513
|
+
// Get hostnames
|
|
14514
|
+
const originURL = String(req.get('origin')
|
|
14515
|
+
|| req.headers.origin
|
|
14516
|
+
|| req.headers.referer);
|
|
14517
|
+
const originHostname = (originURL
|
|
14518
|
+
// Remove protocol
|
|
14519
|
+
.replace(/(^\w+:|^)\/\//, '')
|
|
14520
|
+
// Remove port
|
|
14521
|
+
.replace(/:\d+$/, ''));
|
|
14522
|
+
const serverHostname = String(req.hostname);
|
|
14523
|
+
// Check allowed
|
|
14524
|
+
if (opts.allowedHosts) {
|
|
14525
|
+
// Only accept requests from allowed hosts
|
|
14526
|
+
const allowedArray = (Array.isArray(opts.allowedHosts)
|
|
14527
|
+
? opts.allowedHosts
|
|
14528
|
+
: [opts.allowedHosts]);
|
|
14529
|
+
// Check if server is localhost
|
|
14530
|
+
if (serverHostname === 'localhost') {
|
|
14531
|
+
// Allow localhost
|
|
14532
|
+
allowedArray.push('localhost');
|
|
14533
|
+
}
|
|
14534
|
+
// Check if current host is allowed
|
|
14535
|
+
const allowed = allowedArray.some((allowedHost) => {
|
|
14536
|
+
if (allowedHost.startsWith('*')) {
|
|
14537
|
+
// Check end of hostname
|
|
14538
|
+
return originHostname.endsWith(allowedHost.substring(1));
|
|
14539
|
+
}
|
|
14540
|
+
// Check full hostname
|
|
14541
|
+
return originHostname.toLowerCase() === allowedHost.toLowerCase();
|
|
14542
|
+
});
|
|
14543
|
+
// If not allowed, return error
|
|
14544
|
+
if (!allowed) {
|
|
14545
|
+
return handleError(res, {
|
|
14546
|
+
message: 'You are not allowed to access this endpoint.',
|
|
14547
|
+
code: ReactKitErrorCode$1.HostNotAllowed,
|
|
14548
|
+
status: 403,
|
|
14549
|
+
});
|
|
14550
|
+
}
|
|
14551
|
+
}
|
|
14552
|
+
// Check banned
|
|
14553
|
+
if (opts.bannedHosts) {
|
|
14554
|
+
// Do not allow requests from banned hosts
|
|
14555
|
+
const bannedArray = (Array.isArray(opts.bannedHosts)
|
|
14556
|
+
? opts.bannedHosts
|
|
14557
|
+
: [opts.bannedHosts]);
|
|
14558
|
+
// Check if current host is banned
|
|
14559
|
+
const banned = bannedArray.some((bannedHost) => {
|
|
14560
|
+
if (bannedHost.startsWith('*')) {
|
|
14561
|
+
// Check end of hostname
|
|
14562
|
+
return originHostname.endsWith(bannedHost.substring(1));
|
|
14563
|
+
}
|
|
14564
|
+
// Check full hostname
|
|
14565
|
+
return originHostname.toLowerCase() === bannedHost.toLowerCase();
|
|
14566
|
+
});
|
|
14567
|
+
// If banned, return error
|
|
14568
|
+
if (banned) {
|
|
14569
|
+
return handleError(res, {
|
|
14570
|
+
message: 'You are not allowed to access this endpoint.',
|
|
14571
|
+
code: ReactKitErrorCode$1.HostBanned,
|
|
14572
|
+
status: 403,
|
|
14573
|
+
});
|
|
14574
|
+
}
|
|
14575
|
+
}
|
|
14576
|
+
/*----------------------------------------*/
|
|
14503
14577
|
/* ------------ Parse Params ------------ */
|
|
14504
14578
|
/*----------------------------------------*/
|
|
14505
14579
|
// Process items one by one
|
|
@@ -14697,34 +14771,34 @@ const genRouteHandler = (opts) => {
|
|
|
14697
14771
|
// Add launch info to output
|
|
14698
14772
|
output.userId = (launchInfo
|
|
14699
14773
|
? launchInfo.userId
|
|
14700
|
-
: undefined);
|
|
14774
|
+
: ((_b = output.userId) !== null && _b !== void 0 ? _b : undefined));
|
|
14701
14775
|
output.userFirstName = (launchInfo
|
|
14702
14776
|
? launchInfo.userFirstName
|
|
14703
|
-
: undefined);
|
|
14777
|
+
: ((_c = output.userFirstName) !== null && _c !== void 0 ? _c : undefined));
|
|
14704
14778
|
output.userLastName = (launchInfo
|
|
14705
14779
|
? launchInfo.userLastName
|
|
14706
|
-
: undefined);
|
|
14780
|
+
: ((_d = output.userLastName) !== null && _d !== void 0 ? _d : undefined));
|
|
14707
14781
|
output.userEmail = (launchInfo
|
|
14708
14782
|
? launchInfo.userEmail
|
|
14709
|
-
: undefined);
|
|
14783
|
+
: ((_e = output.userEmail) !== null && _e !== void 0 ? _e : undefined));
|
|
14710
14784
|
output.userAvatarURL = (launchInfo
|
|
14711
|
-
? ((
|
|
14712
|
-
: undefined);
|
|
14785
|
+
? ((_f = launchInfo.userImage) !== null && _f !== void 0 ? _f : 'http://www.gravatar.com/avatar/?d=identicon')
|
|
14786
|
+
: ((_g = output.userAvatarURL) !== null && _g !== void 0 ? _g : undefined));
|
|
14713
14787
|
output.isLearner = (launchInfo
|
|
14714
14788
|
? !!launchInfo.isLearner
|
|
14715
|
-
: undefined);
|
|
14789
|
+
: ((_h = output.isLearner) !== null && _h !== void 0 ? _h : undefined));
|
|
14716
14790
|
output.isTTM = (launchInfo
|
|
14717
14791
|
? !!launchInfo.isTTM
|
|
14718
|
-
: undefined);
|
|
14792
|
+
: ((_j = output.isTTM) !== null && _j !== void 0 ? _j : undefined));
|
|
14719
14793
|
output.isAdmin = (launchInfo
|
|
14720
14794
|
? !!launchInfo.isAdmin
|
|
14721
|
-
: undefined);
|
|
14795
|
+
: ((_k = output.isAdmin) !== null && _k !== void 0 ? _k : undefined));
|
|
14722
14796
|
output.courseId = (launchInfo
|
|
14723
|
-
? ((
|
|
14724
|
-
: undefined);
|
|
14797
|
+
? ((_l = output.courseId) !== null && _l !== void 0 ? _l : launchInfo.courseId)
|
|
14798
|
+
: ((_m = output.courseId) !== null && _m !== void 0 ? _m : undefined));
|
|
14725
14799
|
output.courseName = (launchInfo
|
|
14726
14800
|
? launchInfo.contextLabel
|
|
14727
|
-
: undefined);
|
|
14801
|
+
: ((_o = output.courseName) !== null && _o !== void 0 ? _o : undefined));
|
|
14728
14802
|
// Add other session variables
|
|
14729
14803
|
Object.keys(req.session).forEach((propName) => {
|
|
14730
14804
|
// Skip if prop already in output
|
|
@@ -14798,7 +14872,7 @@ const genRouteHandler = (opts) => {
|
|
|
14798
14872
|
* @author Gabe Abrams
|
|
14799
14873
|
*/
|
|
14800
14874
|
const logServerEvent = (logOpts) => __awaiter(void 0, void 0, void 0, function* () {
|
|
14801
|
-
var
|
|
14875
|
+
var _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _0, _1;
|
|
14802
14876
|
// NOTE: internally, we slip through an opts.overrideAsClientEvent boolean
|
|
14803
14877
|
// that indicates that this is actually a client event, but we don't
|
|
14804
14878
|
// include that in the LogFunction type because this is internal and
|
|
@@ -14830,24 +14904,24 @@ const genRouteHandler = (opts) => {
|
|
|
14830
14904
|
timestamp,
|
|
14831
14905
|
context: (typeof logOpts.context === 'string'
|
|
14832
14906
|
? logOpts.context
|
|
14833
|
-
: ((
|
|
14834
|
-
subcontext: ((
|
|
14835
|
-
tags: ((
|
|
14836
|
-
level: ((
|
|
14837
|
-
metadata: ((
|
|
14907
|
+
: ((_q = ((_p = logOpts.context) !== null && _p !== void 0 ? _p : {})._) !== null && _q !== void 0 ? _q : LogBuiltInMetadata.Context.Uncategorized)),
|
|
14908
|
+
subcontext: ((_r = logOpts.subcontext) !== null && _r !== void 0 ? _r : LogBuiltInMetadata.Context.Uncategorized),
|
|
14909
|
+
tags: ((_s = logOpts.tags) !== null && _s !== void 0 ? _s : []),
|
|
14910
|
+
level: ((_t = logOpts.level) !== null && _t !== void 0 ? _t : LogLevel$1.Info),
|
|
14911
|
+
metadata: ((_u = logOpts.metadata) !== null && _u !== void 0 ? _u : {}),
|
|
14838
14912
|
};
|
|
14839
14913
|
// Type-specific info
|
|
14840
14914
|
const typeSpecificInfo = (('error' in opts && opts.error)
|
|
14841
14915
|
? {
|
|
14842
14916
|
type: LogType$1.Error,
|
|
14843
|
-
errorMessage: (
|
|
14844
|
-
errorCode: (
|
|
14845
|
-
errorStack: (
|
|
14917
|
+
errorMessage: (_v = logOpts.error.message) !== null && _v !== void 0 ? _v : 'Unknown message',
|
|
14918
|
+
errorCode: (_w = logOpts.error.code) !== null && _w !== void 0 ? _w : ReactKitErrorCode$1.NoCode,
|
|
14919
|
+
errorStack: (_x = logOpts.error.stack) !== null && _x !== void 0 ? _x : 'No stack',
|
|
14846
14920
|
}
|
|
14847
14921
|
: {
|
|
14848
14922
|
type: LogType$1.Action,
|
|
14849
|
-
target: ((
|
|
14850
|
-
action: ((
|
|
14923
|
+
target: ((_y = logOpts.target) !== null && _y !== void 0 ? _y : LogBuiltInMetadata.Target.NoTarget),
|
|
14924
|
+
action: ((_z = logOpts.action) !== null && _z !== void 0 ? _z : LogAction$1.Unknown),
|
|
14851
14925
|
});
|
|
14852
14926
|
// Source-specific info
|
|
14853
14927
|
const sourceSpecificInfo = (logOpts.overrideAsClientEvent
|
|
@@ -14882,7 +14956,7 @@ const genRouteHandler = (opts) => {
|
|
|
14882
14956
|
catch (err) {
|
|
14883
14957
|
// Print because we cannot store the error
|
|
14884
14958
|
// eslint-disable-next-line no-console
|
|
14885
|
-
console.error('Could not log the following:', logOpts, 'due to this error:', ((
|
|
14959
|
+
console.error('Could not log the following:', logOpts, 'due to this error:', ((_0 = err) !== null && _0 !== void 0 ? _0 : {}).message, ((_1 = err) !== null && _1 !== void 0 ? _1 : {}).stack);
|
|
14886
14960
|
// Create a dummy log to return
|
|
14887
14961
|
const dummyMainInfo = {
|
|
14888
14962
|
id: '-1',
|