@pnp/cli-microsoft365 7.7.0-beta.72886a7 → 7.7.0-beta.a12fb3e
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/.eslintrc.cjs +1 -0
- package/allCommands.json +1 -1
- package/allCommandsFull.json +1 -1
- package/dist/m365/entra/commands/app/app-add.js +7 -1
- package/dist/m365/entra/commands/app/app-set.js +32 -3
- package/dist/m365/entra/commands/pim/pim-role-assignment-add.js +233 -0
- package/dist/m365/entra/commands/pim/pim-role-assignment-list.js +122 -0
- package/dist/m365/entra/commands.js +2 -0
- package/dist/m365/spo/commands/contenttype/contenttype-sync.js +139 -0
- package/dist/m365/spo/commands.js +1 -0
- package/dist/utils/validation.js +4 -0
- package/docs/docs/cmd/entra/app/app-add.mdx +9 -0
- package/docs/docs/cmd/entra/app/app-set.mdx +9 -0
- package/docs/docs/cmd/entra/pim/pim-role-assignment-add.mdx +230 -0
- package/docs/docs/cmd/entra/pim/pim-role-assignment-list.mdx +224 -0
- package/docs/docs/cmd/spo/contenttype/contenttype-sync.mdx +144 -0
- package/package.json +1 -1
|
@@ -98,6 +98,9 @@ class EntraAppAddCommand extends GraphCommand {
|
|
|
98
98
|
};
|
|
99
99
|
applicationInfo.keyCredentials = [newKeyCredential];
|
|
100
100
|
}
|
|
101
|
+
if (args.options.allowPublicClientFlows) {
|
|
102
|
+
applicationInfo.isFallbackPublicClient = true;
|
|
103
|
+
}
|
|
101
104
|
if (this.verbose) {
|
|
102
105
|
await logger.logToStderr(`Creating Microsoft Entra app registration...`);
|
|
103
106
|
}
|
|
@@ -657,7 +660,8 @@ _a = EntraAppAddCommand, _EntraAppAddCommand_instances = new WeakSet(), _EntraAp
|
|
|
657
660
|
certificateFile: typeof args.options.certificateFile !== 'undefined',
|
|
658
661
|
certificateBase64Encoded: typeof args.options.certificateBase64Encoded !== 'undefined',
|
|
659
662
|
certificateDisplayName: typeof args.options.certificateDisplayName !== 'undefined',
|
|
660
|
-
grantAdminConsent: typeof args.options.grantAdminConsent !== 'undefined'
|
|
663
|
+
grantAdminConsent: typeof args.options.grantAdminConsent !== 'undefined',
|
|
664
|
+
allowPublicClientFlows: typeof args.options.allowPublicClientFlows !== 'undefined'
|
|
661
665
|
});
|
|
662
666
|
});
|
|
663
667
|
}, _EntraAppAddCommand_initOptions = function _EntraAppAddCommand_initOptions() {
|
|
@@ -701,6 +705,8 @@ _a = EntraAppAddCommand, _EntraAppAddCommand_instances = new WeakSet(), _EntraAp
|
|
|
701
705
|
option: '--save'
|
|
702
706
|
}, {
|
|
703
707
|
option: '--grantAdminConsent'
|
|
708
|
+
}, {
|
|
709
|
+
option: '--allowPublicClientFlows'
|
|
704
710
|
});
|
|
705
711
|
}, _EntraAppAddCommand_initValidators = function _EntraAppAddCommand_initValidators() {
|
|
706
712
|
this.validators.push(async (args) => {
|
|
@@ -3,7 +3,7 @@ var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (
|
|
|
3
3
|
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
4
4
|
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
5
5
|
};
|
|
6
|
-
var _EntraAppSetCommand_instances, _a, _EntraAppSetCommand_initTelemetry, _EntraAppSetCommand_initOptions, _EntraAppSetCommand_initValidators, _EntraAppSetCommand_initOptionSets;
|
|
6
|
+
var _EntraAppSetCommand_instances, _a, _EntraAppSetCommand_initTelemetry, _EntraAppSetCommand_initOptions, _EntraAppSetCommand_initValidators, _EntraAppSetCommand_initOptionSets, _EntraAppSetCommand_initTypes;
|
|
7
7
|
import fs from 'fs';
|
|
8
8
|
import request from '../../../../request.js';
|
|
9
9
|
import { formatting } from '../../../../utils/formatting.js';
|
|
@@ -28,6 +28,7 @@ class EntraAppSetCommand extends GraphCommand {
|
|
|
28
28
|
__classPrivateFieldGet(this, _EntraAppSetCommand_instances, "m", _EntraAppSetCommand_initOptions).call(this);
|
|
29
29
|
__classPrivateFieldGet(this, _EntraAppSetCommand_instances, "m", _EntraAppSetCommand_initValidators).call(this);
|
|
30
30
|
__classPrivateFieldGet(this, _EntraAppSetCommand_instances, "m", _EntraAppSetCommand_initOptionSets).call(this);
|
|
31
|
+
__classPrivateFieldGet(this, _EntraAppSetCommand_instances, "m", _EntraAppSetCommand_initTypes).call(this);
|
|
31
32
|
}
|
|
32
33
|
async commandAction(logger, args) {
|
|
33
34
|
await this.showDeprecationWarning(logger, aadCommands.APP_SET, commands.APP_SET);
|
|
@@ -35,6 +36,7 @@ class EntraAppSetCommand extends GraphCommand {
|
|
|
35
36
|
let objectId = await this.getAppObjectId(args, logger);
|
|
36
37
|
objectId = await this.configureUri(args, objectId, logger);
|
|
37
38
|
objectId = await this.configureRedirectUris(args, objectId, logger);
|
|
39
|
+
objectId = await this.updateAllowPublicClientFlows(args, objectId, logger);
|
|
38
40
|
await this.configureCertificate(args, objectId, logger);
|
|
39
41
|
}
|
|
40
42
|
catch (err) {
|
|
@@ -71,6 +73,27 @@ class EntraAppSetCommand extends GraphCommand {
|
|
|
71
73
|
const result = await cli.handleMultipleResultsFound(`Multiple Microsoft Entra application registration with name '${name}' found.`, resultAsKeyValuePair);
|
|
72
74
|
return result.id;
|
|
73
75
|
}
|
|
76
|
+
async updateAllowPublicClientFlows(args, objectId, logger) {
|
|
77
|
+
if (args.options.allowPublicClientFlows === undefined) {
|
|
78
|
+
return objectId;
|
|
79
|
+
}
|
|
80
|
+
if (this.verbose) {
|
|
81
|
+
await logger.logToStderr(`Configuring Entra application AllowPublicClientFlows option...`);
|
|
82
|
+
}
|
|
83
|
+
const applicationInfo = {
|
|
84
|
+
isFallbackPublicClient: args.options.allowPublicClientFlows
|
|
85
|
+
};
|
|
86
|
+
const requestOptions = {
|
|
87
|
+
url: `${this.resource}/v1.0/myorganization/applications/${objectId}`,
|
|
88
|
+
headers: {
|
|
89
|
+
'content-type': 'application/json;odata.metadata=none'
|
|
90
|
+
},
|
|
91
|
+
responseType: 'json',
|
|
92
|
+
data: applicationInfo
|
|
93
|
+
};
|
|
94
|
+
await request.patch(requestOptions);
|
|
95
|
+
return objectId;
|
|
96
|
+
}
|
|
74
97
|
async configureUri(args, objectId, logger) {
|
|
75
98
|
if (!args.options.uris) {
|
|
76
99
|
return objectId;
|
|
@@ -249,14 +272,18 @@ _a = EntraAppSetCommand, _EntraAppSetCommand_instances = new WeakSet(), _EntraAp
|
|
|
249
272
|
uris: typeof args.options.uris !== 'undefined',
|
|
250
273
|
certificateFile: typeof args.options.certificateFile !== 'undefined',
|
|
251
274
|
certificateBase64Encoded: typeof args.options.certificateBase64Encoded !== 'undefined',
|
|
252
|
-
certificateDisplayName: typeof args.options.certificateDisplayName !== 'undefined'
|
|
275
|
+
certificateDisplayName: typeof args.options.certificateDisplayName !== 'undefined',
|
|
276
|
+
allowPublicClientFlows: typeof args.options.allowPublicClientFlows !== 'undefined'
|
|
253
277
|
});
|
|
254
278
|
});
|
|
255
279
|
}, _EntraAppSetCommand_initOptions = function _EntraAppSetCommand_initOptions() {
|
|
256
280
|
this.options.unshift({ option: '--appId [appId]' }, { option: '--objectId [objectId]' }, { option: '-n, --name [name]' }, { option: '-u, --uris [uris]' }, { option: '-r, --redirectUris [redirectUris]' }, { option: '--certificateFile [certificateFile]' }, { option: '--certificateBase64Encoded [certificateBase64Encoded]' }, { option: '--certificateDisplayName [certificateDisplayName]' }, {
|
|
257
281
|
option: '--platform [platform]',
|
|
258
282
|
autocomplete: _a.aadApplicationPlatform
|
|
259
|
-
}, { option: '--redirectUrisToRemove [redirectUrisToRemove]' }
|
|
283
|
+
}, { option: '--redirectUrisToRemove [redirectUrisToRemove]' }, {
|
|
284
|
+
option: '--allowPublicClientFlows [allowPublicClientFlows]',
|
|
285
|
+
autocomplete: ['true', 'false']
|
|
286
|
+
});
|
|
260
287
|
}, _EntraAppSetCommand_initValidators = function _EntraAppSetCommand_initValidators() {
|
|
261
288
|
this.validators.push(async (args) => {
|
|
262
289
|
if (args.options.certificateFile && args.options.certificateBase64Encoded) {
|
|
@@ -279,6 +306,8 @@ _a = EntraAppSetCommand, _EntraAppSetCommand_instances = new WeakSet(), _EntraAp
|
|
|
279
306
|
});
|
|
280
307
|
}, _EntraAppSetCommand_initOptionSets = function _EntraAppSetCommand_initOptionSets() {
|
|
281
308
|
this.optionSets.push({ options: ['appId', 'objectId', 'name'] });
|
|
309
|
+
}, _EntraAppSetCommand_initTypes = function _EntraAppSetCommand_initTypes() {
|
|
310
|
+
this.types.boolean.push('allowPublicClientFlows');
|
|
282
311
|
};
|
|
283
312
|
EntraAppSetCommand.aadApplicationPlatform = ['spa', 'web', 'publicClient'];
|
|
284
313
|
export default new EntraAppSetCommand();
|
|
@@ -0,0 +1,233 @@
|
|
|
1
|
+
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
|
2
|
+
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
|
3
|
+
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
4
|
+
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
5
|
+
};
|
|
6
|
+
var _EntraPimRoleAssignmentAddCommand_instances, _EntraPimRoleAssignmentAddCommand_initTelemetry, _EntraPimRoleAssignmentAddCommand_initOptions, _EntraPimRoleAssignmentAddCommand_initValidators, _EntraPimRoleAssignmentAddCommand_initOptionSets;
|
|
7
|
+
import request from '../../../../request.js';
|
|
8
|
+
import GraphCommand from '../../../base/GraphCommand.js';
|
|
9
|
+
import commands from '../../commands.js';
|
|
10
|
+
import { roleDefinition } from '../../../../utils/roleDefinition.js';
|
|
11
|
+
import { validation } from '../../../../utils/validation.js';
|
|
12
|
+
import { entraUser } from '../../../../utils/entraUser.js';
|
|
13
|
+
import { entraGroup } from '../../../../utils/entraGroup.js';
|
|
14
|
+
import { accessToken } from '../../../../utils/accessToken.js';
|
|
15
|
+
import auth from '../../../../Auth.js';
|
|
16
|
+
class EntraPimRoleAssignmentAddCommand extends GraphCommand {
|
|
17
|
+
get name() {
|
|
18
|
+
return commands.PIM_ROLE_ASSIGNMENT_ADD;
|
|
19
|
+
}
|
|
20
|
+
get description() {
|
|
21
|
+
return 'Request activation of an Entra role assignment for a user or group';
|
|
22
|
+
}
|
|
23
|
+
constructor() {
|
|
24
|
+
super();
|
|
25
|
+
_EntraPimRoleAssignmentAddCommand_instances.add(this);
|
|
26
|
+
__classPrivateFieldGet(this, _EntraPimRoleAssignmentAddCommand_instances, "m", _EntraPimRoleAssignmentAddCommand_initTelemetry).call(this);
|
|
27
|
+
__classPrivateFieldGet(this, _EntraPimRoleAssignmentAddCommand_instances, "m", _EntraPimRoleAssignmentAddCommand_initOptions).call(this);
|
|
28
|
+
__classPrivateFieldGet(this, _EntraPimRoleAssignmentAddCommand_instances, "m", _EntraPimRoleAssignmentAddCommand_initValidators).call(this);
|
|
29
|
+
__classPrivateFieldGet(this, _EntraPimRoleAssignmentAddCommand_instances, "m", _EntraPimRoleAssignmentAddCommand_initOptionSets).call(this);
|
|
30
|
+
}
|
|
31
|
+
async commandAction(logger, args) {
|
|
32
|
+
const { userId, userName, groupId, groupName, startDateTime, endDateTime, ticketNumber, ticketSystem } = args.options;
|
|
33
|
+
try {
|
|
34
|
+
const token = auth.connection.accessTokens[auth.defaultResource].accessToken;
|
|
35
|
+
const isAppOnlyAccessToken = accessToken.isAppOnlyAccessToken(token);
|
|
36
|
+
if (isAppOnlyAccessToken) {
|
|
37
|
+
throw 'When running with application permissions either userId, userName, groupId or groupName is required';
|
|
38
|
+
}
|
|
39
|
+
const roleDefinitionId = await this.getRoleDefinitionId(args.options, logger);
|
|
40
|
+
const principalId = await this.getPrincipalId(args.options, logger);
|
|
41
|
+
const requestOptions = {
|
|
42
|
+
url: `${this.resource}/v1.0/roleManagement/directory/roleAssignmentScheduleRequests`,
|
|
43
|
+
headers: {
|
|
44
|
+
'accept': 'application/json;odata.metadata=none'
|
|
45
|
+
},
|
|
46
|
+
responseType: 'json',
|
|
47
|
+
data: {
|
|
48
|
+
principalId: principalId,
|
|
49
|
+
roleDefinitionId: roleDefinitionId,
|
|
50
|
+
directoryScopeId: this.getDirectoryScope(args.options),
|
|
51
|
+
action: !userId && !userName && !groupId && !groupName ? 'selfActivate' : 'adminAssign',
|
|
52
|
+
justification: args.options.justification,
|
|
53
|
+
scheduleInfo: {
|
|
54
|
+
startDateTime: startDateTime,
|
|
55
|
+
expiration: {
|
|
56
|
+
duration: this.getDuration(args.options),
|
|
57
|
+
endDateTime: endDateTime,
|
|
58
|
+
type: this.getExpirationType(args.options)
|
|
59
|
+
}
|
|
60
|
+
},
|
|
61
|
+
ticketInfo: {
|
|
62
|
+
ticketNumber: ticketNumber,
|
|
63
|
+
ticketSystem: ticketSystem
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
};
|
|
67
|
+
const response = await request.post(requestOptions);
|
|
68
|
+
await logger.log(response);
|
|
69
|
+
}
|
|
70
|
+
catch (err) {
|
|
71
|
+
this.handleRejectedODataJsonPromise(err);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
async getRoleDefinitionId(options, logger) {
|
|
75
|
+
if (options.roleDefinitionId) {
|
|
76
|
+
return options.roleDefinitionId;
|
|
77
|
+
}
|
|
78
|
+
if (this.verbose) {
|
|
79
|
+
await logger.logToStderr(`Retrieving role definition by its name '${options.roleDefinitionName}'`);
|
|
80
|
+
}
|
|
81
|
+
const role = await roleDefinition.getRoleDefinitionByDisplayName(options.roleDefinitionName);
|
|
82
|
+
return role.id;
|
|
83
|
+
}
|
|
84
|
+
async getPrincipalId(options, logger) {
|
|
85
|
+
if (options.userId || options.groupId) {
|
|
86
|
+
return options.userId || options.groupId;
|
|
87
|
+
}
|
|
88
|
+
if (options.userName) {
|
|
89
|
+
if (this.verbose) {
|
|
90
|
+
await logger.logToStderr(`Retrieving user by its name '${options.userName}'`);
|
|
91
|
+
}
|
|
92
|
+
return await entraUser.getUserIdByUpn(options.userName);
|
|
93
|
+
}
|
|
94
|
+
else if (options.groupName) {
|
|
95
|
+
if (this.verbose) {
|
|
96
|
+
await logger.logToStderr(`Retrieving group by its name '${options.groupName}'`);
|
|
97
|
+
}
|
|
98
|
+
return await entraGroup.getGroupIdByDisplayName(options.groupName);
|
|
99
|
+
}
|
|
100
|
+
if (this.verbose) {
|
|
101
|
+
await logger.logToStderr(`Retrieving id of the current user`);
|
|
102
|
+
}
|
|
103
|
+
const token = auth.connection.accessTokens[auth.defaultResource].accessToken;
|
|
104
|
+
return accessToken.getUserIdFromAccessToken(token);
|
|
105
|
+
}
|
|
106
|
+
getExpirationType(options) {
|
|
107
|
+
if (options.endDateTime) {
|
|
108
|
+
return 'afterDateTime';
|
|
109
|
+
}
|
|
110
|
+
if (options.noExpiration) {
|
|
111
|
+
return 'noExpiration';
|
|
112
|
+
}
|
|
113
|
+
return 'afterDuration';
|
|
114
|
+
}
|
|
115
|
+
getDuration(options) {
|
|
116
|
+
if (!options.duration && !options.endDateTime && !options.noExpiration) {
|
|
117
|
+
return 'PT8H';
|
|
118
|
+
}
|
|
119
|
+
return options.duration;
|
|
120
|
+
}
|
|
121
|
+
getDirectoryScope(options) {
|
|
122
|
+
if (options.administrativeUnitId) {
|
|
123
|
+
return `/administrativeUnits/${options.administrativeUnitId}`;
|
|
124
|
+
}
|
|
125
|
+
if (options.applicationId) {
|
|
126
|
+
return `/${options.applicationId}`;
|
|
127
|
+
}
|
|
128
|
+
return '/';
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
_EntraPimRoleAssignmentAddCommand_instances = new WeakSet(), _EntraPimRoleAssignmentAddCommand_initTelemetry = function _EntraPimRoleAssignmentAddCommand_initTelemetry() {
|
|
132
|
+
this.telemetry.push((args) => {
|
|
133
|
+
Object.assign(this.telemetryProperties, {
|
|
134
|
+
roleDefinitionName: typeof args.options.roleDefinitionName !== 'undefined',
|
|
135
|
+
roleDefinitionId: typeof args.options.roleDefinitionId !== 'undefined',
|
|
136
|
+
userId: typeof args.options.userId !== 'undefined',
|
|
137
|
+
userName: typeof args.options.userName !== 'undefined',
|
|
138
|
+
groupId: typeof args.options.groupId !== 'undefined',
|
|
139
|
+
groupName: typeof args.options.groupName !== 'undefined',
|
|
140
|
+
administrativeUnitId: typeof args.options.administrativeUnitId !== 'undefined',
|
|
141
|
+
applicationId: typeof args.options.applicationId !== 'undefined',
|
|
142
|
+
justification: typeof args.options.justification !== 'undefined',
|
|
143
|
+
startDateTime: typeof args.options.startDateTime !== 'undefined',
|
|
144
|
+
endDateTime: typeof args.options.endDateTime !== 'undefined',
|
|
145
|
+
duration: typeof args.options.duration !== 'undefined',
|
|
146
|
+
ticketNumber: typeof args.options.ticketNumber !== 'undefined',
|
|
147
|
+
ticketSystem: typeof args.options.ticketSystem !== 'undefined',
|
|
148
|
+
noExpiration: !!args.options.noExpiration
|
|
149
|
+
});
|
|
150
|
+
});
|
|
151
|
+
}, _EntraPimRoleAssignmentAddCommand_initOptions = function _EntraPimRoleAssignmentAddCommand_initOptions() {
|
|
152
|
+
this.options.unshift({
|
|
153
|
+
option: '-n, --roleDefinitionName [roleDefinitionName]'
|
|
154
|
+
}, {
|
|
155
|
+
option: '-i, --roleDefinitionId [roleDefinitionId]'
|
|
156
|
+
}, {
|
|
157
|
+
option: "--userId [userId]"
|
|
158
|
+
}, {
|
|
159
|
+
option: "--userName [userName]"
|
|
160
|
+
}, {
|
|
161
|
+
option: "--groupId [groupId]"
|
|
162
|
+
}, {
|
|
163
|
+
option: "--groupName [groupName]"
|
|
164
|
+
}, {
|
|
165
|
+
option: "--administrativeUnitId [administrativeUnitId]"
|
|
166
|
+
}, {
|
|
167
|
+
option: "--applicationId [applicationId]"
|
|
168
|
+
}, {
|
|
169
|
+
option: "-j, --justification [justification]"
|
|
170
|
+
}, {
|
|
171
|
+
option: "-s, --startDateTime [startDateTime]"
|
|
172
|
+
}, {
|
|
173
|
+
option: "-e, --endDateTime [endDateTime]"
|
|
174
|
+
}, {
|
|
175
|
+
option: "-d, --duration [duration]"
|
|
176
|
+
}, {
|
|
177
|
+
option: "--ticketNumber [ticketNumber]"
|
|
178
|
+
}, {
|
|
179
|
+
option: "--ticketSystem [ticketSystem]"
|
|
180
|
+
}, {
|
|
181
|
+
option: "--no-expiration"
|
|
182
|
+
});
|
|
183
|
+
}, _EntraPimRoleAssignmentAddCommand_initValidators = function _EntraPimRoleAssignmentAddCommand_initValidators() {
|
|
184
|
+
this.validators.push(async (args) => {
|
|
185
|
+
if (args.options.roleDefinitionId && !validation.isValidGuid(args.options.roleDefinitionId)) {
|
|
186
|
+
return `${args.options.roleDefinitionId} is not a valid GUID`;
|
|
187
|
+
}
|
|
188
|
+
if (args.options.userId && !validation.isValidGuid(args.options.userId)) {
|
|
189
|
+
return `${args.options.userId} is not a valid GUID`;
|
|
190
|
+
}
|
|
191
|
+
if (args.options.groupId && !validation.isValidGuid(args.options.groupId)) {
|
|
192
|
+
return `${args.options.groupId} is not a valid GUID`;
|
|
193
|
+
}
|
|
194
|
+
if (args.options.startDateTime && !validation.isValidISODateTime(args.options.startDateTime)) {
|
|
195
|
+
return `${args.options.startDateTime} is not a valid ISO 8601 date time string`;
|
|
196
|
+
}
|
|
197
|
+
if (args.options.endDateTime && !validation.isValidISODateTime(args.options.endDateTime)) {
|
|
198
|
+
return `${args.options.endDateTime} is not a valid ISO 8601 date time string`;
|
|
199
|
+
}
|
|
200
|
+
if (args.options.duration && !validation.isValidISODuration(args.options.duration)) {
|
|
201
|
+
return `${args.options.duration} is not a valid ISO 8601 duration`;
|
|
202
|
+
}
|
|
203
|
+
if (args.options.administrativeUnitId && !validation.isValidGuid(args.options.administrativeUnitId)) {
|
|
204
|
+
return `${args.options.administrativeUnitId} is not a valid GUID`;
|
|
205
|
+
}
|
|
206
|
+
if (args.options.applicationId && !validation.isValidGuid(args.options.applicationId)) {
|
|
207
|
+
return `${args.options.applicationId} is not a valid GUID`;
|
|
208
|
+
}
|
|
209
|
+
return true;
|
|
210
|
+
});
|
|
211
|
+
}, _EntraPimRoleAssignmentAddCommand_initOptionSets = function _EntraPimRoleAssignmentAddCommand_initOptionSets() {
|
|
212
|
+
this.optionSets.push({ options: ['roleDefinitionName', 'roleDefinitionId'] });
|
|
213
|
+
this.optionSets.push({
|
|
214
|
+
options: ['noExpiration', 'endDateTime', 'duration'],
|
|
215
|
+
runsWhen: (args) => {
|
|
216
|
+
return !!args.options.noExpiration || args.options.endDateTime !== undefined || args.options.duration !== undefined;
|
|
217
|
+
}
|
|
218
|
+
});
|
|
219
|
+
this.optionSets.push({
|
|
220
|
+
options: ['userId', 'userName', 'groupId', 'groupName'],
|
|
221
|
+
runsWhen: (args) => {
|
|
222
|
+
return args.options.userId !== undefined || args.options.userName !== undefined || args.options.groupId !== undefined || args.options.groupName !== undefined;
|
|
223
|
+
}
|
|
224
|
+
});
|
|
225
|
+
this.optionSets.push({
|
|
226
|
+
options: ['administrativeUnitId', 'applicationId'],
|
|
227
|
+
runsWhen: (args) => {
|
|
228
|
+
return args.options.administrativeUnitId !== undefined || args.options.applicationId !== undefined;
|
|
229
|
+
}
|
|
230
|
+
});
|
|
231
|
+
};
|
|
232
|
+
export default new EntraPimRoleAssignmentAddCommand();
|
|
233
|
+
//# sourceMappingURL=pim-role-assignment-add.js.map
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
|
2
|
+
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
|
3
|
+
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
4
|
+
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
5
|
+
};
|
|
6
|
+
var _EntraPimRoleAssignmentListCommand_instances, _EntraPimRoleAssignmentListCommand_initTelemetry, _EntraPimRoleAssignmentListCommand_initOptions, _EntraPimRoleAssignmentListCommand_initValidators, _EntraPimRoleAssignmentListCommand_initOptionSets;
|
|
7
|
+
import GraphCommand from '../../../base/GraphCommand.js';
|
|
8
|
+
import commands from '../../commands.js';
|
|
9
|
+
import { validation } from '../../../../utils/validation.js';
|
|
10
|
+
import { entraUser } from '../../../../utils/entraUser.js';
|
|
11
|
+
import { entraGroup } from '../../../../utils/entraGroup.js';
|
|
12
|
+
import { odata } from '../../../../utils/odata.js';
|
|
13
|
+
class EntraPimRoleAssignmentListCommand extends GraphCommand {
|
|
14
|
+
get name() {
|
|
15
|
+
return commands.PIM_ROLE_ASSIGNMENT_LIST;
|
|
16
|
+
}
|
|
17
|
+
get description() {
|
|
18
|
+
return 'Retrieves a list of Entra role assignments for a user or group';
|
|
19
|
+
}
|
|
20
|
+
constructor() {
|
|
21
|
+
super();
|
|
22
|
+
_EntraPimRoleAssignmentListCommand_instances.add(this);
|
|
23
|
+
__classPrivateFieldGet(this, _EntraPimRoleAssignmentListCommand_instances, "m", _EntraPimRoleAssignmentListCommand_initTelemetry).call(this);
|
|
24
|
+
__classPrivateFieldGet(this, _EntraPimRoleAssignmentListCommand_instances, "m", _EntraPimRoleAssignmentListCommand_initOptions).call(this);
|
|
25
|
+
__classPrivateFieldGet(this, _EntraPimRoleAssignmentListCommand_instances, "m", _EntraPimRoleAssignmentListCommand_initValidators).call(this);
|
|
26
|
+
__classPrivateFieldGet(this, _EntraPimRoleAssignmentListCommand_instances, "m", _EntraPimRoleAssignmentListCommand_initOptionSets).call(this);
|
|
27
|
+
}
|
|
28
|
+
async commandAction(logger, args) {
|
|
29
|
+
const queryParameters = [];
|
|
30
|
+
const filters = [];
|
|
31
|
+
const expands = [];
|
|
32
|
+
try {
|
|
33
|
+
const principalId = await this.getPrincipalId(logger, args.options);
|
|
34
|
+
if (principalId) {
|
|
35
|
+
filters.push(`principalId eq '${principalId}'`);
|
|
36
|
+
}
|
|
37
|
+
if (args.options.startDateTime) {
|
|
38
|
+
filters.push(`startDateTime ge ${args.options.startDateTime}`);
|
|
39
|
+
}
|
|
40
|
+
if (filters.length > 0) {
|
|
41
|
+
queryParameters.push(`$filter=${filters.join(' and ')}`);
|
|
42
|
+
}
|
|
43
|
+
expands.push('roleDefinition($select=displayName)');
|
|
44
|
+
if (args.options.includePrincipalDetails) {
|
|
45
|
+
expands.push('principal');
|
|
46
|
+
}
|
|
47
|
+
queryParameters.push(`$expand=${expands.join(',')}`);
|
|
48
|
+
const queryString = `?${queryParameters.join('&')}`;
|
|
49
|
+
const url = `${this.resource}/v1.0/roleManagement/directory/roleAssignmentScheduleInstances${queryString}`;
|
|
50
|
+
const results = await odata.getAllItems(url);
|
|
51
|
+
await logger.log(results);
|
|
52
|
+
}
|
|
53
|
+
catch (err) {
|
|
54
|
+
this.handleRejectedODataJsonPromise(err);
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
async getPrincipalId(logger, options) {
|
|
58
|
+
let principalId = options.userId;
|
|
59
|
+
if (options.userName) {
|
|
60
|
+
if (this.verbose) {
|
|
61
|
+
await logger.logToStderr(`Retrieving user by its name '${options.userName}'`);
|
|
62
|
+
}
|
|
63
|
+
principalId = await entraUser.getUserIdByUpn(options.userName);
|
|
64
|
+
}
|
|
65
|
+
else if (options.groupId) {
|
|
66
|
+
principalId = options.groupId;
|
|
67
|
+
}
|
|
68
|
+
else if (options.groupName) {
|
|
69
|
+
if (this.verbose) {
|
|
70
|
+
await logger.logToStderr(`Retrieving group by its name '${options.groupName}'`);
|
|
71
|
+
}
|
|
72
|
+
principalId = await entraGroup.getGroupIdByDisplayName(options.groupName);
|
|
73
|
+
}
|
|
74
|
+
return principalId;
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
_EntraPimRoleAssignmentListCommand_instances = new WeakSet(), _EntraPimRoleAssignmentListCommand_initTelemetry = function _EntraPimRoleAssignmentListCommand_initTelemetry() {
|
|
78
|
+
this.telemetry.push((args) => {
|
|
79
|
+
Object.assign(this.telemetryProperties, {
|
|
80
|
+
userId: typeof args.options.userId !== 'undefined',
|
|
81
|
+
userName: typeof args.options.userName !== 'undefined',
|
|
82
|
+
groupId: typeof args.options.groupId !== 'undefined',
|
|
83
|
+
groupName: typeof args.options.groupName !== 'undefined',
|
|
84
|
+
startDateTime: typeof args.options.startDateTime !== 'undefined',
|
|
85
|
+
includePrincipalDetails: !!args.options.includePrincipalDetails
|
|
86
|
+
});
|
|
87
|
+
});
|
|
88
|
+
}, _EntraPimRoleAssignmentListCommand_initOptions = function _EntraPimRoleAssignmentListCommand_initOptions() {
|
|
89
|
+
this.options.unshift({
|
|
90
|
+
option: "--userId [userId]"
|
|
91
|
+
}, {
|
|
92
|
+
option: "--userName [userName]"
|
|
93
|
+
}, {
|
|
94
|
+
option: "--groupId [groupId]"
|
|
95
|
+
}, {
|
|
96
|
+
option: "--groupName [groupName]"
|
|
97
|
+
}, {
|
|
98
|
+
option: "-s, --startDateTime [startDateTime]"
|
|
99
|
+
}, {
|
|
100
|
+
option: "--includePrincipalDetails [includePrincipalDetails]"
|
|
101
|
+
});
|
|
102
|
+
}, _EntraPimRoleAssignmentListCommand_initValidators = function _EntraPimRoleAssignmentListCommand_initValidators() {
|
|
103
|
+
this.validators.push(async (args) => {
|
|
104
|
+
if (args.options.userId && !validation.isValidGuid(args.options.userId)) {
|
|
105
|
+
return `${args.options.userId} is not a valid GUID`;
|
|
106
|
+
}
|
|
107
|
+
if (args.options.groupId && !validation.isValidGuid(args.options.groupId)) {
|
|
108
|
+
return `${args.options.groupId} is not a valid GUID`;
|
|
109
|
+
}
|
|
110
|
+
if (args.options.startDateTime && !validation.isValidISODateTime(args.options.startDateTime)) {
|
|
111
|
+
return `${args.options.startDateTime} is not a valid ISO 8601 date time string`;
|
|
112
|
+
}
|
|
113
|
+
return true;
|
|
114
|
+
});
|
|
115
|
+
}, _EntraPimRoleAssignmentListCommand_initOptionSets = function _EntraPimRoleAssignmentListCommand_initOptionSets() {
|
|
116
|
+
this.optionSets.push({
|
|
117
|
+
options: ['userId', 'userName', 'groupId', 'groupName'],
|
|
118
|
+
runsWhen: (args) => args.options.userId || args.options.userName || args.options.groupId || args.options.groupName
|
|
119
|
+
});
|
|
120
|
+
};
|
|
121
|
+
export default new EntraPimRoleAssignmentListCommand();
|
|
122
|
+
//# sourceMappingURL=pim-role-assignment-list.js.map
|
|
@@ -74,6 +74,8 @@ export default {
|
|
|
74
74
|
OAUTH2GRANT_LIST: `${prefix} oauth2grant list`,
|
|
75
75
|
OAUTH2GRANT_REMOVE: `${prefix} oauth2grant remove`,
|
|
76
76
|
OAUTH2GRANT_SET: `${prefix} oauth2grant set`,
|
|
77
|
+
PIM_ROLE_ASSIGNMENT_ADD: `${prefix} pim role assignment add`,
|
|
78
|
+
PIM_ROLE_ASSIGNMENT_LIST: `${prefix} pim role assignment list`,
|
|
77
79
|
POLICY_LIST: `${prefix} policy list`,
|
|
78
80
|
SITECLASSIFICATION_DISABLE: `${prefix} siteclassification disable`,
|
|
79
81
|
SITECLASSIFICATION_ENABLE: `${prefix} siteclassification enable`,
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
|
|
2
|
+
if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
|
|
3
|
+
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
|
4
|
+
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
|
5
|
+
};
|
|
6
|
+
var _SpoContentTypeSyncCommand_instances, _SpoContentTypeSyncCommand_initTelemetry, _SpoContentTypeSyncCommand_initOptions, _SpoContentTypeSyncCommand_initValidators, _SpoContentTypeSyncCommand_initTypes, _SpoContentTypeSyncCommand_initOptionSets;
|
|
7
|
+
import { formatting } from '../../../../utils/formatting.js';
|
|
8
|
+
import request from '../../../../request.js';
|
|
9
|
+
import { validation } from '../../../../utils/validation.js';
|
|
10
|
+
import SpoCommand from '../../../base/SpoCommand.js';
|
|
11
|
+
import commands from '../../commands.js';
|
|
12
|
+
import { urlUtil } from '../../../../utils/urlUtil.js';
|
|
13
|
+
import { odata } from '../../../../utils/odata.js';
|
|
14
|
+
import { spo } from '../../../../utils/spo.js';
|
|
15
|
+
class SpoContentTypeSyncCommand extends SpoCommand {
|
|
16
|
+
get name() {
|
|
17
|
+
return commands.CONTENTTYPE_SYNC;
|
|
18
|
+
}
|
|
19
|
+
get description() {
|
|
20
|
+
return 'Adds a published content type from the content type hub to a site or syncs its latest changes';
|
|
21
|
+
}
|
|
22
|
+
constructor() {
|
|
23
|
+
super();
|
|
24
|
+
_SpoContentTypeSyncCommand_instances.add(this);
|
|
25
|
+
__classPrivateFieldGet(this, _SpoContentTypeSyncCommand_instances, "m", _SpoContentTypeSyncCommand_initTelemetry).call(this);
|
|
26
|
+
__classPrivateFieldGet(this, _SpoContentTypeSyncCommand_instances, "m", _SpoContentTypeSyncCommand_initOptions).call(this);
|
|
27
|
+
__classPrivateFieldGet(this, _SpoContentTypeSyncCommand_instances, "m", _SpoContentTypeSyncCommand_initValidators).call(this);
|
|
28
|
+
__classPrivateFieldGet(this, _SpoContentTypeSyncCommand_instances, "m", _SpoContentTypeSyncCommand_initTypes).call(this);
|
|
29
|
+
__classPrivateFieldGet(this, _SpoContentTypeSyncCommand_instances, "m", _SpoContentTypeSyncCommand_initOptionSets).call(this);
|
|
30
|
+
}
|
|
31
|
+
async commandAction(logger, args) {
|
|
32
|
+
const { listId, listTitle, listUrl, webUrl } = args.options;
|
|
33
|
+
const url = new URL(webUrl);
|
|
34
|
+
const baseUrl = 'https://graph.microsoft.com/v1.0/sites/';
|
|
35
|
+
try {
|
|
36
|
+
const siteUrl = url.pathname === '/' ? url.host : await spo.getSiteId(webUrl, logger, this.verbose);
|
|
37
|
+
const listPath = listId || listTitle || listUrl ? `/lists/${listId || listTitle || await this.getListIdByUrl(webUrl, listUrl, logger)}` : '';
|
|
38
|
+
const contentTypeId = await this.getContentTypeId(baseUrl, url, args.options, logger);
|
|
39
|
+
if (this.verbose) {
|
|
40
|
+
await logger.logToStderr(`Adding or syncing the content type...`);
|
|
41
|
+
}
|
|
42
|
+
const requestOptions = {
|
|
43
|
+
url: `${baseUrl}${siteUrl}${listPath}/contenttypes/addCopyFromContentTypeHub`,
|
|
44
|
+
headers: {
|
|
45
|
+
'accept': 'application/json;odata.metadata=minimal;odata.streaming=true;IEEE754Compatible=false'
|
|
46
|
+
},
|
|
47
|
+
responseType: 'json',
|
|
48
|
+
data: {
|
|
49
|
+
contentTypeId: contentTypeId
|
|
50
|
+
}
|
|
51
|
+
};
|
|
52
|
+
const response = await request.post(requestOptions);
|
|
53
|
+
// The endpoint only returns a response if the content type has been added for the first time
|
|
54
|
+
// When syncing, the response will be an empty string, which should not be logged.
|
|
55
|
+
if (typeof response === 'object') {
|
|
56
|
+
await logger.log(response);
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
catch (err) {
|
|
60
|
+
this.handleRejectedODataJsonPromise(err);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
async getContentTypeId(baseUrl, url, options, logger) {
|
|
64
|
+
if (options.id) {
|
|
65
|
+
return options.id;
|
|
66
|
+
}
|
|
67
|
+
const siteId = await spo.getSiteId(`${url.origin}/sites/contenttypehub`, logger, this.verbose);
|
|
68
|
+
if (this.verbose) {
|
|
69
|
+
await logger.logToStderr(`Retrieving content type Id by name...`);
|
|
70
|
+
}
|
|
71
|
+
const contentTypes = await odata.getAllItems(`${baseUrl}${siteId}/contenttypes?$filter=name eq '${options.name}'&$select=id,name`);
|
|
72
|
+
if (contentTypes.length === 0) {
|
|
73
|
+
throw `Content type with name ${options.name} not found.`;
|
|
74
|
+
}
|
|
75
|
+
return contentTypes[0].id;
|
|
76
|
+
}
|
|
77
|
+
async getListIdByUrl(webUrl, listUrl, logger) {
|
|
78
|
+
if (this.verbose) {
|
|
79
|
+
await logger.logToStderr(`Retrieving list id to sync the content type to...`);
|
|
80
|
+
}
|
|
81
|
+
const listServerRelativeUrl = urlUtil.getServerRelativePath(webUrl, listUrl);
|
|
82
|
+
const requestOptions = {
|
|
83
|
+
url: `${webUrl}/_api/web/GetList('${formatting.encodeQueryParameter(listServerRelativeUrl)}')?$select=id`,
|
|
84
|
+
headers: {
|
|
85
|
+
'accept': 'application/json;odata=nometadata'
|
|
86
|
+
},
|
|
87
|
+
responseType: 'json'
|
|
88
|
+
};
|
|
89
|
+
const response = await request.get(requestOptions);
|
|
90
|
+
return response.Id;
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
_SpoContentTypeSyncCommand_instances = new WeakSet(), _SpoContentTypeSyncCommand_initTelemetry = function _SpoContentTypeSyncCommand_initTelemetry() {
|
|
94
|
+
this.telemetry.push((args) => {
|
|
95
|
+
Object.assign(this.telemetryProperties, {
|
|
96
|
+
id: typeof args.options.id !== 'undefined',
|
|
97
|
+
name: typeof args.options.name !== 'undefined',
|
|
98
|
+
listId: typeof args.options.listId !== 'undefined',
|
|
99
|
+
listTitle: typeof args.options.listTitle !== 'undefined',
|
|
100
|
+
listUrl: typeof args.options.listUrl !== 'undefined'
|
|
101
|
+
});
|
|
102
|
+
});
|
|
103
|
+
}, _SpoContentTypeSyncCommand_initOptions = function _SpoContentTypeSyncCommand_initOptions() {
|
|
104
|
+
this.options.unshift({
|
|
105
|
+
option: '-u, --webUrl <webUrl>'
|
|
106
|
+
}, {
|
|
107
|
+
option: '-i, --id [id]'
|
|
108
|
+
}, {
|
|
109
|
+
option: '-n, --name [name]'
|
|
110
|
+
}, {
|
|
111
|
+
option: '--listTitle [listTitle]'
|
|
112
|
+
}, {
|
|
113
|
+
option: '--listId [listId]'
|
|
114
|
+
}, {
|
|
115
|
+
option: '--listUrl [listUrl]'
|
|
116
|
+
});
|
|
117
|
+
}, _SpoContentTypeSyncCommand_initValidators = function _SpoContentTypeSyncCommand_initValidators() {
|
|
118
|
+
this.validators.push(async (args) => {
|
|
119
|
+
const isValidSharePointUrl = validation.isValidSharePointUrl(args.options.webUrl);
|
|
120
|
+
if (isValidSharePointUrl !== true) {
|
|
121
|
+
return isValidSharePointUrl;
|
|
122
|
+
}
|
|
123
|
+
if (args.options.listId && !validation.isValidGuid(args.options.listId)) {
|
|
124
|
+
return `${args.options.listId} is not a valid GUID`;
|
|
125
|
+
}
|
|
126
|
+
return true;
|
|
127
|
+
});
|
|
128
|
+
}, _SpoContentTypeSyncCommand_initTypes = function _SpoContentTypeSyncCommand_initTypes() {
|
|
129
|
+
this.types.string.push('webUrl', 'id', 'name', 'listTitle', 'listId', 'listUrl');
|
|
130
|
+
}, _SpoContentTypeSyncCommand_initOptionSets = function _SpoContentTypeSyncCommand_initOptionSets() {
|
|
131
|
+
this.optionSets.push({
|
|
132
|
+
options: ['id', 'name']
|
|
133
|
+
}, {
|
|
134
|
+
options: ['listId', 'listTitle', 'listUrl'],
|
|
135
|
+
runsWhen: (args) => args.options.listId || args.options.listTitle || args.options.listUrl
|
|
136
|
+
});
|
|
137
|
+
};
|
|
138
|
+
export default new SpoContentTypeSyncCommand();
|
|
139
|
+
//# sourceMappingURL=contenttype-sync.js.map
|
|
@@ -37,6 +37,7 @@ export default {
|
|
|
37
37
|
CONTENTTYPE_LIST: `${prefix} contenttype list`,
|
|
38
38
|
CONTENTTYPE_REMOVE: `${prefix} contenttype remove`,
|
|
39
39
|
CONTENTTYPE_SET: `${prefix} contenttype set`,
|
|
40
|
+
CONTENTTYPE_SYNC: `${prefix} contenttype sync`,
|
|
40
41
|
CONTENTTYPEHUB_GET: `${prefix} contenttypehub get`,
|
|
41
42
|
CUSTOMACTION_ADD: `${prefix} customaction add`,
|
|
42
43
|
CUSTOMACTION_CLEAR: `${prefix} customaction clear`,
|
package/dist/utils/validation.js
CHANGED
|
@@ -325,6 +325,10 @@ export const validation = {
|
|
|
325
325
|
isValidMailNickname(mailNickname) {
|
|
326
326
|
const mailNicknameRegEx = new RegExp(/^[a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]*$/i);
|
|
327
327
|
return mailNicknameRegEx.test(mailNickname);
|
|
328
|
+
},
|
|
329
|
+
isValidISODuration(duration) {
|
|
330
|
+
const durationRegEx = new RegExp(/^P(?!$)((\d+Y)|(\d+\.\d+Y$))?((\d+M)|(\d+\.\d+M$))?((\d+W)|(\d+\.\d+W$))?((\d+D)|(\d+\.\d+D$))?(T(?=\d)((\d+H)|(\d+\.\d+H$))?((\d+M)|(\d+\.\d+M$))?(\d+(\.\d+)?S)?)??$/);
|
|
331
|
+
return durationRegEx.test(duration);
|
|
328
332
|
}
|
|
329
333
|
};
|
|
330
334
|
//# sourceMappingURL=validation.js.map
|
|
@@ -78,6 +78,9 @@ m365 entra appregistration add [options]
|
|
|
78
78
|
|
|
79
79
|
`--save`
|
|
80
80
|
: Use to store the information about the created app in a local file.
|
|
81
|
+
|
|
82
|
+
`--allowPublicClientFlows`
|
|
83
|
+
: Enable the allow public client flows feature on the app registration.
|
|
81
84
|
```
|
|
82
85
|
|
|
83
86
|
<Global />
|
|
@@ -192,6 +195,12 @@ Create new Entra app registration with a certificate
|
|
|
192
195
|
m365 entra app add --name 'My Entra app' --certificateDisplayName "Some certificate name" --certificateFile "c:\temp\some-certificate.cer"
|
|
193
196
|
```
|
|
194
197
|
|
|
198
|
+
Create a new Entra app registration with the allow public client flows feature enabled.
|
|
199
|
+
|
|
200
|
+
```sh
|
|
201
|
+
m365 entra app add --name 'My Entra app' --allowPublicClientFlows
|
|
202
|
+
```
|
|
203
|
+
|
|
195
204
|
## Response
|
|
196
205
|
|
|
197
206
|
### Standard response
|