OCI IAM → STACKIT ACCESS MODEL · ARCHITECTURE
OCI IAM, compartments and policies migration
OCI states access as policy statements over compartments; STACKIT states it as role bindings of a subject on an organization, folder or project. There is no document to convert, so the work is a redesign: compartments become projects or folders, groups and users become subjects, statements become roles, and dynamic groups become service accounts. StackToIT lists every identity resource of your Terraform and leaves each to the architect, which is the right division of labour for this decision.
How the OCI identity objects line up
Each OCI object, the nearest STACKIT concept and what the run recorded for the demo estate. The STACKIT column is design guidance from the STACKIT documentation; the run states a target for none of these objects.
| OCI object | Nearest STACKIT concept | What the run recorded |
|---|---|---|
| Compartment | A project, or a folder that groups projects. Cloud services are provisioned in projects; folders hold no resources. | Resource type not in the catalogue: MANUAL_REVIEW, low, nothing assessed |
| User | A user account stored in the identity provider; a role binding names the user by email address | MANUAL_REVIEW, low |
| Group | A group as the subject of a role binding | MANUAL_REVIEW, low |
| Group membership | The STACKIT IdP page names SCIM provisioning for automated user and group synchronisation; how groups are managed inside STACKIT is not described on the pages used here, so confirm it before you rely on it | Resource type not in the catalogue: MANUAL_REVIEW, low |
| Policy statement | A role binding: subject, role and scope | MANUAL_REVIEW, low; statements named as a setting left to you |
| Dynamic group | A service account assigned to the workload | Resource type not in the catalogue: MANUAL_REVIEW, low |
Counts from the run: 10 units, all MANUAL_REVIEW at low confidence. Six are types the catalogue knows as identity resources; four are not in the catalogue. The reason the run gives for the six is that OCI policies have no document-level counterpart on STACKIT.
A compartment, a policy and a dynamic group, assessed
A ten-resource Oracle Cloud identity estate written for this page and assessed by StackToIT on 4 November 2026. Left: three blocks of the input. Right: the decision recorded for each. assessment.json is written as a single line, so the pane shows selected fields of each unit, indented and nested as in the file, with the values unchanged. The input blocks are shown in separate panes because they are not next to each other in main.tf.
resource "oci_identity_compartment" "prod" {
compartment_id = var.tenancy_ocid
name = "prod"
description = "Production workloads"
}resource "oci_identity_policy" "platform" {
compartment_id = oci_identity_compartment.prod.id
name = "platform-manage-infra"
description = "Platform team manages compute and network in prod"
statements = [
"Allow group platform-team to manage instance-family in compartment prod",
"Allow group platform-team to manage virtual-network-family in compartment prod",
]
}resource "oci_identity_dynamic_group" "app_instances" {
compartment_id = var.tenancy_ocid
name = "app-instances"
description = "Application instances in prod"
matching_rule = "ALL {instance.compartment.id = '${oci_identity_compartment.prod.id}'}"
}[
{
"id": "oci_identity_compartment.prod",
"result": {
"class": "MANUAL_REVIEW",
"confidence": "LOW",
"reason": "oci_identity_compartment is not in the knowledge base catalogue; an architect has to decide the target. Nothing of this resource is assessed or drafted (unknown source type)."
}
},
{
"id": "oci_identity_policy.platform",
"result": {
"class": "MANUAL_REVIEW",
"confidence": "LOW",
"reason": "OCI policies have no document-level counterpart on STACKIT. Map people and workloads to STACKIT roles and service accounts."
}
},
{
"id": "oci_identity_dynamic_group.app_instances",
"result": {
"class": "MANUAL_REVIEW",
"confidence": "LOW",
"reason": "oci_identity_dynamic_group is not in the knowledge base catalogue; an architect has to decide the target. Nothing of this resource is assessed or drafted (unknown source type)."
}
}
]Statements are text to read
The policy carries two statements naming a group and a compartment as strings. The run lists statements, name, description and compartment_id as settings left to you and moves nothing; reading the statements one by one is the translation work.
The compartment is unknown to the run
oci_identity_compartment is in no catalogue of the build used here, so the run assesses nothing for it and says so where it matters: the dynamic group carries a warning that the compartment linked to it is not assessed.
Dynamic groups are rules
The matching rule selects instances by compartment. On STACKIT there is no matching rule: a service account is created in a project and assigned to the workload, so the rule becomes a list of workloads to equip.
The order the run proposes
Units sit in waves from their Terraform references. Note what puts a unit in wave 2: the policy for the platform team depends on the compartment because its compartment_id points at it. The database policy names the same compartment only inside a statement string, so it sits in wave 1.
## Wave 1 — 6 unit(s)
| Unit | Class | Target |
|---|---|---|
| `oci_identity_compartment.dev` | MANUAL_REVIEW / LOW | — |
| `oci_identity_compartment.prod` | MANUAL_REVIEW / LOW | — |
| `oci_identity_group.dba` | MANUAL_REVIEW / LOW | — |
| `oci_identity_group.platform` | MANUAL_REVIEW / LOW | — |
| `oci_identity_policy.dba` | MANUAL_REVIEW / LOW | — |
| `oci_identity_user.alice` | MANUAL_REVIEW / LOW | — |
## Wave 2 — 4 unit(s)
| Unit | Class | Target |
|---|---|---|
| `oci_identity_dynamic_group.app_instances` | MANUAL_REVIEW / LOW | — |
| `oci_identity_policy.app_secrets` | MANUAL_REVIEW / LOW | — |
| `oci_identity_policy.platform` | MANUAL_REVIEW / LOW | — |
| `oci_identity_user_group_membership.alice_platform` | MANUAL_REVIEW / LOW | — |References order, names do not
Group names inside statements are strings, so the run does not tie a policy to its groups. Build the order yourself: structure first, then subjects, then role bindings, then workloads and their service accounts.
Nothing here is a schedule
The waves are an input to your plan. The manual steps are collected in execution/manual/actions.md. The users, groups and policies sit with the Identity Architect; the package that holds the compartments, the dynamic group and the group membership names no owner. Every step carries a rollback line that says the person carrying it out records how to undo it.
Four ways to lay out the STACKIT structure
The scope of a STACKIT role binding is the organization, a folder or a project. A binding on a single resource such as one bucket or one server is not supported, and access is additive: a binding on a child cannot take away what a parent grants.
| Option | How it works | Trade-off |
|---|---|---|
| One project per compartment | Every compartment, including nested ones, becomes a project; the tree is flattened | Closest to what you have. Many projects, many bindings, and networking between projects to plan. Projects that need a Network Area must be created inside it, because the label cannot be changed afterwards. |
| One project per environment | Production and development become two projects; the old compartment names become labels and naming conventions | Few bindings and little to maintain. Isolation inside an environment is lost, because a role applies to the whole project. |
| Folders for areas, projects for environments | One folder per business area, then a project per environment inside it | Roles granted on a folder pass down to its projects, which suits platform teams. STACKIT supports a single level of folders, so deeper trees cannot be mirrored. |
| Separate projects for sensitive data only | A shared project for ordinary workloads and one project per data class that needs its own access list | A small number of boundaries, each with a reason. Needs a clear data classification first. |
No option mirrors a deep compartment tree. If your tenancy nests compartments several levels, flattening is part of the decision, not a loss the migration causes.
How to decide
Work through these questions with the owners of each compartment. The answers pick the option above.
1. Who needs to be separated from whom?
List the groups and the compartments they touch. Two groups that must not see each other's resources need two projects, because a role cannot be narrowed below a project.
2. Which statements are really used?
Go through every statement. A statement over a resource family, for example instance-family or database-family, can be approximated by a broad role such as editor on a project, or by a product role. A statement that depends on a where-condition, for example an MFA check, needs a decision about where that control lives on STACKIT.
3. Where do people come from?
STACKIT user accounts sign in with a password or through federation. The STACKIT IdP documentation has guides for generic OIDC, SAML 2.0, Microsoft Entra ID and Google Workspace, and SCIM provisioning for automated user and group synchronisation. As a practice, federating your existing provider is less work than recreating users one by one.
4. Which workloads act as principals?
Every dynamic group is a list of workloads that call APIs. For each, create a service account in the right project; it has no access until a role is assigned. Workload identity federation with your OIDC issuer gives short-lived tokens without a static key, while a key file is highly sensitive; service account access tokens are deprecated.
5. Which roles do you grant?
Predefined roles are owner, editor and reader, plus product roles such as postgres-flex.admin that are meant mostly for service accounts. Giving a person only a product role can leave parts of the Portal inaccessible.
6. How will you write it down?
Keep the structure in code with the STACKIT Terraform provider. A project is a stackit_resourcemanager_project, and the networkArea label that places it in a Network Area is set at creation and cannot be changed later. Review the code like any other change.
Decisions your architects own
Project boundaries
The number and shape of projects, and the Network Area each one joins. This choice is the hardest to change later.
Role mapping
Which OCI verb levels, from inspect through read and use to manage, map to which STACKIT roles. There is no one-to-one table to apply.
Human identity
Federate an existing provider or create accounts. Decide who owns the lifecycle of joiners and leavers.
Workload identity
Keys or federation for each service account, and where any secret lives.
Break-glass access
Who holds owner on the organization, and how that access is audited. The run does not assess it.
Cutover order
Create structure and bindings before workloads arrive, so the first deploy does not need an exception.
Questions identity teams ask
Can OCI policy statements be converted automatically?
No. The run lists every policy as MANUAL_REVIEW and names the statements as a setting left to you. A statement and a role binding differ in structure, so each statement is read and re-expressed as a subject, a role and a scope.
Can we keep nested compartments as nested folders?
No. STACKIT currently supports a single level of folders. Flatten the tree into folders and projects, and keep the former path in a project name or label.
What replaces instance principals and dynamic groups?
Service accounts. You create one in a project, assign it to the workload and give it roles; with workload identity federation a trusted OIDC issuer gives short-lived tokens without a static key.
Does StackToIT read our tenancy?
No. It reads Terraform and OpenTofu code and connects to nothing. Users and groups created by hand in the console do not appear in it, so export those separately.
Sources
Your next move: STACKIT.
Tell us about your estate. We show you what StackToIT delivers for it: target architecture, Terraform artifacts and a structured migration plan.