opal-security 3.2.1 → 3.2.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/README.md +28 -25
- package/lib/commands/login.js +18 -11
- package/lib/commands/request/create.d.ts +2 -0
- package/lib/commands/request/create.js +41 -20
- package/lib/commands/request/get.js +7 -58
- package/lib/commands/request/list.js +3 -60
- package/lib/graphql/gql.d.ts +35 -15
- package/lib/graphql/gql.js +9 -5
- package/lib/graphql/graphql.d.ts +1138 -383
- package/lib/graphql/graphql.js +1780 -1104
- package/lib/handler.d.ts +6 -6
- package/lib/handler.js +1 -1
- package/lib/labels.d.ts +3 -0
- package/lib/labels.js +40 -0
- package/lib/lib/apollo.d.ts +3 -3
- package/lib/lib/apollo.js +24 -47
- package/lib/lib/request/api/index.d.ts +6 -0
- package/lib/lib/request/api/index.js +20 -0
- package/lib/lib/request/api/mutations/create-request.d.ts +8 -0
- package/lib/lib/request/api/mutations/create-request.js +159 -0
- package/lib/lib/request/api/queries/apps.d.ts +4 -0
- package/lib/lib/request/api/queries/apps.js +73 -0
- package/lib/lib/request/api/queries/assets.d.ts +6 -0
- package/lib/lib/request/api/queries/assets.js +136 -0
- package/lib/lib/request/api/queries/request-defaults.d.ts +5 -0
- package/lib/lib/request/api/queries/request-defaults.js +52 -0
- package/lib/lib/request/api/queries/requests.d.ts +4 -0
- package/lib/lib/request/api/queries/requests.js +163 -0
- package/lib/lib/request/api/queries/roles.d.ts +5 -0
- package/lib/lib/request/api/queries/roles.js +239 -0
- package/lib/{utils → lib/request}/displays.d.ts +7 -5
- package/lib/{utils → lib/request}/displays.js +52 -30
- package/lib/lib/request/prompts/apps-prompt.d.ts +4 -0
- package/lib/lib/request/prompts/apps-prompt.js +35 -0
- package/lib/lib/request/prompts/asset-prompt.d.ts +5 -0
- package/lib/lib/request/prompts/asset-prompt.js +81 -0
- package/lib/lib/request/prompts/duration-prompt.d.ts +2 -0
- package/lib/lib/request/prompts/duration-prompt.js +125 -0
- package/lib/lib/request/prompts/index.d.ts +8 -0
- package/lib/lib/request/prompts/index.js +20 -0
- package/lib/lib/request/prompts/reason-prompt.d.ts +2 -0
- package/lib/lib/request/prompts/reason-prompt.js +20 -0
- package/lib/lib/request/prompts/role-prompt.d.ts +4 -0
- package/lib/lib/request/prompts/role-prompt.js +44 -0
- package/lib/lib/request/prompts/validate-prompt.d.ts +4 -0
- package/lib/lib/request/prompts/validate-prompt.js +29 -0
- package/lib/lib/request/request-utils.d.ts +14 -0
- package/lib/lib/request/request-utils.js +468 -0
- package/lib/lib/request/types.d.ts +55 -0
- package/lib/lib/request/types.js +15 -0
- package/lib/lib/resources.d.ts +1 -1
- package/lib/lib/sessions.d.ts +1 -1
- package/lib/lib/sessions.js +3 -2
- package/lib/lib/util.d.ts +1 -0
- package/lib/lib/util.js +16 -0
- package/lib/types.d.ts +19 -3
- package/lib/types.js +18 -2
- package/oclif.manifest.json +54 -38
- package/package.json +4 -3
- package/lib/lib/requests.d.ts +0 -54
- package/lib/lib/requests.js +0 -1160
- package/lib/utils/utils.d.ts +0 -1
- package/lib/utils/utils.js +0 -18
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.queryRequestDefaults = queryRequestDefaults;
|
|
4
|
+
const graphql_1 = require("../../../../graphql");
|
|
5
|
+
const REQUEST_DEFAULTS_QUERY = (0, graphql_1.graphql)(`
|
|
6
|
+
query RequestDefaults(
|
|
7
|
+
$requestedResources: [RequestConfigurationResourceInput!]!
|
|
8
|
+
$requestedGroups: [RequestConfigurationGroupInput!]!
|
|
9
|
+
) {
|
|
10
|
+
requestDefaults(input: {
|
|
11
|
+
requestedResources: $requestedResources,
|
|
12
|
+
requestedGroups: $requestedGroups,
|
|
13
|
+
}
|
|
14
|
+
) {
|
|
15
|
+
... on RequestDefaults {
|
|
16
|
+
durationOptions {
|
|
17
|
+
durationInMinutes
|
|
18
|
+
label
|
|
19
|
+
}
|
|
20
|
+
recommendedDurationInMinutes
|
|
21
|
+
defaultDurationInMinutes
|
|
22
|
+
maxDurationInMinutes
|
|
23
|
+
requireSupportTicket
|
|
24
|
+
reasonOptional
|
|
25
|
+
requesterIsAdmin
|
|
26
|
+
messages {
|
|
27
|
+
entityId
|
|
28
|
+
level
|
|
29
|
+
code
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
}`);
|
|
34
|
+
async function queryRequestDefaults(cmd, client, requestedResources, requestedGroups) {
|
|
35
|
+
var _a;
|
|
36
|
+
try {
|
|
37
|
+
const resp = await client.query({
|
|
38
|
+
query: REQUEST_DEFAULTS_QUERY,
|
|
39
|
+
variables: {
|
|
40
|
+
requestedResources: requestedResources,
|
|
41
|
+
requestedGroups: requestedGroups,
|
|
42
|
+
},
|
|
43
|
+
fetchPolicy: "network-only", // to avoid caching
|
|
44
|
+
});
|
|
45
|
+
return (_a = resp === null || resp === void 0 ? void 0 : resp.data) === null || _a === void 0 ? void 0 : _a.requestDefaults;
|
|
46
|
+
}
|
|
47
|
+
catch (error) {
|
|
48
|
+
if (error instanceof Error || typeof error === "string") {
|
|
49
|
+
cmd.error(error);
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { ApolloClient } from "@apollo/client";
|
|
2
|
+
export declare const queryRequest: (client: ApolloClient, requestId: string) => Promise<ApolloClient.QueryResult<import("../../../../graphql/graphql").GetRequestQuery>>;
|
|
3
|
+
export declare const queryRequests: (client: ApolloClient, pageSize: number, showPendingOnly: boolean) => Promise<ApolloClient.QueryResult<import("../../../../graphql/graphql").GetRequestsQuery>>;
|
|
4
|
+
export declare const queryBundle: (client: ApolloClient, bundleId: string) => Promise<ApolloClient.QueryResult<import("../../../../graphql/graphql").GetBundleQuery>>;
|
|
@@ -0,0 +1,163 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.queryBundle = exports.queryRequests = exports.queryRequest = void 0;
|
|
4
|
+
const graphql_1 = require("../../../../graphql");
|
|
5
|
+
const RESOURCE_FRAGMENT = (0, graphql_1.graphql)(`
|
|
6
|
+
fragment ResourceFields on Resource {
|
|
7
|
+
displayName
|
|
8
|
+
id
|
|
9
|
+
connectionId
|
|
10
|
+
connection {
|
|
11
|
+
name
|
|
12
|
+
connectionType
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
`);
|
|
16
|
+
const GROUP_FRAGMENT = (0, graphql_1.graphql)(`
|
|
17
|
+
fragment GroupFields on Group {
|
|
18
|
+
name
|
|
19
|
+
id
|
|
20
|
+
connectionId
|
|
21
|
+
connection {
|
|
22
|
+
name
|
|
23
|
+
connectionType
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
`);
|
|
27
|
+
const REQUEST_FIELDS_FRAGMENT = (0, graphql_1.graphql)(`
|
|
28
|
+
fragment RequestFields on Request {
|
|
29
|
+
id
|
|
30
|
+
createdAt
|
|
31
|
+
status
|
|
32
|
+
durationInMinutes
|
|
33
|
+
reason
|
|
34
|
+
requester {
|
|
35
|
+
displayName
|
|
36
|
+
}
|
|
37
|
+
targetUser {
|
|
38
|
+
displayName
|
|
39
|
+
}
|
|
40
|
+
requestedResources {
|
|
41
|
+
resource {
|
|
42
|
+
...ResourceFields
|
|
43
|
+
}
|
|
44
|
+
accessLevel {
|
|
45
|
+
accessLevelName
|
|
46
|
+
accessLevelRemoteId
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
requestedGroups {
|
|
50
|
+
group {
|
|
51
|
+
...GroupFields
|
|
52
|
+
}
|
|
53
|
+
accessLevel {
|
|
54
|
+
accessLevelName
|
|
55
|
+
accessLevelRemoteId
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
`);
|
|
60
|
+
const GET_REQUEST = (0, graphql_1.graphql)(`
|
|
61
|
+
query GetRequest(
|
|
62
|
+
$id: RequestId!
|
|
63
|
+
) {
|
|
64
|
+
request(input: {id: $id}) {
|
|
65
|
+
__typename
|
|
66
|
+
... on RequestResult {
|
|
67
|
+
request {
|
|
68
|
+
...RequestFields
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
... on RequestNotFoundError {
|
|
72
|
+
message
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
`);
|
|
77
|
+
const queryRequest = async (client, requestId) => {
|
|
78
|
+
const resp = await client.query({
|
|
79
|
+
query: GET_REQUEST,
|
|
80
|
+
variables: {
|
|
81
|
+
id: requestId,
|
|
82
|
+
},
|
|
83
|
+
fetchPolicy: "network-only", // to avoid caching
|
|
84
|
+
});
|
|
85
|
+
return resp;
|
|
86
|
+
};
|
|
87
|
+
exports.queryRequest = queryRequest;
|
|
88
|
+
// TODO: Add date filters, search query,
|
|
89
|
+
const GET_OUTGOING_REQUESTS = (0, graphql_1.graphql)(`
|
|
90
|
+
query GetRequests($showPendingOnly: Boolean!, $pageSize: Int) {
|
|
91
|
+
requests(input: {
|
|
92
|
+
requestType: OUTGOING
|
|
93
|
+
maxNumEntries: $pageSize
|
|
94
|
+
filters: {
|
|
95
|
+
showPendingOnly: $showPendingOnly
|
|
96
|
+
}
|
|
97
|
+
}) {
|
|
98
|
+
__typename
|
|
99
|
+
... on RequestsResult {
|
|
100
|
+
requestType
|
|
101
|
+
requests {
|
|
102
|
+
...RequestFields
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
}
|
|
108
|
+
}`);
|
|
109
|
+
const queryRequests = async (client, pageSize, showPendingOnly) => {
|
|
110
|
+
const resp = await client.query({
|
|
111
|
+
query: GET_OUTGOING_REQUESTS,
|
|
112
|
+
variables: {
|
|
113
|
+
pageSize: pageSize,
|
|
114
|
+
showPendingOnly: showPendingOnly,
|
|
115
|
+
},
|
|
116
|
+
fetchPolicy: "network-only", // to avoid caching
|
|
117
|
+
});
|
|
118
|
+
return resp;
|
|
119
|
+
};
|
|
120
|
+
exports.queryRequests = queryRequests;
|
|
121
|
+
const GET_BUNDLE = (0, graphql_1.graphql)(`query GetBundle($id: BundleId!) {
|
|
122
|
+
bundle(input: { id: $id }) {
|
|
123
|
+
__typename
|
|
124
|
+
... on BundleResult {
|
|
125
|
+
bundle {
|
|
126
|
+
name
|
|
127
|
+
id
|
|
128
|
+
items {
|
|
129
|
+
edges {
|
|
130
|
+
accessLevel {
|
|
131
|
+
accessLevelName
|
|
132
|
+
accessLevelRemoteId
|
|
133
|
+
}
|
|
134
|
+
node {
|
|
135
|
+
... on Resource {
|
|
136
|
+
...ResourceFields
|
|
137
|
+
isRequestable
|
|
138
|
+
}
|
|
139
|
+
... on Group {
|
|
140
|
+
...GroupFields
|
|
141
|
+
isRequestable
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
... on BundleNotFoundError {
|
|
149
|
+
message
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
}`);
|
|
153
|
+
const queryBundle = async (client, bundleId) => {
|
|
154
|
+
const resp = await client.query({
|
|
155
|
+
query: GET_BUNDLE,
|
|
156
|
+
variables: {
|
|
157
|
+
id: bundleId,
|
|
158
|
+
},
|
|
159
|
+
fetchPolicy: "network-only", // to avoid caching
|
|
160
|
+
});
|
|
161
|
+
return resp;
|
|
162
|
+
};
|
|
163
|
+
exports.queryBundle = queryBundle;
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import type { ApolloClient } from "@apollo/client";
|
|
2
|
+
import type { Command } from "@oclif/core";
|
|
3
|
+
import type { PromptChoice } from "../../types";
|
|
4
|
+
export declare function queryAssetRoles(cmd: Command, client: ApolloClient, assetType: string, assetId: string): Promise<PromptChoice[] | undefined>;
|
|
5
|
+
export declare function queryAssociatedItems(cmd: Command, client: ApolloClient, id: string, input: string | undefined): Promise<PromptChoice[] | undefined>;
|
|
@@ -0,0 +1,239 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.queryAssetRoles = queryAssetRoles;
|
|
4
|
+
exports.queryAssociatedItems = queryAssociatedItems;
|
|
5
|
+
const graphql_1 = require("../../../../graphql");
|
|
6
|
+
const graphql_2 = require("../../../../graphql/graphql");
|
|
7
|
+
const labels_1 = require("../../../../labels");
|
|
8
|
+
const RESOURCE_ROLES_QUERY = (0, graphql_1.graphql)(`
|
|
9
|
+
query ResourceAccessLevels($resourceId: ResourceId!) {
|
|
10
|
+
accessLevels(input: {
|
|
11
|
+
resourceId: $resourceId,
|
|
12
|
+
onlyMine: false,
|
|
13
|
+
}) {
|
|
14
|
+
__typename
|
|
15
|
+
... on ResourceAccessLevelsResult {
|
|
16
|
+
accessLevels {
|
|
17
|
+
... on ResourceAccessLevel {
|
|
18
|
+
accessLevelName
|
|
19
|
+
accessLevelRemoteId
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
... on ResourceNotFoundError {
|
|
24
|
+
message
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
`);
|
|
29
|
+
const GROUP_ROLES_QUERY = (0, graphql_1.graphql)(`
|
|
30
|
+
query GroupAccessLevels($groupId: GroupId!) {
|
|
31
|
+
groupAccessLevels(
|
|
32
|
+
input: { groupId: $groupId }
|
|
33
|
+
) {
|
|
34
|
+
... on GroupAccessLevelsResult {
|
|
35
|
+
groupId
|
|
36
|
+
accessLevels {
|
|
37
|
+
... on GroupAccessLevel {
|
|
38
|
+
accessLevelName
|
|
39
|
+
accessLevelRemoteId
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
`);
|
|
46
|
+
async function queryAssetRoles(cmd, client, assetType, assetId) {
|
|
47
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k;
|
|
48
|
+
try {
|
|
49
|
+
switch (assetType) {
|
|
50
|
+
case graphql_2.EntityType.Resource: {
|
|
51
|
+
const resp = await client.query({
|
|
52
|
+
query: RESOURCE_ROLES_QUERY,
|
|
53
|
+
variables: {
|
|
54
|
+
resourceId: assetId,
|
|
55
|
+
},
|
|
56
|
+
fetchPolicy: "network-only", // to avoid caching
|
|
57
|
+
});
|
|
58
|
+
// no fall through doesn't consider process.exit();
|
|
59
|
+
let x;
|
|
60
|
+
switch ((_a = resp === null || resp === void 0 ? void 0 : resp.data) === null || _a === void 0 ? void 0 : _a.accessLevels.__typename) {
|
|
61
|
+
case "ResourceAccessLevelsResult":
|
|
62
|
+
return (_d = (_c = (_b = resp.data) === null || _b === void 0 ? void 0 : _b.accessLevels) === null || _c === void 0 ? void 0 : _c.accessLevels) === null || _d === void 0 ? void 0 : _d.map((role) => {
|
|
63
|
+
return {
|
|
64
|
+
message: role.accessLevelName || "",
|
|
65
|
+
value: {
|
|
66
|
+
name: role.accessLevelName || "",
|
|
67
|
+
id: role.accessLevelRemoteId || "",
|
|
68
|
+
},
|
|
69
|
+
};
|
|
70
|
+
});
|
|
71
|
+
case "ResourceNotFoundError":
|
|
72
|
+
x = cmd.error((_f = (_e = resp.data) === null || _e === void 0 ? void 0 : _e.accessLevels) === null || _f === void 0 ? void 0 : _f.message);
|
|
73
|
+
break;
|
|
74
|
+
default:
|
|
75
|
+
cmd.error(resp.error || "Unknown error occurred.");
|
|
76
|
+
}
|
|
77
|
+
return;
|
|
78
|
+
}
|
|
79
|
+
case graphql_2.EntityType.Group: {
|
|
80
|
+
const resp = await client.query({
|
|
81
|
+
query: GROUP_ROLES_QUERY,
|
|
82
|
+
variables: {
|
|
83
|
+
groupId: assetId,
|
|
84
|
+
},
|
|
85
|
+
fetchPolicy: "network-only", // to avoid caching
|
|
86
|
+
});
|
|
87
|
+
// no fall through doesn't consider process.exit();
|
|
88
|
+
let x;
|
|
89
|
+
switch ((_g = resp === null || resp === void 0 ? void 0 : resp.data) === null || _g === void 0 ? void 0 : _g.groupAccessLevels.__typename) {
|
|
90
|
+
case "GroupAccessLevelsResult":
|
|
91
|
+
return (_k = (_j = (_h = resp.data) === null || _h === void 0 ? void 0 : _h.groupAccessLevels) === null || _j === void 0 ? void 0 : _j.accessLevels) === null || _k === void 0 ? void 0 : _k.map((role) => {
|
|
92
|
+
return {
|
|
93
|
+
message: role.accessLevelName,
|
|
94
|
+
value: {
|
|
95
|
+
name: role.accessLevelName,
|
|
96
|
+
id: role.accessLevelRemoteId,
|
|
97
|
+
},
|
|
98
|
+
};
|
|
99
|
+
});
|
|
100
|
+
default:
|
|
101
|
+
x = cmd.error(resp.error || "Unknown error occurred.");
|
|
102
|
+
}
|
|
103
|
+
return;
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
catch (error) {
|
|
108
|
+
if (error instanceof Error || typeof error === "string") {
|
|
109
|
+
cmd.error(error);
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
const ASSOCIATED_ITEMS_QUERY = (0, graphql_1.graphql)(`
|
|
114
|
+
query GetAssociatedItems($resourceId: ResourceId!, $searchQuery: String) {
|
|
115
|
+
resource(input: {
|
|
116
|
+
id: $resourceId
|
|
117
|
+
}) {
|
|
118
|
+
__typename
|
|
119
|
+
... on ResourceResult {
|
|
120
|
+
__typename
|
|
121
|
+
resource {
|
|
122
|
+
associatedItems(
|
|
123
|
+
first: 200
|
|
124
|
+
filters: {
|
|
125
|
+
searchQuery: {
|
|
126
|
+
contains: $searchQuery
|
|
127
|
+
}
|
|
128
|
+
access: REQUESTABLE
|
|
129
|
+
endUserVisible: true
|
|
130
|
+
entityType: {
|
|
131
|
+
in: [GROUP, RESOURCE]
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
) {
|
|
135
|
+
edges {
|
|
136
|
+
__typename
|
|
137
|
+
... on ResourceAssociatedItemEdge {
|
|
138
|
+
alias
|
|
139
|
+
node {
|
|
140
|
+
__typename
|
|
141
|
+
id
|
|
142
|
+
name
|
|
143
|
+
... on Resource {
|
|
144
|
+
accessLevels(
|
|
145
|
+
filters: {
|
|
146
|
+
skipRemoteAccessLevels: false # azure app roles are remote
|
|
147
|
+
}
|
|
148
|
+
) {
|
|
149
|
+
__typename
|
|
150
|
+
accessLevelName
|
|
151
|
+
accessLevelRemoteId
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
... on ResourceNotFoundError {
|
|
161
|
+
message
|
|
162
|
+
}
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
`);
|
|
166
|
+
function appRolesFromEdge(edge) {
|
|
167
|
+
var _a, _b, _c, _d;
|
|
168
|
+
switch (edge.node.__typename) {
|
|
169
|
+
case "Resource": {
|
|
170
|
+
if (edge.node.accessLevels && edge.node.accessLevels.length > 0) {
|
|
171
|
+
return edge.node.accessLevels.map((accessLevel) => ({
|
|
172
|
+
message: accessLevel.accessLevelName || "No Role (Direct access)",
|
|
173
|
+
value: {
|
|
174
|
+
id: edge.node.id + accessLevel.accessLevelRemoteId,
|
|
175
|
+
name: accessLevel.accessLevelName,
|
|
176
|
+
type: labels_1.DisplayLabels[graphql_2.EntityType.Resource],
|
|
177
|
+
toString: () => accessLevel.accessLevelName,
|
|
178
|
+
},
|
|
179
|
+
}));
|
|
180
|
+
}
|
|
181
|
+
return [
|
|
182
|
+
{
|
|
183
|
+
message: (_a = edge.alias) !== null && _a !== void 0 ? _a : edge.node.name,
|
|
184
|
+
value: {
|
|
185
|
+
id: edge.node.id,
|
|
186
|
+
name: (_b = edge.alias) !== null && _b !== void 0 ? _b : edge.node.name,
|
|
187
|
+
type: labels_1.DisplayLabels[graphql_2.EntityType.Resource],
|
|
188
|
+
toString: () => { var _a; return (_a = edge.alias) !== null && _a !== void 0 ? _a : edge.node.name; },
|
|
189
|
+
},
|
|
190
|
+
},
|
|
191
|
+
];
|
|
192
|
+
}
|
|
193
|
+
case "Group":
|
|
194
|
+
return [
|
|
195
|
+
{
|
|
196
|
+
message: `${(_c = edge.alias) !== null && _c !== void 0 ? _c : edge.node.name} ${graphql_2.EntityType.Group}`,
|
|
197
|
+
value: {
|
|
198
|
+
id: edge.node.id,
|
|
199
|
+
name: (_d = edge.alias) !== null && _d !== void 0 ? _d : edge.node.name,
|
|
200
|
+
type: labels_1.DisplayLabels[graphql_2.EntityType.Group],
|
|
201
|
+
toString: () => { var _a; return (_a = edge.alias) !== null && _a !== void 0 ? _a : edge.node.name; },
|
|
202
|
+
},
|
|
203
|
+
},
|
|
204
|
+
];
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
async function queryAssociatedItems(cmd, client, id, input) {
|
|
208
|
+
var _a, _b, _c;
|
|
209
|
+
try {
|
|
210
|
+
const resp = await client.query({
|
|
211
|
+
query: ASSOCIATED_ITEMS_QUERY,
|
|
212
|
+
variables: {
|
|
213
|
+
resourceId: id || "",
|
|
214
|
+
searchQuery: input || "",
|
|
215
|
+
},
|
|
216
|
+
fetchPolicy: "network-only", // to avoid caching
|
|
217
|
+
});
|
|
218
|
+
switch ((_a = resp === null || resp === void 0 ? void 0 : resp.data) === null || _a === void 0 ? void 0 : _a.resource.__typename) {
|
|
219
|
+
case "ResourceResult": {
|
|
220
|
+
const associatedItems = resp.data.resource.resource.associatedItems.edges.filter((edge) => edge.__typename === "ResourceAssociatedItemEdge");
|
|
221
|
+
const initial = [];
|
|
222
|
+
for (const edge of associatedItems) {
|
|
223
|
+
initial.push(...appRolesFromEdge(edge));
|
|
224
|
+
}
|
|
225
|
+
return initial;
|
|
226
|
+
}
|
|
227
|
+
case "ResourceNotFoundError":
|
|
228
|
+
cmd.log((_c = (_b = resp.data) === null || _b === void 0 ? void 0 : _b.resource) === null || _c === void 0 ? void 0 : _c.message);
|
|
229
|
+
break;
|
|
230
|
+
default:
|
|
231
|
+
cmd.error(resp.error || "Unknown error occurred.");
|
|
232
|
+
}
|
|
233
|
+
}
|
|
234
|
+
catch (error) {
|
|
235
|
+
if (error instanceof Error || typeof error === "string") {
|
|
236
|
+
cmd.error(error);
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
}
|
|
@@ -1,10 +1,12 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { ApolloClient } from "@apollo/client";
|
|
2
2
|
import type { Command } from "@oclif/core/lib/command";
|
|
3
|
-
import type { GetRequestQuery, GetRequestsQuery } from "
|
|
4
|
-
import {
|
|
3
|
+
import type { GetRequestQuery, GetRequestsQuery } from "../../graphql/graphql";
|
|
4
|
+
import type { RequestMap, RequestMetadata } from "./types";
|
|
5
5
|
export declare function headerMessage(cmd: Command): void;
|
|
6
6
|
export declare function treeifyRequestMap(cmd: Command, requestMap: RequestMap): void;
|
|
7
7
|
export declare function displayFinalRequestSummary(cmd: Command, metadata: RequestMetadata): void;
|
|
8
8
|
export declare function getStyledStatus(status: string): string;
|
|
9
|
-
export declare function displayRequestDetails(cmd: Command, requestResp:
|
|
10
|
-
export declare function displayRequestListTable(cmd: Command, requestResp:
|
|
9
|
+
export declare function displayRequestDetails(cmd: Command, requestResp: ApolloClient.QueryResult<GetRequestQuery>): void;
|
|
10
|
+
export declare function displayRequestListTable(cmd: Command, requestResp: ApolloClient.QueryResult<GetRequestsQuery>): void;
|
|
11
|
+
export declare function formatDuration(durationInMinutes: number): string;
|
|
12
|
+
export declare function displayRequestAgain(cmd: Command, id: string): void;
|
|
@@ -6,8 +6,10 @@ exports.displayFinalRequestSummary = displayFinalRequestSummary;
|
|
|
6
6
|
exports.getStyledStatus = getStyledStatus;
|
|
7
7
|
exports.displayRequestDetails = displayRequestDetails;
|
|
8
8
|
exports.displayRequestListTable = displayRequestListTable;
|
|
9
|
+
exports.formatDuration = formatDuration;
|
|
10
|
+
exports.displayRequestAgain = displayRequestAgain;
|
|
9
11
|
const chalk_1 = require("chalk");
|
|
10
|
-
const
|
|
12
|
+
const labels_1 = require("../../labels");
|
|
11
13
|
const Table = require("cli-table3");
|
|
12
14
|
function headerMessage(cmd) {
|
|
13
15
|
console.clear();
|
|
@@ -15,6 +17,16 @@ function headerMessage(cmd) {
|
|
|
15
17
|
cmd.log("Opal Access Request ✏️");
|
|
16
18
|
cmd.log("Press Ctrl+C to cancel at any time.\n");
|
|
17
19
|
}
|
|
20
|
+
/*
|
|
21
|
+
Example treeified output:
|
|
22
|
+
|
|
23
|
+
Opal [App]
|
|
24
|
+
└── Infosec Group [Group]
|
|
25
|
+
└── Infosec Prod Databases [Group]
|
|
26
|
+
MongoDB Atlas Test [App]
|
|
27
|
+
└── my-mongo-db-atlas [Resource]
|
|
28
|
+
└── admin:test [Role]
|
|
29
|
+
*/
|
|
18
30
|
function treeifyRequestMap(cmd, requestMap) {
|
|
19
31
|
for (const [_appId, appNode] of Object.entries(requestMap)) {
|
|
20
32
|
// Print App title first (without tree lines)
|
|
@@ -22,7 +34,7 @@ function treeifyRequestMap(cmd, requestMap) {
|
|
|
22
34
|
for (const [_assetId, assetNode] of Object.entries(appNode.assets)) {
|
|
23
35
|
// If okta/azure asset with no role, change asset name
|
|
24
36
|
const assetName = assetNode.assetName || "No Role (Direct access)";
|
|
25
|
-
cmd.log(`└── ${assetName} ${chalk_1.default.dim(`[${
|
|
37
|
+
cmd.log(`└── ${assetName} ${chalk_1.default.dim(`[${labels_1.DisplayLabels[assetNode.type]}]`)}`);
|
|
26
38
|
if (assetNode.roles !== undefined) {
|
|
27
39
|
for (const [_roleId, roleNode] of Object.entries(assetNode.roles)) {
|
|
28
40
|
const roleName = roleNode.roleName;
|
|
@@ -72,39 +84,42 @@ function getStyledStatus(status) {
|
|
|
72
84
|
}
|
|
73
85
|
}
|
|
74
86
|
function displayRequestDetails(cmd, requestResp) {
|
|
75
|
-
var _a, _b, _c, _d, _e, _f;
|
|
76
|
-
switch (requestResp.data.request.__typename) {
|
|
87
|
+
var _a, _b, _c, _d, _e, _f, _g;
|
|
88
|
+
switch ((_a = requestResp.data) === null || _a === void 0 ? void 0 : _a.request.__typename) {
|
|
77
89
|
case "RequestResult": {
|
|
90
|
+
const request = requestResp.data.request.request;
|
|
78
91
|
cmd.log("━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━");
|
|
79
|
-
cmd.log(`Request Details ${chalk_1.default.cyan(
|
|
92
|
+
cmd.log(`Request Details ${chalk_1.default.cyan(request.id)}`);
|
|
80
93
|
cmd.log("━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━");
|
|
81
|
-
const status =
|
|
94
|
+
const status = request.status;
|
|
82
95
|
cmd.log(getStyledStatus(status));
|
|
83
96
|
// Request users "Requested by: <requester> -> Requested for: <targetUser>"
|
|
84
|
-
const requester = (
|
|
85
|
-
const targetUser = (
|
|
97
|
+
const requester = (_b = request.requester) === null || _b === void 0 ? void 0 : _b.displayName;
|
|
98
|
+
const targetUser = (_c = request.targetUser) === null || _c === void 0 ? void 0 : _c.displayName;
|
|
86
99
|
if (requester && targetUser) {
|
|
87
100
|
cmd.log(`${chalk_1.default.bold("Requested by:")} ${requester} ${chalk_1.default.gray("->")} ${chalk_1.default.bold("Requested for:")} ${targetUser}`);
|
|
88
101
|
}
|
|
89
|
-
const durationInMinutes =
|
|
102
|
+
const durationInMinutes = request.durationInMinutes;
|
|
90
103
|
cmd.log(`${chalk_1.default.bold("Duration:")} ${durationInMinutes ? formatDuration(durationInMinutes) : "Permanent"}`);
|
|
91
|
-
const reason =
|
|
104
|
+
const reason = request.reason;
|
|
92
105
|
if (reason) {
|
|
93
106
|
cmd.log(`${chalk_1.default.bold("Reason:")} "${chalk_1.default.italic(reason)}"`);
|
|
94
107
|
}
|
|
95
108
|
// Requested resources
|
|
96
|
-
const requestedResources = (
|
|
97
|
-
var _a, _b
|
|
109
|
+
const requestedResources = (_e = (_d = request.requestedResources) === null || _d === void 0 ? void 0 : _d.map((resource) => {
|
|
110
|
+
var _a, _b;
|
|
98
111
|
if (((_a = resource.resource) === null || _a === void 0 ? void 0 : _a.__typename) === "Resource") {
|
|
99
|
-
|
|
112
|
+
const requestedResource = resource.resource;
|
|
113
|
+
return formatAssetName(requestedResource.displayName, ((_b = resource.accessLevel) === null || _b === void 0 ? void 0 : _b.accessLevelName) || "");
|
|
100
114
|
}
|
|
101
|
-
})) !== null &&
|
|
102
|
-
const requestedGroups = (
|
|
103
|
-
var _a, _b
|
|
115
|
+
})) !== null && _e !== void 0 ? _e : [];
|
|
116
|
+
const requestedGroups = (_g = (_f = request.requestedGroups) === null || _f === void 0 ? void 0 : _f.map((group) => {
|
|
117
|
+
var _a, _b;
|
|
104
118
|
if (((_a = group.group) === null || _a === void 0 ? void 0 : _a.__typename) === "Group") {
|
|
105
|
-
|
|
119
|
+
const requestedGroup = group.group;
|
|
120
|
+
return formatAssetName(requestedGroup.name, ((_b = group.accessLevel) === null || _b === void 0 ? void 0 : _b.accessLevelName) || "");
|
|
106
121
|
}
|
|
107
|
-
})) !== null &&
|
|
122
|
+
})) !== null && _g !== void 0 ? _g : [];
|
|
108
123
|
const requestedItems = [...requestedResources, ...requestedGroups].join(", ");
|
|
109
124
|
if (requestedItems) {
|
|
110
125
|
cmd.log(`${chalk_1.default.bold("Requested Items:")} ${chalk_1.default.cyan(requestedItems)}`);
|
|
@@ -113,8 +128,8 @@ function displayRequestDetails(cmd, requestResp) {
|
|
|
113
128
|
}
|
|
114
129
|
}
|
|
115
130
|
function displayRequestListTable(cmd, requestResp) {
|
|
116
|
-
var _a, _b, _c, _d, _e;
|
|
117
|
-
switch (requestResp.data.requests.__typename) {
|
|
131
|
+
var _a, _b, _c, _d, _e, _f;
|
|
132
|
+
switch ((_a = requestResp.data) === null || _a === void 0 ? void 0 : _a.requests.__typename) {
|
|
118
133
|
case "RequestsResult": {
|
|
119
134
|
const requests = requestResp.data.requests.requests;
|
|
120
135
|
if (requests && requests.length > 0) {
|
|
@@ -131,25 +146,28 @@ function displayRequestListTable(cmd, requestResp) {
|
|
|
131
146
|
wordWrap: true,
|
|
132
147
|
wrapOnWordBoundary: false,
|
|
133
148
|
});
|
|
134
|
-
for (const
|
|
135
|
-
const
|
|
149
|
+
for (const req of requests) {
|
|
150
|
+
const request = req;
|
|
151
|
+
const targetUser = (_b = request.targetUser) === null || _b === void 0 ? void 0 : _b.displayName;
|
|
136
152
|
const reason = request.reason;
|
|
137
153
|
const status = request.status;
|
|
138
154
|
const formattedDuration = request.durationInMinutes
|
|
139
155
|
? formatDuration(request.durationInMinutes)
|
|
140
156
|
: "Permanent";
|
|
141
|
-
const requestedResources = (
|
|
142
|
-
var _a, _b
|
|
157
|
+
const requestedResources = (_d = (_c = request.requestedResources) === null || _c === void 0 ? void 0 : _c.map((resource) => {
|
|
158
|
+
var _a, _b;
|
|
143
159
|
if (((_a = resource.resource) === null || _a === void 0 ? void 0 : _a.__typename) === "Resource") {
|
|
144
|
-
|
|
160
|
+
const requestedResource = resource.resource;
|
|
161
|
+
return formatAssetName(requestedResource.displayName, ((_b = resource.accessLevel) === null || _b === void 0 ? void 0 : _b.accessLevelName) || "");
|
|
145
162
|
}
|
|
146
|
-
})) !== null &&
|
|
147
|
-
const requestedGroups = (
|
|
148
|
-
var _a, _b
|
|
163
|
+
})) !== null && _d !== void 0 ? _d : [];
|
|
164
|
+
const requestedGroups = (_f = (_e = request.requestedGroups) === null || _e === void 0 ? void 0 : _e.map((group) => {
|
|
165
|
+
var _a, _b;
|
|
149
166
|
if (((_a = group.group) === null || _a === void 0 ? void 0 : _a.__typename) === "Group") {
|
|
150
|
-
|
|
167
|
+
const requestedGroup = group.group;
|
|
168
|
+
return formatAssetName(requestedGroup.name, ((_b = group.accessLevel) === null || _b === void 0 ? void 0 : _b.accessLevelName) || "");
|
|
151
169
|
}
|
|
152
|
-
})) !== null &&
|
|
170
|
+
})) !== null && _f !== void 0 ? _f : [];
|
|
153
171
|
const requestedItems = [
|
|
154
172
|
...requestedResources,
|
|
155
173
|
...requestedGroups,
|
|
@@ -199,3 +217,7 @@ function formatAssetName(assetName, roleName) {
|
|
|
199
217
|
}
|
|
200
218
|
return str;
|
|
201
219
|
}
|
|
220
|
+
function displayRequestAgain(cmd, id) {
|
|
221
|
+
cmd.log(chalk_1.default.bold("\nTo request this again, run:"));
|
|
222
|
+
cmd.log(chalk_1.default.italic(` opal request create --template ${id}\n`));
|
|
223
|
+
}
|