GitLab Access Token: How to Create and Use It (Scopes, Types, and Best Practices)
April 23, 2026
What is a GitLab access token?
A GitLab access token is a credential used to authenticate to the GitLab REST API, Git over HTTPS, and related services. It replaces passwords and provides scoped, time-limited access to repositories, pipelines, and automation workflows.
Unlike simple API keys, GitLab tokens are:
- tied to a user, project, or group
- restricted by scopes and roles
- optionally time-bound and rotatable
Why GitLab access tokens matter
GitLab tokens are the foundation for:
- API integrations
- CI/CD automation
- repository access
- multi-tenant SaaS connections
They determine:
- what your application can do
- which data it can access
- how risky a leak would be
In production systems, most 'API issues' are actually token configuration or lifecycle issues.
How to create a GitLab access token
Quick steps
- Log in to GitLab
- Go to Profile → Access Tokens
- Enter:
- Name
- Expiration date
- Scopes
- Click Create token
- Copy and store it securely
You will not be able to view the token again after creation.
Example: using a GitLab access token
API request (recommended)
curl --header "Authorization: Bearer $GITLAB_TOKEN" \
"https://gitlab.com/api/v4/projects"
Alternative header (legacy)
curl --header "PRIVATE-TOKEN: $GITLAB_TOKEN" \
"https://gitlab.com/api/v4/projects"
Git over HTTPS
git clone https://gitlab.com/my-group/my-project.git
- Username: anything
- Password: your token
Types of GitLab access tokens
Personal access token (PAT)
- tied to a user
- inherits user permissions
- works across all accessible projects
Project access token
- scoped to a single project
- acts as a bot user
- safer for automation
Group access token
- scoped to a group
- works across multiple projects
- centrally managed
Token types compared
| Token type | Scope | Best for | Risk level |
|---|---|---|---|
| Personal | All user access | scripts, admin tasks | High |
| Project | Single project | CI/CD, integrations | Low |
| Group | Multiple repos | org automation | Medium |
Token scopes (what your token can do)
Scopes define allowed operations.
Common scopes
api→ full API accessread_api→ read-only API accessread_repository→ read repo onlywrite_repository→ push coderead_registry/write_registry→ container registry
Critical rule
Scopes do not override roles.
A token with api scope:
- cannot perform Maintainer actions
- if the underlying user only has Developer access
Common GitLab access token use cases
CI/CD automation
- push code
- manage pipelines
- create tags
SaaS integrations
- create merge requests
- sync issues
- manage repos
Internal tooling
- dashboards
- analytics pipelines
Bots and background jobs
- scheduled tasks
- service automation
GitLab access token not working: common fixes
401 Unauthorized
- token expired
- invalid token
403 Forbidden
- insufficient permissions
- missing role
404 Not Found (misleading)
- token lacks access to resource
- wrong project or group context
Scope mismatch
- wrong scope for endpoint
- read vs write mismatch
Quick checklist
- correct scopes
- correct role
- token still valid
- correct resource context
Real-world GitLab API behavior (what actually happens in production)
Wrong scope or permissions → confusing 403s
curl --header "PRIVATE-TOKEN: $TOKEN" \
"https://gitlab.com/api/v4/projects/$PROJECT_ID/repository/tags"
# {"message":"403 Forbidden"}
This does not always mean the scope is wrong.
It can indicate:
- missing project access
- repository disabled
- insufficient role
Key takeaway:
A 403 often reflects permissions or project configuration—not just scopes.
CI job tokens fail on certain endpoints
curl --header "JOB-TOKEN: $CI_JOB_TOKEN" \
"https://gitlab.com/api/v4/projects/$PROJECT_ID/merge_requests"
# {"message":"404 Not found"}
But with a PAT:
curl --header "PRIVATE-TOKEN: $PERSONAL_API_TOKEN" \
"https://gitlab.com/api/v4/projects/$PROJECT_ID/merge_requests"
# 200 OK
Key takeaway:
CI job tokens cannot access some endpoints (especially merge requests), which is why teams often use PATs in pipelines.
Expired tokens → production failures
{
"status": 401,
"meta.auth_fail_reason": "token_expired"
}
Common pattern:
- token expires
- automation breaks
- token is recreated with broader scopes
Token type vs permissions mismatch
Even with identical scopes:
- project token → 403
- user PAT → 200
Because:
- access depends on backing identity (user vs bot)
Key takeaway:
Scope alone does not determine access—token type and role matter.
GitLab CI job tokens vs personal access tokens
What CI_JOB_TOKEN actually is
- short-lived token
- tied to the pipeline job
- scoped to the project
Used for:
- cloning repos
- CI operations
- limited API calls
Why CI job tokens don't behave like PATs
- limited endpoint access
- restricted permissions
- inconsistent error responses
Example:
- merge request APIs often fail
- returns 404 instead of 403
When to use PATs instead
Use a PAT or project token when:
- creating or updating merge requests
- managing project configuration
- integrating external tools
GitLab vs GitHub authentication
Key differences
- GitLab supports project + group tokens
- scopes differ (
apivsrepo) - permissions combine roles + scopes
Practical implication
You cannot treat Git providers as interchangeable.
Token management in SaaS: what actually scales
The only model that works long-term:
Each customer → one GitLab connection → one token set → one scope contract → one expiration lifecycle
What this looks like
Each connection tracks:
- instance URL
- token(s)
- scopes
- expiration
Why this matters
Without this:
- tokens are scattered
- scopes are inconsistent
- failures are hard to debug
With it:
- each tenant is isolated
- tokens are traceable
- failures are diagnosable
Security best practices
Store tokens securely
- environment variables
- secrets managers
Avoid frontend exposure
- tokens are long-lived secrets
Rotate tokens regularly
- follow expiration policies
- track lifecycle
Apply least privilege
- use minimal scopes
- prefer project tokens over PATs
FAQs
What is a GitLab access token?
A credential used to authenticate API and Git operations.
What's the difference between PAT and project token?
PATs apply to a user; project tokens are scoped to one project.
Does a GitLab token expire?
Yes, based on configuration or admin policy.
What scope should I use?
Use the minimum required for your use case.
Can tokens be used in frontend apps?
No. Always use backend systems.
GitLab authentication: simple mental model
- token = identity + scope + role
- scope defines capability
- role defines permission
- token type affects behavior
Key takeaways
- GitLab tokens are more structured than typical API keys
- token type matters as much as scopes
- most issues come from role + scope mismatches
- CI job tokens are not interchangeable with PATs
- token management becomes complex at scale
- for SaaS, authentication is an infrastructure problem—not a config step
If you're integrating GitLab, the hardest part isn't generating a token—it's managing it correctly across systems and users.