dce-reactkit 3.11.4 → 3.12.1-beta-cross-server.2
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/.vscode/settings.json +1 -3
- package/README.md +20 -0
- package/dist/cjs/index.js +294 -162
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/types/helpers/dataSigner.d.ts +38 -0
- package/dist/cjs/types/helpers/genRouteHandler.d.ts +10 -10
- package/dist/cjs/types/helpers/visitEndpointOnAnotherServer/index.d.ts +15 -13
- package/dist/cjs/types/helpers/visitEndpointOnAnotherServer/sendServerToServerRequest.d.ts +0 -6
- package/dist/cjs/types/index.d.ts +3 -2
- package/dist/cjs/types/server/initCrossServerCredentialCollection.d.ts +8 -0
- package/dist/cjs/types/server/initServer.d.ts +11 -0
- package/dist/cjs/types/types/CrossServerCredential.d.ts +11 -0
- package/dist/cjs/types/types/ReactKitErrorCode.d.ts +13 -1
- package/dist/esm/index.js +293 -162
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/types/helpers/dataSigner.d.ts +38 -0
- package/dist/esm/types/helpers/genRouteHandler.d.ts +10 -10
- package/dist/esm/types/helpers/visitEndpointOnAnotherServer/index.d.ts +15 -13
- package/dist/esm/types/helpers/visitEndpointOnAnotherServer/sendServerToServerRequest.d.ts +0 -6
- package/dist/esm/types/index.d.ts +3 -2
- package/dist/esm/types/server/initCrossServerCredentialCollection.d.ts +8 -0
- package/dist/esm/types/server/initServer.d.ts +11 -0
- package/dist/esm/types/types/CrossServerCredential.d.ts +11 -0
- package/dist/esm/types/types/ReactKitErrorCode.d.ts +13 -1
- package/dist/index.d.ts +62 -35
- package/genEncodedSecret.ts +28 -0
- package/package.json +5 -2
- package/src/components/IntelliTable.tsx +1 -1
- package/src/components/ItemPicker/NestableItemList.tsx +0 -1
- package/src/helpers/dataSigner.ts +232 -0
- package/src/helpers/genRouteHandler.ts +55 -95
- package/src/helpers/visitEndpointOnAnotherServer/index.ts +42 -41
- package/src/helpers/visitEndpointOnAnotherServer/sendServerToServerRequest.ts +3 -5
- package/src/index.ts +4 -2
- package/src/server/initCrossServerCredentialCollection.ts +16 -0
- package/src/server/initServer.ts +18 -0
- package/src/types/CrossServerCredential.ts +16 -0
- package/src/types/ReactKitErrorCode.tsx +13 -1
- package/dist/cjs/types/helpers/getWordCount.d.ts +0 -10
- package/dist/esm/types/helpers/getWordCount.d.ts +0 -10
- package/src/helpers/getWordCount.ts +0 -26
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Sign data with a private reactkit key, package it into a signed data pack
|
|
3
|
+
* @author Gabe Abrams
|
|
4
|
+
* @param opts object containing all arguments
|
|
5
|
+
* @param opts.method the method to sign
|
|
6
|
+
* @param opts.path the http request path
|
|
7
|
+
* @param opts.params the data in the body to sign
|
|
8
|
+
* @param opts.key the reactkit key to sign with
|
|
9
|
+
* @param opts.secret the reactkit secret to sign with
|
|
10
|
+
* @return the signed data
|
|
11
|
+
*/
|
|
12
|
+
export declare const createSignedPack: (opts: {
|
|
13
|
+
method: string;
|
|
14
|
+
path: string;
|
|
15
|
+
params: {
|
|
16
|
+
[key: string]: any;
|
|
17
|
+
};
|
|
18
|
+
key: string;
|
|
19
|
+
secret: string;
|
|
20
|
+
}) => string;
|
|
21
|
+
/**
|
|
22
|
+
* Parse signed pack. Throws an error if invalid
|
|
23
|
+
* @author Gabe Abrams
|
|
24
|
+
* @param opts object containing all arguments
|
|
25
|
+
* @param opts.method the method of the data validate
|
|
26
|
+
* @param opts.path the http request path to validate
|
|
27
|
+
* @param opts.scope the name of the scope to validate
|
|
28
|
+
* @param opts.signedPack the signed data pack to validate
|
|
29
|
+
* @returns parsed and validated params
|
|
30
|
+
*/
|
|
31
|
+
export declare const parseSignedPack: (opts: {
|
|
32
|
+
method: string;
|
|
33
|
+
path: string;
|
|
34
|
+
scope: string;
|
|
35
|
+
signedPack: string;
|
|
36
|
+
}) => Promise<{
|
|
37
|
+
[key: string]: any;
|
|
38
|
+
}>;
|
|
@@ -7,14 +7,15 @@ import LogFunction from '../types/LogFunction';
|
|
|
7
7
|
* @param opts.paramTypes map containing the types for each parameter that is
|
|
8
8
|
* included in the request (map: param name => type)
|
|
9
9
|
* @param opts.handler function that processes the request
|
|
10
|
-
* @param [opts.
|
|
11
|
-
*
|
|
12
|
-
*
|
|
13
|
-
*
|
|
14
|
-
*
|
|
15
|
-
*
|
|
16
|
-
*
|
|
17
|
-
*
|
|
10
|
+
* @param [opts.crossServerScope] the scope associated with this endpoint.
|
|
11
|
+
* If defined, this is a cross-server endpoint, which will never
|
|
12
|
+
* have any launch data, will never check Canvas roles or launch status, and will
|
|
13
|
+
* instead use scopes and reactkit credentials to sign and validate requests.
|
|
14
|
+
* Never start the path with /api/ttm or /api/admin if the endpoint is a cross-server
|
|
15
|
+
* endpoint because those roles will not be validated
|
|
16
|
+
* @param [opts.skipSessionCheck=true if crossServerScope defined] if true, skip
|
|
17
|
+
* the session check (allow users to not be logged in and launched via LTI).
|
|
18
|
+
* If crossServerScope is defined, this is always true
|
|
18
19
|
* @param [opts.unhandledErrorMessagePrefix] if included, when an error that
|
|
19
20
|
* is not of type ErrorWithCode is thrown, the client will receive an error
|
|
20
21
|
* where the error message is prefixed with this string. For example,
|
|
@@ -68,9 +69,8 @@ declare const genRouteHandler: (opts: {
|
|
|
68
69
|
}) => void;
|
|
69
70
|
logServerEvent: LogFunction;
|
|
70
71
|
}) => any;
|
|
72
|
+
crossServerScope?: string | undefined;
|
|
71
73
|
skipSessionCheck?: boolean | undefined;
|
|
72
|
-
allowedHosts?: string | string[] | undefined;
|
|
73
|
-
bannedHosts?: string | string[] | undefined;
|
|
74
74
|
unhandledErrorMessagePrefix?: string | undefined;
|
|
75
75
|
}) => (req: any, res: any, next: () => void) => Promise<undefined>;
|
|
76
76
|
export default genRouteHandler;
|
|
@@ -1,24 +1,26 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
3
|
-
* dce-reactkit [for server only]
|
|
2
|
+
* Visit an endpoint on another server
|
|
4
3
|
* @author Gabe Abrams
|
|
5
4
|
* @param opts object containing all arguments
|
|
6
|
-
* @param opts.
|
|
7
|
-
* @param opts.path
|
|
8
|
-
* @param
|
|
9
|
-
* @param [opts.
|
|
10
|
-
*
|
|
11
|
-
* @
|
|
5
|
+
* @param opts.method the method of the endpoint
|
|
6
|
+
* @param opts.path the path of the other server's endpoint
|
|
7
|
+
* @param opts.host the host of the other server
|
|
8
|
+
* @param [opts.key=process.env.REACTKIT_CROSS_SERVER_CREDENTIAL_KEY] reactkit cross-server
|
|
9
|
+
* credential key
|
|
10
|
+
* @param [opts.secret=process.env.REACTKIT_CROSS_SERVER_CREDENTIAL_SECRET reactkit cross-server
|
|
11
|
+
* credential secret
|
|
12
|
+
* @param [opts.params={}] query/body parameters to include
|
|
13
|
+
* @param [opts.responseType=JSON] the response type from the other server
|
|
12
14
|
*/
|
|
13
15
|
declare const visitEndpointOnAnotherServer: (opts: {
|
|
14
|
-
|
|
16
|
+
method: 'GET' | 'POST' | 'DELETE' | 'PUT';
|
|
15
17
|
path: string;
|
|
16
|
-
|
|
18
|
+
host: string;
|
|
19
|
+
key?: string | undefined;
|
|
20
|
+
secret?: string | undefined;
|
|
17
21
|
params?: {
|
|
18
22
|
[x: string]: any;
|
|
19
23
|
} | undefined;
|
|
20
|
-
|
|
21
|
-
[x: string]: any;
|
|
22
|
-
} | undefined;
|
|
24
|
+
responseType?: "Text" | "JSON" | undefined;
|
|
23
25
|
}) => Promise<any>;
|
|
24
26
|
export default visitEndpointOnAnotherServer;
|
|
@@ -6,9 +6,6 @@
|
|
|
6
6
|
* @param [opts.host] host to send request to
|
|
7
7
|
* @param [opts.method=GET] http method to use
|
|
8
8
|
* @param [opts.params] body/data to include in the request
|
|
9
|
-
* @param [opts.headers] headers to include in the request
|
|
10
|
-
* @param [opts.sendCrossDomainCredentials=true if in development mode] if true,
|
|
11
|
-
* send cross-domain credentials even if not in dev mode
|
|
12
9
|
* @param [opts.responseType=JSON] expected response type
|
|
13
10
|
* @returns { body, status, headers } on success
|
|
14
11
|
*/
|
|
@@ -19,9 +16,6 @@ declare const sendServerToServerRequest: (opts: {
|
|
|
19
16
|
params?: {
|
|
20
17
|
[x: string]: any;
|
|
21
18
|
} | undefined;
|
|
22
|
-
headers?: {
|
|
23
|
-
[x: string]: any;
|
|
24
|
-
} | undefined;
|
|
25
19
|
responseType?: "Text" | "JSON" | undefined;
|
|
26
20
|
}) => Promise<{
|
|
27
21
|
body: any;
|
|
@@ -54,6 +54,7 @@ import onlyKeepLetters from './helpers/onlyKeepLetters';
|
|
|
54
54
|
import parallelLimit from './helpers/parallelLimit';
|
|
55
55
|
import logClientEvent, { setClientEventMetadataPopulator } from './helpers/logClientEvent';
|
|
56
56
|
import initLogCollection from './server/initLogCollection';
|
|
57
|
+
import initCrossServerCredentialCollection from './server/initCrossServerCredentialCollection';
|
|
57
58
|
import getMonthName from './helpers/getMonthName';
|
|
58
59
|
import genCSV from './helpers/genCSV';
|
|
59
60
|
import canReviewLogs from './helpers/canReviewLogs';
|
|
@@ -79,7 +80,6 @@ import someAsync from './helpers/asyncArrayFunctions/someAsync';
|
|
|
79
80
|
import capitalize from './helpers/capitalize';
|
|
80
81
|
import shuffleArray from './helpers/shuffleArray';
|
|
81
82
|
import visitEndpointOnAnotherServer from './helpers/visitEndpointOnAnotherServer';
|
|
82
|
-
import getWordCount from './helpers/getWordCount';
|
|
83
83
|
import ModalButtonType from './types/ModalButtonType';
|
|
84
84
|
import ModalSize from './types/ModalSize';
|
|
85
85
|
import ModalType from './types/ModalType';
|
|
@@ -96,8 +96,9 @@ import LogMetadataType from './types/LogMetadataType';
|
|
|
96
96
|
import LogFunction from './types/LogFunction';
|
|
97
97
|
import IntelliTableColumn from './types/IntelliTableColumn';
|
|
98
98
|
import DropdownItemType from './types/DropdownItemType';
|
|
99
|
+
import CrossServerCredential from './types/CrossServerCredential';
|
|
99
100
|
import PickableItem from './components/ItemPicker/types/PickableItem';
|
|
100
101
|
import DBEntry from './components/DBEntryManagerPanel/types/DBEntry';
|
|
101
102
|
import DBEntryField from './components/DBEntryManagerPanel/types/DBEntryField';
|
|
102
103
|
import DBEntryFieldType from './components/DBEntryManagerPanel/types/DBEntryFieldType';
|
|
103
|
-
export { AppWrapper, LoadingSpinner, ErrorBox, Modal, TabBox, RadioButton, CheckboxButton, ButtonInputGroup, SimpleDateChooser, Drawer, PopSuccessMark, PopFailureMark, PopPendingMark, CopiableBox, ItemPicker, LogReviewer, IntelliTable, CSVDownloadButton, DBEntryManagerPanel, Tooltip, ToggleSwitch, AutoscrollToBottomContainer, MultiSwitch, Dropdown, alert, prompt, confirm, showFatalError, ErrorWithCode, MINUTE_IN_MS, HOUR_IN_MS, DAY_IN_MS, DynamicWord, abbreviate, avg, ceilToNumDecimals, floorToNumDecimals, forceNumIntoBounds, padDecimalZeros, padZerosLeft, roundToNumDecimals, sum, waitMs, getOrdinal, getTimeInfoInET, stubServerEndpoint, startMinWait, getHumanReadableDate, getPartOfDay, stringsToHumanReadableList, onlyKeepLetters, parallelLimit, getMonthName, genCSV, canReviewLogs, isMobileOrTablet, extractProp, compareArraysByProp, genCommaList, validateEmail, validatePhoneNumber, validateString, getLocalTimeInfo, idify, makeLinksClickable, prefixWithAOrAn, everyAsync, filterAsync, forEachAsync, mapAsync, someAsync, capitalize, shuffleArray,
|
|
104
|
+
export { AppWrapper, LoadingSpinner, ErrorBox, Modal, TabBox, RadioButton, CheckboxButton, ButtonInputGroup, SimpleDateChooser, Drawer, PopSuccessMark, PopFailureMark, PopPendingMark, CopiableBox, ItemPicker, LogReviewer, IntelliTable, CSVDownloadButton, DBEntryManagerPanel, Tooltip, ToggleSwitch, AutoscrollToBottomContainer, MultiSwitch, Dropdown, alert, prompt, confirm, showFatalError, ErrorWithCode, MINUTE_IN_MS, HOUR_IN_MS, DAY_IN_MS, DynamicWord, abbreviate, avg, ceilToNumDecimals, floorToNumDecimals, forceNumIntoBounds, padDecimalZeros, padZerosLeft, roundToNumDecimals, sum, waitMs, getOrdinal, getTimeInfoInET, stubServerEndpoint, startMinWait, getHumanReadableDate, getPartOfDay, stringsToHumanReadableList, onlyKeepLetters, parallelLimit, getMonthName, genCSV, canReviewLogs, isMobileOrTablet, extractProp, compareArraysByProp, genCommaList, validateEmail, validatePhoneNumber, validateString, getLocalTimeInfo, idify, makeLinksClickable, prefixWithAOrAn, everyAsync, filterAsync, forEachAsync, mapAsync, someAsync, capitalize, shuffleArray, initClient, visitServerEndpoint, logClientEvent, addFatalErrorHandler, leaveToURL, combineClassNames, useForceRender, setClientEventMetadataPopulator, initServer, genRouteHandler, handleError, handleSuccess, initLogCollection, initCrossServerCredentialCollection, addDBEditorEndpoints, visitEndpointOnAnotherServer, ModalButtonType, ModalSize, ModalType, ReactKitErrorCode, Variant, DayOfWeek, Log, LogType, LogSource, LogAction, LogBuiltInMetadata, LogMetadataType, LogFunction, IntelliTableColumn, DropdownItemType, CrossServerCredential, PickableItem, DBEntry, DBEntryField, DBEntryFieldType, ParamType, };
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Initialize a cross-server credential collection given the dce-mango Collection class
|
|
3
|
+
* @author Gabe Abrams
|
|
4
|
+
* @param Collection the Collection class from dce-mango
|
|
5
|
+
* @returns initialized logCollection
|
|
6
|
+
*/
|
|
7
|
+
declare const initCrossServerCredentialCollection: (Collection: any) => any;
|
|
8
|
+
export default initCrossServerCredentialCollection;
|
|
@@ -16,6 +16,13 @@ export declare const cacclGetLaunchInfo: GetLaunchInfoFunction;
|
|
|
16
16
|
* have a log collection (yet)
|
|
17
17
|
*/
|
|
18
18
|
export declare const internalGetLogCollection: () => any;
|
|
19
|
+
/**
|
|
20
|
+
* Get cross-server credential collection
|
|
21
|
+
* @author Gabe Abrams
|
|
22
|
+
* @return cross-server credential collection if one was included during launch or null
|
|
23
|
+
* if we don't have a cross-server credential collection (yet)
|
|
24
|
+
*/
|
|
25
|
+
export declare const internalGetCrossServerCredentialCollection: () => any;
|
|
19
26
|
/**
|
|
20
27
|
* Prepare dce-reactkit to run on the server
|
|
21
28
|
* @author Gabe Abrams
|
|
@@ -32,11 +39,15 @@ export declare const internalGetLogCollection: () => any;
|
|
|
32
39
|
* userIds are allowed to review logs. If a dce-mango collection, only
|
|
33
40
|
* Canvas admins with entries in that collection ({ userId, ...}) are allowed
|
|
34
41
|
* to review logs
|
|
42
|
+
* @param [opts.crossServerCredentialCollection] mongo collection from dce-mango to use for
|
|
43
|
+
* storing cross-server credentials. If none is included, cross-server credentials
|
|
44
|
+
* are not supported
|
|
35
45
|
*/
|
|
36
46
|
declare const initServer: (opts: {
|
|
37
47
|
app: any;
|
|
38
48
|
getLaunchInfo: GetLaunchInfoFunction;
|
|
39
49
|
logCollection?: any;
|
|
40
50
|
logReviewAdmins?: (number[] | any);
|
|
51
|
+
crossServerCredentialCollection?: any;
|
|
41
52
|
}) => void;
|
|
42
53
|
export default initServer;
|
|
@@ -20,6 +20,18 @@ declare enum ReactKitErrorCode {
|
|
|
20
20
|
SessionExpiredMessageGottenBeforeReactKitReady = "DRK13",
|
|
21
21
|
NotConnected = "DRK14",
|
|
22
22
|
SelfSigned = "DRK15",
|
|
23
|
-
ResponseParseError = "DRK16"
|
|
23
|
+
ResponseParseError = "DRK16",
|
|
24
|
+
PackUnparseable = "DRK28",
|
|
25
|
+
PackInvalidMethod = "DRK19",
|
|
26
|
+
PackInvalidPath = "DRK20",
|
|
27
|
+
PackInvalidCollection = "DRK21",
|
|
28
|
+
PackInvalidCredential = "DRK23",
|
|
29
|
+
PackInvalidScope = "DRK22",
|
|
30
|
+
PackInvalidTimestamp = "DRK24",
|
|
31
|
+
PackInvalidSignature = "DRK25",
|
|
32
|
+
PackInvalidBody = "DRK26",
|
|
33
|
+
CrossServerNoCredentialsToSignWith = "DRK27",
|
|
34
|
+
CrossServerNoPack = "DRK29",
|
|
35
|
+
CrossServerNoCredentialEncodingSalt = "DRK30"
|
|
24
36
|
}
|
|
25
37
|
export default ReactKitErrorCode;
|
package/dist/index.d.ts
CHANGED
|
@@ -1086,14 +1086,15 @@ type LogFunction = (opts: ({
|
|
|
1086
1086
|
* @param opts.paramTypes map containing the types for each parameter that is
|
|
1087
1087
|
* included in the request (map: param name => type)
|
|
1088
1088
|
* @param opts.handler function that processes the request
|
|
1089
|
-
* @param [opts.
|
|
1090
|
-
*
|
|
1091
|
-
*
|
|
1092
|
-
*
|
|
1093
|
-
*
|
|
1094
|
-
*
|
|
1095
|
-
*
|
|
1096
|
-
*
|
|
1089
|
+
* @param [opts.crossServerScope] the scope associated with this endpoint.
|
|
1090
|
+
* If defined, this is a cross-server endpoint, which will never
|
|
1091
|
+
* have any launch data, will never check Canvas roles or launch status, and will
|
|
1092
|
+
* instead use scopes and reactkit credentials to sign and validate requests.
|
|
1093
|
+
* Never start the path with /api/ttm or /api/admin if the endpoint is a cross-server
|
|
1094
|
+
* endpoint because those roles will not be validated
|
|
1095
|
+
* @param [opts.skipSessionCheck=true if crossServerScope defined] if true, skip
|
|
1096
|
+
* the session check (allow users to not be logged in and launched via LTI).
|
|
1097
|
+
* If crossServerScope is defined, this is always true
|
|
1097
1098
|
* @param [opts.unhandledErrorMessagePrefix] if included, when an error that
|
|
1098
1099
|
* is not of type ErrorWithCode is thrown, the client will receive an error
|
|
1099
1100
|
* where the error message is prefixed with this string. For example,
|
|
@@ -1147,9 +1148,8 @@ declare const genRouteHandler: (opts: {
|
|
|
1147
1148
|
}) => void;
|
|
1148
1149
|
logServerEvent: LogFunction;
|
|
1149
1150
|
}) => any;
|
|
1151
|
+
crossServerScope?: string | undefined;
|
|
1150
1152
|
skipSessionCheck?: boolean | undefined;
|
|
1151
|
-
allowedHosts?: string | string[] | undefined;
|
|
1152
|
-
bannedHosts?: string | string[] | undefined;
|
|
1153
1153
|
unhandledErrorMessagePrefix?: string | undefined;
|
|
1154
1154
|
}) => (req: any, res: any, next: () => void) => Promise<undefined>;
|
|
1155
1155
|
|
|
@@ -1199,12 +1199,16 @@ type GetLaunchInfoFunction = (req: any) => {
|
|
|
1199
1199
|
* userIds are allowed to review logs. If a dce-mango collection, only
|
|
1200
1200
|
* Canvas admins with entries in that collection ({ userId, ...}) are allowed
|
|
1201
1201
|
* to review logs
|
|
1202
|
+
* @param [opts.crossServerCredentialCollection] mongo collection from dce-mango to use for
|
|
1203
|
+
* storing cross-server credentials. If none is included, cross-server credentials
|
|
1204
|
+
* are not supported
|
|
1202
1205
|
*/
|
|
1203
1206
|
declare const initServer: (opts: {
|
|
1204
1207
|
app: any;
|
|
1205
1208
|
getLaunchInfo: GetLaunchInfoFunction;
|
|
1206
1209
|
logCollection?: any;
|
|
1207
1210
|
logReviewAdmins?: (number[] | any);
|
|
1211
|
+
crossServerCredentialCollection?: any;
|
|
1208
1212
|
}) => void;
|
|
1209
1213
|
|
|
1210
1214
|
/**
|
|
@@ -1335,6 +1339,14 @@ declare const logClientEvent: LogFunction;
|
|
|
1335
1339
|
*/
|
|
1336
1340
|
declare const initLogCollection: (Collection: any) => any;
|
|
1337
1341
|
|
|
1342
|
+
/**
|
|
1343
|
+
* Initialize a cross-server credential collection given the dce-mango Collection class
|
|
1344
|
+
* @author Gabe Abrams
|
|
1345
|
+
* @param Collection the Collection class from dce-mango
|
|
1346
|
+
* @returns initialized logCollection
|
|
1347
|
+
*/
|
|
1348
|
+
declare const initCrossServerCredentialCollection: (Collection: any) => any;
|
|
1349
|
+
|
|
1338
1350
|
/**
|
|
1339
1351
|
* Get the name of a month given the month number (1 = January, etc.)
|
|
1340
1352
|
* If an invalid number is provided, we will treat it like January
|
|
@@ -1656,39 +1668,31 @@ declare const capitalize: (str: string) => string;
|
|
|
1656
1668
|
declare const shuffleArray: <T>(arr: T[]) => T[];
|
|
1657
1669
|
|
|
1658
1670
|
/**
|
|
1659
|
-
*
|
|
1660
|
-
* dce-reactkit [for server only]
|
|
1671
|
+
* Visit an endpoint on another server
|
|
1661
1672
|
* @author Gabe Abrams
|
|
1662
1673
|
* @param opts object containing all arguments
|
|
1663
|
-
* @param opts.
|
|
1664
|
-
* @param opts.path
|
|
1665
|
-
* @param
|
|
1666
|
-
* @param [opts.
|
|
1667
|
-
*
|
|
1668
|
-
* @
|
|
1674
|
+
* @param opts.method the method of the endpoint
|
|
1675
|
+
* @param opts.path the path of the other server's endpoint
|
|
1676
|
+
* @param opts.host the host of the other server
|
|
1677
|
+
* @param [opts.key=process.env.REACTKIT_CROSS_SERVER_CREDENTIAL_KEY] reactkit cross-server
|
|
1678
|
+
* credential key
|
|
1679
|
+
* @param [opts.secret=process.env.REACTKIT_CROSS_SERVER_CREDENTIAL_SECRET reactkit cross-server
|
|
1680
|
+
* credential secret
|
|
1681
|
+
* @param [opts.params={}] query/body parameters to include
|
|
1682
|
+
* @param [opts.responseType=JSON] the response type from the other server
|
|
1669
1683
|
*/
|
|
1670
1684
|
declare const visitEndpointOnAnotherServer: (opts: {
|
|
1671
|
-
|
|
1685
|
+
method: 'GET' | 'POST' | 'DELETE' | 'PUT';
|
|
1672
1686
|
path: string;
|
|
1673
|
-
|
|
1687
|
+
host: string;
|
|
1688
|
+
key?: string | undefined;
|
|
1689
|
+
secret?: string | undefined;
|
|
1674
1690
|
params?: {
|
|
1675
1691
|
[x: string]: any;
|
|
1676
1692
|
} | undefined;
|
|
1677
|
-
|
|
1678
|
-
[x: string]: any;
|
|
1679
|
-
} | undefined;
|
|
1693
|
+
responseType?: "Text" | "JSON" | undefined;
|
|
1680
1694
|
}) => Promise<any>;
|
|
1681
1695
|
|
|
1682
|
-
/**
|
|
1683
|
-
* Get number of words in string
|
|
1684
|
-
* @author Gardenia Liu
|
|
1685
|
-
* @author Allison Zhang
|
|
1686
|
-
* @author Gabe Abrams
|
|
1687
|
-
* @param text the string to check
|
|
1688
|
-
* @returns number of words in the string
|
|
1689
|
-
*/
|
|
1690
|
-
declare const getWordCount: (text: string) => number;
|
|
1691
|
-
|
|
1692
1696
|
/**
|
|
1693
1697
|
* List of error codes built into the react kit
|
|
1694
1698
|
* @author Gabe Abrams
|
|
@@ -1711,7 +1715,19 @@ declare enum ReactKitErrorCode {
|
|
|
1711
1715
|
SessionExpiredMessageGottenBeforeReactKitReady = "DRK13",
|
|
1712
1716
|
NotConnected = "DRK14",
|
|
1713
1717
|
SelfSigned = "DRK15",
|
|
1714
|
-
ResponseParseError = "DRK16"
|
|
1718
|
+
ResponseParseError = "DRK16",
|
|
1719
|
+
PackUnparseable = "DRK28",
|
|
1720
|
+
PackInvalidMethod = "DRK19",
|
|
1721
|
+
PackInvalidPath = "DRK20",
|
|
1722
|
+
PackInvalidCollection = "DRK21",
|
|
1723
|
+
PackInvalidCredential = "DRK23",
|
|
1724
|
+
PackInvalidScope = "DRK22",
|
|
1725
|
+
PackInvalidTimestamp = "DRK24",
|
|
1726
|
+
PackInvalidSignature = "DRK25",
|
|
1727
|
+
PackInvalidBody = "DRK26",
|
|
1728
|
+
CrossServerNoCredentialsToSignWith = "DRK27",
|
|
1729
|
+
CrossServerNoPack = "DRK29",
|
|
1730
|
+
CrossServerNoCredentialEncodingSalt = "DRK30"
|
|
1715
1731
|
}
|
|
1716
1732
|
|
|
1717
1733
|
/**
|
|
@@ -1744,4 +1760,15 @@ declare const LogBuiltInMetadata: {
|
|
|
1744
1760
|
};
|
|
1745
1761
|
};
|
|
1746
1762
|
|
|
1747
|
-
|
|
1763
|
+
/**
|
|
1764
|
+
* Single cross-server credential
|
|
1765
|
+
* @author Gabe Abrams
|
|
1766
|
+
*/
|
|
1767
|
+
type CrossServerCredential = {
|
|
1768
|
+
description: string;
|
|
1769
|
+
key: string;
|
|
1770
|
+
encodedeSecret: string;
|
|
1771
|
+
scopes: string[];
|
|
1772
|
+
};
|
|
1773
|
+
|
|
1774
|
+
export { AppWrapper, AutoscrollToBottomContainer, ButtonInputGroup, CSVDownloadButton, CheckboxButton, CopiableBox, CrossServerCredential, DAY_IN_MS, DBEntry, DBEntryField, DBEntryFieldType, DBEntryManagerPanel, DayOfWeek, Drawer, Dropdown, DropdownItemType, DynamicWord, ErrorBox, ErrorWithCode, HOUR_IN_MS, IntelliTable, IntelliTableColumn, ItemPicker, LoadingSpinner, Log, LogAction, LogBuiltInMetadata, LogFunction, LogMetadataType, LogReviewer, LogSource, LogType, MINUTE_IN_MS, Modal, ModalButtonType, ModalSize, ModalType, MultiSwitch, ParamType, PickableItem, PopFailureMark, PopPendingMark, PopSuccessMark, RadioButton, ReactKitErrorCode, SimpleDateChooser, TabBox, ToggleSwitch, Tooltip, Variant, abbreviate, addDBEditorEndpoints, addFatalErrorHandler, alert, avg, canReviewLogs, capitalize, ceilToNumDecimals, combineClassNames, compareArraysByProp, confirm, everyAsync, extractProp, filterAsync, floorToNumDecimals, forEachAsync, forceNumIntoBounds, genCSV, genCommaList, genRouteHandler, getHumanReadableDate, getLocalTimeInfo, getMonthName, getOrdinal, getPartOfDay, getTimeInfoInET, handleError, handleSuccess, idify, initClient, initCrossServerCredentialCollection, initLogCollection, initServer, isMobileOrTablet, leaveToURL, logClientEvent, makeLinksClickable, mapAsync, onlyKeepLetters, padDecimalZeros, padZerosLeft, parallelLimit, prefixWithAOrAn, prompt, roundToNumDecimals, setClientEventMetadataPopulator, showFatalError, shuffleArray, someAsync, startMinWait, stringsToHumanReadableList, stubServerEndpoint, sum, useForceRender, validateEmail, validatePhoneNumber, validateString, visitEndpointOnAnotherServer, visitServerEndpoint, waitMs };
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
// Import jwt
|
|
2
|
+
import jwt from 'jwt-simple';
|
|
3
|
+
|
|
4
|
+
// Get args
|
|
5
|
+
let { REACTKIT_CRED_ENCODING_SALT } = process.env;
|
|
6
|
+
if (!REACTKIT_CRED_ENCODING_SALT) {
|
|
7
|
+
REACTKIT_CRED_ENCODING_SALT = process.env.npm_config_salt;
|
|
8
|
+
}
|
|
9
|
+
if (!REACTKIT_CRED_ENCODING_SALT) {
|
|
10
|
+
console.log('REACTKIT_CRED_ENCODING_SALT is required either as an environment variable or as: --salt=...');
|
|
11
|
+
process.exit(1);
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
// Get secret
|
|
15
|
+
let secret = process.env.npm_config_secret;
|
|
16
|
+
if (!secret) {
|
|
17
|
+
// Generate a random secret
|
|
18
|
+
const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
|
|
19
|
+
secret = '';
|
|
20
|
+
for (let i = 0; i < 64; i++) {
|
|
21
|
+
secret += chars.charAt(Math.floor(Math.random() * chars.length));
|
|
22
|
+
}
|
|
23
|
+
console.log('Generated a random secret. If you have one in mind, use --secret=...');
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
// Encode the secret
|
|
27
|
+
const encodedSecret = jwt.encode(secret, REACTKIT_CRED_ENCODING_SALT);
|
|
28
|
+
console.log(`\nNew Secret Generated!\n\nSecret: ${secret}\n\nEncoded Secret: ${encodedSecret}`);
|
package/package.json
CHANGED
|
@@ -1,13 +1,14 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "dce-reactkit",
|
|
3
|
-
"version": "3.
|
|
3
|
+
"version": "3.12.1-beta-cross-server.2",
|
|
4
4
|
"description": "Shared components for Harvard DCE apps",
|
|
5
5
|
"main": "dist/cjs/index.js",
|
|
6
6
|
"module": "dist/esm/index.js",
|
|
7
7
|
"types": "dist/index.d.ts",
|
|
8
8
|
"scripts": {
|
|
9
9
|
"build": "rm -rf dist && rollup -c",
|
|
10
|
-
"test": "jest --runInBand"
|
|
10
|
+
"test": "jest --runInBand",
|
|
11
|
+
"gen-reactkit-cross-server-secret": "npx tsx genEncodedSecret.ts"
|
|
11
12
|
},
|
|
12
13
|
"jest": {
|
|
13
14
|
"preset": "ts-jest",
|
|
@@ -24,6 +25,7 @@
|
|
|
24
25
|
},
|
|
25
26
|
"homepage": "https://github.com/harvard-edtech/dce-reactkit#readme",
|
|
26
27
|
"dependencies": {
|
|
28
|
+
"jwt-simple": "^0.5.6",
|
|
27
29
|
"qs": "^6.x.x",
|
|
28
30
|
"react-select": "^5.7.3"
|
|
29
31
|
},
|
|
@@ -45,6 +47,7 @@
|
|
|
45
47
|
"@types/bootstrap": "^5.2.8",
|
|
46
48
|
"@types/express": "^4.17.17",
|
|
47
49
|
"@types/jest": "^28.1.7",
|
|
50
|
+
"@types/jwt-simple": "^0.5.36",
|
|
48
51
|
"@types/node": "^20.2.5",
|
|
49
52
|
"@types/react": "^17.0.7",
|
|
50
53
|
"@typescript-eslint/eslint-plugin": "^5.59.9",
|
|
@@ -315,7 +315,7 @@ const IntelliTable: React.FC<Props> = (props) => {
|
|
|
315
315
|
checked={columnVisibilityMap[column.param]}
|
|
316
316
|
ariaLabel={`show "${column.title}" column in the ${title} table`}
|
|
317
317
|
checkedVariant={Variant.Light}
|
|
318
|
-
uncheckedVariant={Variant.
|
|
318
|
+
uncheckedVariant={Variant.Secondary}
|
|
319
319
|
/>
|
|
320
320
|
);
|
|
321
321
|
})
|