[{"data":1,"prerenderedAt":735},["ShallowReactive",2],{"/en-us/blog/automating-role-based-access-control-rbac-at-scale/":3,"navigation-en-us":32,"banner-en-us":460,"footer-en-us":477,"James Wormwell-Paul Meresanu-Kees Valkhof":687,"next-steps-en-us":720},{"_path":4,"_dir":5,"_draft":6,"_partial":6,"_locale":7,"seo":8,"content":11,"config":21,"_id":25,"_type":26,"title":27,"_source":28,"_file":29,"_stem":30,"_extension":31},"/en-us/blog/automating-role-based-access-control-rbac-at-scale","blog",false,"",{"noIndex":6,"title":9,"description":10},"Automating role-based access control (RBAC) at scale","This guide details setting up GitLab + Keycloak + OIDC for RBAC, covering planning, Docker configuration, and automated access governance for DevSecOps.",{"title":9,"description":10,"heroImage":12,"date":13,"body":14,"category":15,"tags":16,"authors":17},"https://res.cloudinary.com/about-gitlab-com/image/upload/v1749659561/Blog/Hero%20Images/securitycheck.png","2025-06-20","Security starts with structure. Building a scalable and secure development\nplatform begins with getting the fundamentals right — especially role-based\naccess control (RBAC).\n\n\nTo help our customers scale effectively, we developed the RBAC Accelerator — a modular, outcome-driven enablement program that supports large organizations in defining, enforcing, and scaling access policies across GitLab.\n\n\nThis foundation enables broader transformation. For example, the Secure SDLC Accelerator, built on top of the RBAC Accelerator, empowers customers to integrate compliance, security, and DevSecOps best practices into their workflows.\n\n\nGitLab customer [Lely](https://www.lelyna.com/us/), a major Dutch manufacturer of agricultural machines and robots, used this approach to migrate to GitLab Dedicated. Lely automated user provisioning via Azure AD using OpenID Connect (OIDC), enforced [least-privilege policies](https://about.gitlab.com/blog/the-ultimate-guide-to-least-privilege-access-with-gitlab/), and created a scalable, reusable access model to support their future development initiatives.\n\n\nIn this guide, we’ll take you through a hands-on implementation example of GitLab + [Keycloak](https://www.keycloak.org/) + OIDC, covering everything from running the setup in a Docker environment to automating role mapping, designing a scalable group hierarchy, and aligning GitLab access controls with organizational structure and compliance goals.\n\n\nThis is a local demo setup intended for proof-of-concept purposes only.\n\n\nWhether you’re just starting out or optimizing at scale, this modular foundation ensures you’re not just securing access — you’re enabling everything that comes next.\n\n\n## Getting started with access control planning\n\n\nBefore implementing any tooling, it’s essential to understand your access landscape. \n\n\nConsider:\n\n- What GitLab resources need protection (projects, groups, environments)?\n\n- Who are your personas (Developers, Maintainers, Guests, etc.)?\n\n- What organizational units (departments, cost centers) should govern access?\n\n- How does your IdP structure (Keycloak) define users and roles?\n\n\nUse this stage to draft your:\n\n- Access control matrix\n\n- GitLab group hierarchy (team- or product-based)\n\n- Least privilege policy assumptions\n\n\nSample group hierarchy \n\n\n```mermaid\n\ngraph TD\n    Root[\"Root (Root Group)\"]\n    FirmwareTeam[\"Firmware-Team\"]\n    FirmwareDevelopers[\"Developers (GitLab Developer Role)\"]\n    FirmwareMaintainers[\"Maintainers (GitLab Maintainer Role)\"]\n    FirmwareReporters[\"Reporters (GitLab Reporter Role)\"]\n    HardwareTeam[\"Hardware-Team\"]\n    HardwareDevelopers[\"Developers\"]\n    SoftwareTeam[\"Software-Team\"]\n    SoftwareDevelopers[\"Developers\"]\n    SoftwareMaintainers[\"Maintainers\"]\n    SoftwareReporters[\"Reporters\"]\n    \n    Enterprise --> FirmwareTeam\n    Enterprise --> HardwareTeam\n    Enterprise --> SoftwareTeam\n    \n    FirmwareTeam --> FirmwareDevelopers\n    FirmwareTeam --> FirmwareMaintainers\n    FirmwareTeam --> FirmwareReporters\n    \n    HardwareTeam --> HardwareDevelopers\n    \n    SoftwareTeam --> SoftwareDevelopers\n    SoftwareTeam --> SoftwareMaintainers\n    SoftwareTeam --> SoftwareReporters\n```\n\n\n## Demo system setup: GitLab + Keycloak in a local Docker environment\n\n### Prerequisites\n\n\n- Docker, Docker Compose, OpenSSL\n\n- GitLab Version 17.7.3 and Keycloak Version 23.0.7 container images\n\n- Self-signed certificates\n\n\n### .env configuration\n\n\nThe demo setup is using the following GitLab and Keycloak versions, ports and secrets.\n\n\n#### GitLab configuration\n\n\n```bash\n\nGITLAB_VERSION=17.7.3-ee.0\n\nGITLAB_EXTERNAL_URL=http://localhost:8081\n\nGITLAB_SSH_PORT=8222\n\n```\n\n\n####  Keycloak configuration\n\n\n```bash\n\nKEYCLOAK_VERSION=latest\n\nKEYCLOAK_ADMIN=\u003Cyour-admin-username>\n\nKEYCLOAK_ADMIN_PASSWORD=\u003Cyour-admin-password>\n\nKEYCLOAK_HTTPS_PORT=8443\n\nKEYCLOAK_CLIENT_SECRET=\u003Cyour-client-secret>  # Get this from Keycloak after setup\n\n```\n\n\n## Generate SSL certificates\n\n\nTo establish trust between GitLab and Keycloak, especially in a self-hosted Docker environment, we’ll need to generate self-signed SSL certificates. These certificates will enable encrypted HTTPS communication and ensure GitLab can securely talk to Keycloak during the OIDC authentication process.\n\n\nFor production environments, we recommend using certificates from a trusted Certificate Authority (CA), but for local testing and development, self-signed certificates are sufficient.\n\n\nFollow these step-by-step instructions:\n\n\n1. Create a folder for the certificates.\n\n\n\n``` mkdir -p certs```\n\n\n2. Generate a self-signed certificate with OpenSSL.\n\n\n```bash\n\nopenssl req -x509 -nodes -days 365 -newkey rsa:2048 \\\n  -keyout certs/tls.key \\\n  -out certs/tls.crt \\\n  -subj \"/CN=keycloak\" \\\n  -addext \"subjectAltName=DNS:keycloak,DNS:localhost\"\n```\n\n\n3. Create a PKCS12 keystore for Keycloak.\n\n\n\n```bash\n\nopenssl pkcs12 -export \\\n  -in certs/tls.crt \\\n  -inkey certs/tls.key \\\n  -out certs/keystore.p12 \\\n  -name keycloak \\\n  -password pass:password\n```\n\n\n## Start the service using Docker compose\n\n\nNow that we have our certificates, we can stand up our local GitLab + Keycloak environment using Docker Compose:\n\n\n\n```yaml\n\nversion: '3.8'\n\nservices:\n  gitlab:\n    image: gitlab/gitlab-ee:${GITLAB_VERSION}\n    container_name: gitlab\n    restart: unless-stopped\n    environment:\n      GITLAB_OMNIBUS_CONFIG: |\n        external_url '${GITLAB_EXTERNAL_URL:-http://localhost:8081}'\n        gitlab_rails['gitlab_shell_ssh_port'] = ${GITLAB_SSH_PORT:-8222}\n        gitlab_rails['display_initial_root_password'] = true\n\n        # OAuth Configuration\n        gitlab_rails['omniauth_enabled'] = true\n        gitlab_rails['omniauth_allow_single_sign_on'] = ['openid_connect']\n        gitlab_rails['omniauth_block_auto_created_users'] = false\n        gitlab_rails['omniauth_providers'] = [\n            {\n                'name' => 'openid_connect',\n                'label' => 'Keycloak',\n                'args' => {\n                    'name' => 'openid_connect',\n                    'scope' => ['openid', 'profile', 'email'],\n                    'response_type' => 'code',\n                    'issuer' => 'https://localhost:8443/realms/GitLab',\n                    'client_auth_method' => 'query',\n                    'discovery' => false,\n                    'uid_field' => 'preferred_username',\n                    'pkce' => true,\n                    'client_options' => {\n                        'identifier' => 'gitlab',\n                        'secret' => '${KEYCLOAK_CLIENT_SECRET}',\n                        'redirect_uri' => '${GITLAB_EXTERNAL_URL:-http://localhost:8081}/users/auth/openid_connect/callback',\n                        'authorization_endpoint' => 'https://localhost:8443/realms/GitLab/protocol/openid-connect/auth',\n                        'token_endpoint' => 'https://keycloak:8443/realms/GitLab/protocol/openid-connect/token',\n                        'userinfo_endpoint' => 'https://keycloak:8443/realms/GitLab/protocol/openid-connect/userinfo',\n                        'jwks_uri' => 'https://keycloak:8443/realms/GitLab/protocol/openid-connect/certs'\n                    }\n                }\n            }\n        ]\n    volumes:\n      - gl-config:/etc/gitlab\n      - gl-data:/var/opt/gitlab\n      - ./certs/tls.crt:/etc/gitlab/trusted-certs/keycloak.crt\n    ports:\n      - '${GITLAB_EXTERNAL_PORT:-8081}:8081'\n      - '${GITLAB_SSH_PORT:-8222}:22'\n    shm_size: '256m'\n\n  keycloak:\n    image: quay.io/keycloak/keycloak:${KEYCLOAK_VERSION}\n    container_name: keycloak-server\n    restart: unless-stopped\n    command: [\n      \"start-dev\",\n      \"--import-realm\",\n      \"--https-port=${KEYCLOAK_HTTPS_PORT}\",\n      \"--https-key-store-file=/etc/x509/https/keystore.p12\",\n      \"--https-key-store-password=password\"\n    ]\n    volumes:\n      - ./data:/opt/keycloak/data/import\n      - ./certs:/etc/x509/https\n    environment:\n      KEYCLOAK_ADMIN: ${KEYCLOAK_ADMIN}\n      KEYCLOAK_ADMIN_PASSWORD: ${KEYCLOAK_ADMIN_PASSWORD}\n    ports:\n      - \"${KEYCLOAK_HTTPS_PORT}:8443\"\n\nvolumes:\n  gl-config:\n  gl-data:\n```\n\n  \nRun the `docker-compose up -d` command and your GitLab + Keycloak environment will be up in minutes.\n\n\n\n```\n\ndocker-compose up -d\n\n```\n\n\n## Keycloak realm configuration\n\n\nYour Keycloak realm is automatically configured on startup as it's defined in the `docker-compose` file.\n\n\nThe realm configuration will include:\n\n\n- Pre-configured GitLab client\n\n- Default client secret\n\n\nYou can access Keycloak admin console at `https://localhost:8443` with:\n\n\n- Username: admin\n\n- Password: from your `.env` file\n\n- To verify the setup:\n  - Log into Keycloak admin console\n  - Select the **GitLab** realm\n  - Check **Clients > gitlab**\n\n\nVerify the client configuration matches your environment.\n\n\nTo showcase the automated RBAC mechanism, you will need to follow these steps:\n\n\n- Map realm roles to GitLab roles\n\n- Create group structure with mapping roles, matching the Group, Sub-group, Project pattern in GitLab.\n\n\nBefore provisioning your first users to the user groups, it’s recommended to log into your GitLab instance to retrieve your instance root password:\n\n\n1. Access GitLab at `http://localhost:8081`.\n\n\n2. Get the root password:\n\n\n``` \n\ndocker exec gitlab grep 'Password:' `/etc/gitlab/initial_root_password`\n\n\n```\n\n\n3. Log in as root with the retrieved password.\n\n\n## Putting it all together\n\n\nTo demonstrate the power of this integrated RBAC model, start by walking through a real-world user journey — from identity to access. \n\n\nBegin in Keycloak by showcasing a user assigned to specific realm roles (e.g., developer, maintainer) and groups (e.g., /engineering/platform). These roles have been mapped to GitLab access levels via OIDC claims, while group affiliations align with GitLab’s structured hierarchy of root groups, sub-groups, and projects. \n\n\nUpon login through GitLab’s SSO Keycloak endpoint, the user is automatically provisioned into the correct group and assigned the appropriate role — with no manual intervention. \n\n\nWithin GitLab, you can see that the  user can interact with the assigned project: For example, a developer might push code and open a merge request, but not merge to protected branches — validating the least-privilege model. \n\n\nFinally, you can showcase access across multiple teams or products that are managed centrally in Keycloak, yet enforced precisely in GitLab through group sync and permissions inheritance. This demo illustrates not just role assignment, but how GitLab and Keycloak together deliver real-time, automated access governance at scale — ready for secure, compliant, enterprise-grade software development.\n\n\n## Why GitLab?\n\n\nGitLab’s comprehensive, intelligent DevSecOps platform is the ideal foundation for secure, scalable access management. With native OIDC support, granular role enforcement, SCIM-based user provisioning, and built-in audit logging, GitLab allows organizations to centralize control without compromising agility. Its flexible group hierarchy mirrors enterprise structure, making it easy to manage access across teams. \n\n\nIntegrating with identity providers like Keycloak automates onboarding, ensures least-privilege access, and creates a seamless identity-to-permission pipeline that supports regulatory and security goals. As a core component of GitLab’s security capabilities, RBAC ties directly into CI/CD, policy enforcement, and vulnerability management workflows.\n\n\n## Summary\n\nRBAC is just the beginning. With GitLab and Keycloak, you’re not just securing access — you’re enabling structured, automated governance that scales. As you expand into policy enforcement, Secure SDLC, and DevSecOps automation, this foundation becomes a launchpad for sustainable, enterprise-grade software delivery.\n\n\n> Get started with RBAC in GitLab today with a free trial of GitLab Ultimate. [Sign up today](https://about.gitlab.com/free-trial/)!","security",[15],[18,19,20],"James Wormwell","Paul Meresanu","Kees Valkhof",{"featured":22,"template":23,"slug":24},true,"BlogPost","automating-role-based-access-control-rbac-at-scale","content:en-us:blog:automating-role-based-access-control-rbac-at-scale.yml","yaml","Automating Role Based Access Control Rbac At Scale","content","en-us/blog/automating-role-based-access-control-rbac-at-scale.yml","en-us/blog/automating-role-based-access-control-rbac-at-scale","yml",{"_path":33,"_dir":34,"_draft":6,"_partial":6,"_locale":7,"data":35,"_id":456,"_type":26,"title":457,"_source":28,"_file":458,"_stem":459,"_extension":31},"/shared/en-us/main-navigation","en-us",{"logo":36,"freeTrial":41,"sales":46,"login":51,"items":56,"search":387,"minimal":418,"duo":437,"pricingDeployment":446},{"config":37},{"href":38,"dataGaName":39,"dataGaLocation":40},"/","gitlab logo","header",{"text":42,"config":43},"Get free trial",{"href":44,"dataGaName":45,"dataGaLocation":40},"https://gitlab.com/-/trial_registrations/new?glm_source=about.gitlab.com&glm_content=default-saas-trial/","free trial",{"text":47,"config":48},"Talk to sales",{"href":49,"dataGaName":50,"dataGaLocation":40},"/sales/","sales",{"text":52,"config":53},"Sign in",{"href":54,"dataGaName":55,"dataGaLocation":40},"https://gitlab.com/users/sign_in/","sign in",[57,101,198,203,308,368],{"text":58,"config":59,"cards":61,"footer":84},"Platform",{"dataNavLevelOne":60},"platform",[62,68,76],{"title":58,"description":63,"link":64},"The most comprehensive AI-powered DevSecOps Platform",{"text":65,"config":66},"Explore our Platform",{"href":67,"dataGaName":60,"dataGaLocation":40},"/platform/",{"title":69,"description":70,"link":71},"GitLab Duo (AI)","Build software faster with AI at every stage of development",{"text":72,"config":73},"Meet GitLab Duo",{"href":74,"dataGaName":75,"dataGaLocation":40},"/gitlab-duo/","gitlab duo ai",{"title":77,"description":78,"link":79},"Why GitLab","10 reasons why Enterprises choose GitLab",{"text":80,"config":81},"Learn more",{"href":82,"dataGaName":83,"dataGaLocation":40},"/why-gitlab/","why gitlab",{"title":85,"items":86},"Get started with",[87,92,97],{"text":88,"config":89},"Platform Engineering",{"href":90,"dataGaName":91,"dataGaLocation":40},"/solutions/platform-engineering/","platform engineering",{"text":93,"config":94},"Developer Experience",{"href":95,"dataGaName":96,"dataGaLocation":40},"/developer-experience/","Developer experience",{"text":98,"config":99},"MLOps",{"href":100,"dataGaName":98,"dataGaLocation":40},"/topics/devops/the-role-of-ai-in-devops/",{"text":102,"left":22,"config":103,"link":105,"lists":109,"footer":180},"Product",{"dataNavLevelOne":104},"solutions",{"text":106,"config":107},"View all Solutions",{"href":108,"dataGaName":104,"dataGaLocation":40},"/solutions/",[110,135,159],{"title":111,"description":112,"link":113,"items":118},"Automation","CI/CD and automation to accelerate deployment",{"config":114},{"icon":115,"href":116,"dataGaName":117,"dataGaLocation":40},"AutomatedCodeAlt","/solutions/delivery-automation/","automated software delivery",[119,123,127,131],{"text":120,"config":121},"CI/CD",{"href":122,"dataGaLocation":40,"dataGaName":120},"/solutions/continuous-integration/",{"text":124,"config":125},"AI-Assisted Development",{"href":74,"dataGaLocation":40,"dataGaName":126},"AI assisted development",{"text":128,"config":129},"Source Code Management",{"href":130,"dataGaLocation":40,"dataGaName":128},"/solutions/source-code-management/",{"text":132,"config":133},"Automated Software Delivery",{"href":116,"dataGaLocation":40,"dataGaName":134},"Automated software delivery",{"title":136,"description":137,"link":138,"items":143},"Security","Deliver code faster without compromising security",{"config":139},{"href":140,"dataGaName":141,"dataGaLocation":40,"icon":142},"/solutions/security-compliance/","security and compliance","ShieldCheckLight",[144,149,154],{"text":145,"config":146},"Application Security Testing",{"href":147,"dataGaName":148,"dataGaLocation":40},"/solutions/application-security-testing/","Application security testing",{"text":150,"config":151},"Software Supply Chain Security",{"href":152,"dataGaLocation":40,"dataGaName":153},"/solutions/supply-chain/","Software supply chain security",{"text":155,"config":156},"Software Compliance",{"href":157,"dataGaName":158,"dataGaLocation":40},"/solutions/software-compliance/","software compliance",{"title":160,"link":161,"items":166},"Measurement",{"config":162},{"icon":163,"href":164,"dataGaName":165,"dataGaLocation":40},"DigitalTransformation","/solutions/visibility-measurement/","visibility and measurement",[167,171,175],{"text":168,"config":169},"Visibility & Measurement",{"href":164,"dataGaLocation":40,"dataGaName":170},"Visibility and Measurement",{"text":172,"config":173},"Value Stream Management",{"href":174,"dataGaLocation":40,"dataGaName":172},"/solutions/value-stream-management/",{"text":176,"config":177},"Analytics & Insights",{"href":178,"dataGaLocation":40,"dataGaName":179},"/solutions/analytics-and-insights/","Analytics and insights",{"title":181,"items":182},"GitLab for",[183,188,193],{"text":184,"config":185},"Enterprise",{"href":186,"dataGaLocation":40,"dataGaName":187},"/enterprise/","enterprise",{"text":189,"config":190},"Small Business",{"href":191,"dataGaLocation":40,"dataGaName":192},"/small-business/","small business",{"text":194,"config":195},"Public Sector",{"href":196,"dataGaLocation":40,"dataGaName":197},"/solutions/public-sector/","public sector",{"text":199,"config":200},"Pricing",{"href":201,"dataGaName":202,"dataGaLocation":40,"dataNavLevelOne":202},"/pricing/","pricing",{"text":204,"config":205,"link":207,"lists":211,"feature":295},"Resources",{"dataNavLevelOne":206},"resources",{"text":208,"config":209},"View all resources",{"href":210,"dataGaName":206,"dataGaLocation":40},"/resources/",[212,245,267],{"title":213,"items":214},"Getting started",[215,220,225,230,235,240],{"text":216,"config":217},"Install",{"href":218,"dataGaName":219,"dataGaLocation":40},"/install/","install",{"text":221,"config":222},"Quick start guides",{"href":223,"dataGaName":224,"dataGaLocation":40},"/get-started/","quick setup checklists",{"text":226,"config":227},"Learn",{"href":228,"dataGaLocation":40,"dataGaName":229},"https://university.gitlab.com/","learn",{"text":231,"config":232},"Product documentation",{"href":233,"dataGaName":234,"dataGaLocation":40},"https://docs.gitlab.com/","product documentation",{"text":236,"config":237},"Best practice videos",{"href":238,"dataGaName":239,"dataGaLocation":40},"/getting-started-videos/","best practice videos",{"text":241,"config":242},"Integrations",{"href":243,"dataGaName":244,"dataGaLocation":40},"/integrations/","integrations",{"title":246,"items":247},"Discover",[248,253,257,262],{"text":249,"config":250},"Customer success stories",{"href":251,"dataGaName":252,"dataGaLocation":40},"/customers/","customer success stories",{"text":254,"config":255},"Blog",{"href":256,"dataGaName":5,"dataGaLocation":40},"/blog/",{"text":258,"config":259},"Remote",{"href":260,"dataGaName":261,"dataGaLocation":40},"https://handbook.gitlab.com/handbook/company/culture/all-remote/","remote",{"text":263,"config":264},"TeamOps",{"href":265,"dataGaName":266,"dataGaLocation":40},"/teamops/","teamops",{"title":268,"items":269},"Connect",[270,275,280,285,290],{"text":271,"config":272},"GitLab Services",{"href":273,"dataGaName":274,"dataGaLocation":40},"/services/","services",{"text":276,"config":277},"Community",{"href":278,"dataGaName":279,"dataGaLocation":40},"/community/","community",{"text":281,"config":282},"Forum",{"href":283,"dataGaName":284,"dataGaLocation":40},"https://forum.gitlab.com/","forum",{"text":286,"config":287},"Events",{"href":288,"dataGaName":289,"dataGaLocation":40},"/events/","events",{"text":291,"config":292},"Partners",{"href":293,"dataGaName":294,"dataGaLocation":40},"/partners/","partners",{"backgroundColor":296,"textColor":297,"text":298,"image":299,"link":303},"#2f2a6b","#fff","Insights for the future of software development",{"altText":300,"config":301},"the source promo card",{"src":302},"https://res.cloudinary.com/about-gitlab-com/image/upload/v1758208064/dzl0dbift9xdizyelkk4.svg",{"text":304,"config":305},"Read the latest",{"href":306,"dataGaName":307,"dataGaLocation":40},"/the-source/","the source",{"text":309,"config":310,"lists":312},"Company",{"dataNavLevelOne":311},"company",[313],{"items":314},[315,320,326,328,333,338,343,348,353,358,363],{"text":316,"config":317},"About",{"href":318,"dataGaName":319,"dataGaLocation":40},"/company/","about",{"text":321,"config":322,"footerGa":325},"Jobs",{"href":323,"dataGaName":324,"dataGaLocation":40},"/jobs/","jobs",{"dataGaName":324},{"text":286,"config":327},{"href":288,"dataGaName":289,"dataGaLocation":40},{"text":329,"config":330},"Leadership",{"href":331,"dataGaName":332,"dataGaLocation":40},"/company/team/e-group/","leadership",{"text":334,"config":335},"Team",{"href":336,"dataGaName":337,"dataGaLocation":40},"/company/team/","team",{"text":339,"config":340},"Handbook",{"href":341,"dataGaName":342,"dataGaLocation":40},"https://handbook.gitlab.com/","handbook",{"text":344,"config":345},"Investor relations",{"href":346,"dataGaName":347,"dataGaLocation":40},"https://ir.gitlab.com/","investor relations",{"text":349,"config":350},"Trust Center",{"href":351,"dataGaName":352,"dataGaLocation":40},"/security/","trust center",{"text":354,"config":355},"AI Transparency Center",{"href":356,"dataGaName":357,"dataGaLocation":40},"/ai-transparency-center/","ai transparency center",{"text":359,"config":360},"Newsletter",{"href":361,"dataGaName":362,"dataGaLocation":40},"/company/contact/","newsletter",{"text":364,"config":365},"Press",{"href":366,"dataGaName":367,"dataGaLocation":40},"/press/","press",{"text":369,"config":370,"lists":371},"Contact us",{"dataNavLevelOne":311},[372],{"items":373},[374,377,382],{"text":47,"config":375},{"href":49,"dataGaName":376,"dataGaLocation":40},"talk to sales",{"text":378,"config":379},"Get help",{"href":380,"dataGaName":381,"dataGaLocation":40},"/support/","get help",{"text":383,"config":384},"Customer portal",{"href":385,"dataGaName":386,"dataGaLocation":40},"https://customers.gitlab.com/customers/sign_in/","customer portal",{"close":388,"login":389,"suggestions":396},"Close",{"text":390,"link":391},"To search repositories and projects, login to",{"text":392,"config":393},"gitlab.com",{"href":54,"dataGaName":394,"dataGaLocation":395},"search login","search",{"text":397,"default":398},"Suggestions",[399,401,405,407,411,415],{"text":69,"config":400},{"href":74,"dataGaName":69,"dataGaLocation":395},{"text":402,"config":403},"Code Suggestions (AI)",{"href":404,"dataGaName":402,"dataGaLocation":395},"/solutions/code-suggestions/",{"text":120,"config":406},{"href":122,"dataGaName":120,"dataGaLocation":395},{"text":408,"config":409},"GitLab on AWS",{"href":410,"dataGaName":408,"dataGaLocation":395},"/partners/technology-partners/aws/",{"text":412,"config":413},"GitLab on Google Cloud",{"href":414,"dataGaName":412,"dataGaLocation":395},"/partners/technology-partners/google-cloud-platform/",{"text":416,"config":417},"Why GitLab?",{"href":82,"dataGaName":416,"dataGaLocation":395},{"freeTrial":419,"mobileIcon":424,"desktopIcon":429,"secondaryButton":432},{"text":420,"config":421},"Start free trial",{"href":422,"dataGaName":45,"dataGaLocation":423},"https://gitlab.com/-/trials/new/","nav",{"altText":425,"config":426},"Gitlab Icon",{"src":427,"dataGaName":428,"dataGaLocation":423},"https://res.cloudinary.com/about-gitlab-com/image/upload/v1758203874/jypbw1jx72aexsoohd7x.svg","gitlab icon",{"altText":425,"config":430},{"src":431,"dataGaName":428,"dataGaLocation":423},"https://res.cloudinary.com/about-gitlab-com/image/upload/v1758203875/gs4c8p8opsgvflgkswz9.svg",{"text":433,"config":434},"Get Started",{"href":435,"dataGaName":436,"dataGaLocation":423},"https://gitlab.com/-/trial_registrations/new?glm_source=about.gitlab.com/compare/gitlab-vs-github/","get started",{"freeTrial":438,"mobileIcon":442,"desktopIcon":444},{"text":439,"config":440},"Learn more about GitLab Duo",{"href":74,"dataGaName":441,"dataGaLocation":423},"gitlab duo",{"altText":425,"config":443},{"src":427,"dataGaName":428,"dataGaLocation":423},{"altText":425,"config":445},{"src":431,"dataGaName":428,"dataGaLocation":423},{"freeTrial":447,"mobileIcon":452,"desktopIcon":454},{"text":448,"config":449},"Back to pricing",{"href":201,"dataGaName":450,"dataGaLocation":423,"icon":451},"back to pricing","GoBack",{"altText":425,"config":453},{"src":427,"dataGaName":428,"dataGaLocation":423},{"altText":425,"config":455},{"src":431,"dataGaName":428,"dataGaLocation":423},"content:shared:en-us:main-navigation.yml","Main Navigation","shared/en-us/main-navigation.yml","shared/en-us/main-navigation",{"_path":461,"_dir":34,"_draft":6,"_partial":6,"_locale":7,"title":462,"button":463,"image":468,"config":472,"_id":474,"_type":26,"_source":28,"_file":475,"_stem":476,"_extension":31},"/shared/en-us/banner","is now in public beta!",{"text":464,"config":465},"Try the Beta",{"href":466,"dataGaName":467,"dataGaLocation":40},"/gitlab-duo/agent-platform/","duo banner",{"altText":469,"config":470},"GitLab Duo Agent Platform",{"src":471},"https://res.cloudinary.com/about-gitlab-com/image/upload/v1753720689/somrf9zaunk0xlt7ne4x.svg",{"layout":473},"release","content:shared:en-us:banner.yml","shared/en-us/banner.yml","shared/en-us/banner",{"_path":478,"_dir":34,"_draft":6,"_partial":6,"_locale":7,"data":479,"_id":683,"_type":26,"title":684,"_source":28,"_file":685,"_stem":686,"_extension":31},"/shared/en-us/main-footer",{"text":480,"source":481,"edit":487,"contribute":492,"config":497,"items":502,"minimal":675},"Git is a trademark of Software Freedom Conservancy and our use of 'GitLab' is under license",{"text":482,"config":483},"View page source",{"href":484,"dataGaName":485,"dataGaLocation":486},"https://gitlab.com/gitlab-com/marketing/digital-experience/about-gitlab-com/","page source","footer",{"text":488,"config":489},"Edit this page",{"href":490,"dataGaName":491,"dataGaLocation":486},"https://gitlab.com/gitlab-com/marketing/digital-experience/about-gitlab-com/-/blob/main/content/","web ide",{"text":493,"config":494},"Please contribute",{"href":495,"dataGaName":496,"dataGaLocation":486},"https://gitlab.com/gitlab-com/marketing/digital-experience/about-gitlab-com/-/blob/main/CONTRIBUTING.md/","please contribute",{"twitter":498,"facebook":499,"youtube":500,"linkedin":501},"https://twitter.com/gitlab","https://www.facebook.com/gitlab","https://www.youtube.com/channel/UCnMGQ8QHMAnVIsI3xJrihhg","https://www.linkedin.com/company/gitlab-com",[503,526,582,611,645],{"title":58,"links":504,"subMenu":509},[505],{"text":506,"config":507},"DevSecOps platform",{"href":67,"dataGaName":508,"dataGaLocation":486},"devsecops platform",[510],{"title":199,"links":511},[512,516,521],{"text":513,"config":514},"View plans",{"href":201,"dataGaName":515,"dataGaLocation":486},"view plans",{"text":517,"config":518},"Why Premium?",{"href":519,"dataGaName":520,"dataGaLocation":486},"/pricing/premium/","why premium",{"text":522,"config":523},"Why Ultimate?",{"href":524,"dataGaName":525,"dataGaLocation":486},"/pricing/ultimate/","why ultimate",{"title":527,"links":528},"Solutions",[529,534,536,538,543,548,552,555,559,564,566,569,572,577],{"text":530,"config":531},"Digital transformation",{"href":532,"dataGaName":533,"dataGaLocation":486},"/topics/digital-transformation/","digital transformation",{"text":145,"config":535},{"href":147,"dataGaName":145,"dataGaLocation":486},{"text":134,"config":537},{"href":116,"dataGaName":117,"dataGaLocation":486},{"text":539,"config":540},"Agile development",{"href":541,"dataGaName":542,"dataGaLocation":486},"/solutions/agile-delivery/","agile delivery",{"text":544,"config":545},"Cloud transformation",{"href":546,"dataGaName":547,"dataGaLocation":486},"/topics/cloud-native/","cloud transformation",{"text":549,"config":550},"SCM",{"href":130,"dataGaName":551,"dataGaLocation":486},"source code management",{"text":120,"config":553},{"href":122,"dataGaName":554,"dataGaLocation":486},"continuous integration & delivery",{"text":556,"config":557},"Value stream management",{"href":174,"dataGaName":558,"dataGaLocation":486},"value stream management",{"text":560,"config":561},"GitOps",{"href":562,"dataGaName":563,"dataGaLocation":486},"/solutions/gitops/","gitops",{"text":184,"config":565},{"href":186,"dataGaName":187,"dataGaLocation":486},{"text":567,"config":568},"Small business",{"href":191,"dataGaName":192,"dataGaLocation":486},{"text":570,"config":571},"Public sector",{"href":196,"dataGaName":197,"dataGaLocation":486},{"text":573,"config":574},"Education",{"href":575,"dataGaName":576,"dataGaLocation":486},"/solutions/education/","education",{"text":578,"config":579},"Financial services",{"href":580,"dataGaName":581,"dataGaLocation":486},"/solutions/finance/","financial services",{"title":204,"links":583},[584,586,588,590,593,595,597,599,601,603,605,607,609],{"text":216,"config":585},{"href":218,"dataGaName":219,"dataGaLocation":486},{"text":221,"config":587},{"href":223,"dataGaName":224,"dataGaLocation":486},{"text":226,"config":589},{"href":228,"dataGaName":229,"dataGaLocation":486},{"text":231,"config":591},{"href":233,"dataGaName":592,"dataGaLocation":486},"docs",{"text":254,"config":594},{"href":256,"dataGaName":5,"dataGaLocation":486},{"text":249,"config":596},{"href":251,"dataGaName":252,"dataGaLocation":486},{"text":258,"config":598},{"href":260,"dataGaName":261,"dataGaLocation":486},{"text":271,"config":600},{"href":273,"dataGaName":274,"dataGaLocation":486},{"text":263,"config":602},{"href":265,"dataGaName":266,"dataGaLocation":486},{"text":276,"config":604},{"href":278,"dataGaName":279,"dataGaLocation":486},{"text":281,"config":606},{"href":283,"dataGaName":284,"dataGaLocation":486},{"text":286,"config":608},{"href":288,"dataGaName":289,"dataGaLocation":486},{"text":291,"config":610},{"href":293,"dataGaName":294,"dataGaLocation":486},{"title":309,"links":612},[613,615,617,619,621,623,625,629,634,636,638,640],{"text":316,"config":614},{"href":318,"dataGaName":311,"dataGaLocation":486},{"text":321,"config":616},{"href":323,"dataGaName":324,"dataGaLocation":486},{"text":329,"config":618},{"href":331,"dataGaName":332,"dataGaLocation":486},{"text":334,"config":620},{"href":336,"dataGaName":337,"dataGaLocation":486},{"text":339,"config":622},{"href":341,"dataGaName":342,"dataGaLocation":486},{"text":344,"config":624},{"href":346,"dataGaName":347,"dataGaLocation":486},{"text":626,"config":627},"Sustainability",{"href":628,"dataGaName":626,"dataGaLocation":486},"/sustainability/",{"text":630,"config":631},"Diversity, inclusion and belonging (DIB)",{"href":632,"dataGaName":633,"dataGaLocation":486},"/diversity-inclusion-belonging/","Diversity, inclusion and belonging",{"text":349,"config":635},{"href":351,"dataGaName":352,"dataGaLocation":486},{"text":359,"config":637},{"href":361,"dataGaName":362,"dataGaLocation":486},{"text":364,"config":639},{"href":366,"dataGaName":367,"dataGaLocation":486},{"text":641,"config":642},"Modern Slavery Transparency Statement",{"href":643,"dataGaName":644,"dataGaLocation":486},"https://handbook.gitlab.com/handbook/legal/modern-slavery-act-transparency-statement/","modern slavery transparency statement",{"title":646,"links":647},"Contact Us",[648,651,653,655,660,665,670],{"text":649,"config":650},"Contact an expert",{"href":49,"dataGaName":50,"dataGaLocation":486},{"text":378,"config":652},{"href":380,"dataGaName":381,"dataGaLocation":486},{"text":383,"config":654},{"href":385,"dataGaName":386,"dataGaLocation":486},{"text":656,"config":657},"Status",{"href":658,"dataGaName":659,"dataGaLocation":486},"https://status.gitlab.com/","status",{"text":661,"config":662},"Terms of use",{"href":663,"dataGaName":664,"dataGaLocation":486},"/terms/","terms of use",{"text":666,"config":667},"Privacy statement",{"href":668,"dataGaName":669,"dataGaLocation":486},"/privacy/","privacy statement",{"text":671,"config":672},"Cookie preferences",{"dataGaName":673,"dataGaLocation":486,"id":674,"isOneTrustButton":22},"cookie preferences","ot-sdk-btn",{"items":676},[677,679,681],{"text":661,"config":678},{"href":663,"dataGaName":664,"dataGaLocation":486},{"text":666,"config":680},{"href":668,"dataGaName":669,"dataGaLocation":486},{"text":671,"config":682},{"dataGaName":673,"dataGaLocation":486,"id":674,"isOneTrustButton":22},"content:shared:en-us:main-footer.yml","Main Footer","shared/en-us/main-footer.yml","shared/en-us/main-footer",[688,700,710],{"_path":689,"_dir":690,"_draft":6,"_partial":6,"_locale":7,"content":691,"config":695,"_id":697,"_type":26,"title":18,"_source":28,"_file":698,"_stem":699,"_extension":31},"/en-us/blog/authors/james-wormwell","authors",{"name":18,"config":692},{"headshot":693,"ctfId":694},"https://res.cloudinary.com/about-gitlab-com/image/upload/v1749659474/Blog/Author%20Headshots/james_wormwell_headshot.png","CPPijHb0Op5C5aVcvsOEf",{"template":696},"BlogAuthor","content:en-us:blog:authors:james-wormwell.yml","en-us/blog/authors/james-wormwell.yml","en-us/blog/authors/james-wormwell",{"_path":701,"_dir":690,"_draft":6,"_partial":6,"_locale":7,"content":702,"config":705,"_id":707,"_type":26,"title":19,"_source":28,"_file":708,"_stem":709,"_extension":31},"/en-us/blog/authors/paul-meresanu",{"name":19,"role":7,"config":703},{"headshot":704},"https://res.cloudinary.com/about-gitlab-com/image/upload/v1750267141/qpw5ayteg0sewyh7s8xi.png",{"template":696,"gitlabHandle":706},"pmeresanu","content:en-us:blog:authors:paul-meresanu.yml","en-us/blog/authors/paul-meresanu.yml","en-us/blog/authors/paul-meresanu",{"_path":711,"_dir":690,"_draft":6,"_partial":6,"_locale":7,"content":712,"config":716,"_id":717,"_type":26,"title":20,"_source":28,"_file":718,"_stem":719,"_extension":31},"/en-us/blog/authors/kees-valkhof",{"name":20,"role":713,"config":714},"Configuration manager at Lely",{"headshot":715},"https://res.cloudinary.com/about-gitlab-com/image/upload/v1750331281/xojwtvpk5pif84wlahx1.jpg",{"template":696},"content:en-us:blog:authors:kees-valkhof.yml","en-us/blog/authors/kees-valkhof.yml","en-us/blog/authors/kees-valkhof",{"_path":721,"_dir":34,"_draft":6,"_partial":6,"_locale":7,"header":722,"eyebrow":723,"blurb":724,"button":725,"secondaryButton":729,"_id":731,"_type":26,"title":732,"_source":28,"_file":733,"_stem":734,"_extension":31},"/shared/en-us/next-steps","Start shipping better software faster","50%+ of the Fortune 100 trust GitLab","See what your team can do with the intelligent\n\n\nDevSecOps platform.\n",{"text":42,"config":726},{"href":727,"dataGaName":45,"dataGaLocation":728},"https://gitlab.com/-/trial_registrations/new?glm_content=default-saas-trial&glm_source=about.gitlab.com/","feature",{"text":47,"config":730},{"href":49,"dataGaName":50,"dataGaLocation":728},"content:shared:en-us:next-steps.yml","Next Steps","shared/en-us/next-steps.yml","shared/en-us/next-steps",1758662305217]