Skip to content

Commit 260444b

Browse files
committed
fix: map roles to security_manager for PPL permissions
all_access alone doesn't grant cluster:admin/opensearch/ppl on newer OpenSearch versions. Map to both all_access and security_manager. Signed-off-by: Kyle Hounslow <kylhouns@amazon.com>
1 parent b6b6dad commit 260444b

1 file changed

Lines changed: 27 additions & 24 deletions

File tree

aws/cli-installer/src/aws.mjs

Lines changed: 27 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -290,7 +290,7 @@ export async function mapOsiRoleInDomain(cfg) {
290290
}
291291
}
292292

293-
const url = `${cfg.opensearchEndpoint}/_plugins/_security/api/rolesmapping/all_access`;
293+
const url = `${cfg.opensearchEndpoint}/_plugins/_security/api/rolesmapping`;
294294
const auth = Buffer.from(`${cfg.opensearchUser || 'admin'}:${masterPass}`).toString('base64');
295295

296296
// Map both the OSI pipeline role and the caller's role (for OpenSearch UI access)
@@ -300,35 +300,38 @@ export async function mapOsiRoleInDomain(cfg) {
300300
newRoles.push(callerRoleArn);
301301
}
302302

303+
// Map to both all_access and security_manager for full permissions (including PPL)
304+
const rolesToMap = ['all_access', 'security_manager'];
305+
303306
try {
304307
const headers = { 'Content-Type': 'application/json', 'Authorization': `Basic ${auth}` };
305308

306-
// GET existing mapping and merge to avoid overwriting other stacks' roles
307-
const getResp = await fetch(url, { headers });
308-
let existing = [];
309-
if (getResp.ok) {
310-
const data = await getResp.json();
311-
existing = data?.all_access?.backend_roles || [];
312-
}
313-
const merged = [...new Set([...existing, ...newRoles])];
314-
315-
const resp = await fetch(url, {
316-
method: 'PATCH',
317-
headers,
318-
body: JSON.stringify([
319-
{ op: 'add', path: '/backend_roles', value: merged },
320-
]),
321-
});
309+
for (const role of rolesToMap) {
310+
const roleUrl = `${url}/${role}`;
311+
const getResp = await fetch(roleUrl, { headers });
312+
let existing = [];
313+
if (getResp.ok) {
314+
const data = await getResp.json();
315+
existing = data?.[role]?.backend_roles || [];
316+
}
317+
const merged = [...new Set([...existing, ...newRoles])];
318+
319+
const resp = await fetch(roleUrl, {
320+
method: 'PATCH',
321+
headers,
322+
body: JSON.stringify([
323+
{ op: 'add', path: '/backend_roles', value: merged },
324+
]),
325+
});
322326

323-
if (resp.ok) {
324-
printSuccess(`OSI role mapped to all_access in OpenSearch`);
325-
} else {
326-
const body = await resp.text();
327-
printWarning(`FGAC mapping returned ${resp.status}: ${body}`);
328-
printInfo('You may need to manually map the IAM role in OpenSearch UI → Security → Roles');
327+
if (!resp.ok) {
328+
const body = await resp.text();
329+
printWarning(`FGAC mapping for ${role} returned ${resp.status}: ${body}`);
330+
}
329331
}
332+
printSuccess('Roles mapped to all_access and security_manager in OpenSearch');
330333
} catch (err) {
331-
printWarning(`Could not map OSI role in FGAC: ${err.message}`);
334+
printWarning(`Could not map roles in FGAC: ${err.message}`);
332335
printInfo('You may need to manually map the IAM role in OpenSearch UI → Security → Roles');
333336
}
334337
}

0 commit comments

Comments
 (0)