API testing checklist
- HTTP methods - check whether appropriate method is used or whether dangerous methods are enabled
- GET (read)
- POST (create)
- PUT/PATCH (replace/update)
- DELETE (delete)
- TRACE (replay message) - should be disabled
- CONNECT (tunnel) - should be disabled
- OPTIONS (list available methods) - better be disabled, but if enabled, check if it doesn't disclose dangerous HTTP methods
- HEAD (GET without body) - test on endpoints that require authentication. Should not return 200
- INVALID - check how server responds on invalid data
- IDORS
- ID values - should not be used. If sequential values are present, try different ID
- UUID values - changed to simple sequential ID that are sometimes left for backward compatibility
- CRUD - test for all CREATE/READ/UPDATE/DELETE
- Check for pattern that is not recommended /userid/something/. User ID should come from authentication data.
- Param validation
- Simple validation - e.g. if numbers, test for negative/invalid/string/hex etc.
- Arrays instead of simple vars - e.g. for ?param=test try ?param[]=test
- Injection - start with basic e.g. '
- XSS - check if payload is reflected
- Null byte - %00 or URL encoded %25%30%30
- Unicode - chose your own symbol %e2%98%a3
- Path traversal - /../ or URL encoded %2f%2e%2e%2f
- Parameter polution - e.g. ?user=regular&user=admin
- Payload validation
- If XML is used - try XXE attacks
- If json is used
- Check malformed json
- Check duplicate parameters
- Check invalid data types - e.g. {"username": "Test"} {"username": true} {"username": null} {"username": 1} {"username": [true]} {"username": ["Test", true]} {"username": {"$neq": "black"}
- Check for mass assignement
- Payloads can be tested with commands, injections and etc.
- Wildcards - e.g. /api/users/* /api/users/% /api/users/_ /api/users/.
- Sensitive data in URL
- Rate limiting (where applicable)
- HTTPS enforcement (or HSTS)
- API version
- if /api/v2/ check if /api/v1/ exists. Might be more vulnerable
- Private APIs
- Check that access from public is forbidden
- Try bypassing forbidden
- For /smt/path try /smt/%2e/path
- Try adding HTTP headers X-Originating-IP: 127.0.0.1 X-Forwarded-For: 127.0.0.1 X-Remote-IP: 127.0.0.1 X-Remote-Addr: 127.0.0.1
- CORS (for sensitive endpoints)
- Pass Origin header with our domains and check whether CORS response is present. If so, check for CORS misconfiguration
- Origin: null
- Origin: whitelisted.evil.com
- More advanced techniques
- Pass Origin header with our domains and check whether CORS response is present. If so, check for CORS misconfiguration
- Content negiotation
- Check Accept header - try changing values e.g. from application/json to application/xml
- Posted data type
- Check content-type - try changing values e.g. from application/json to application/xml
- Security headers
- X-Frame-Options - better be set to deny
- Content-Security-Policy - not usually implemented
- Fingerprinting - X-Powered-By, Server etc. should better be off. If on, check whether discloses too much info
- Cache - check if sensitive responses are not cached
- Authentication
- Basic Auth
- Malformed string, null bytes etc.
- JWT
- Check for sensitive data inside token
- Check JWT attacks
- Oauth
- Check redirect URL validation
- Check response_type=token
- Check state parameter validation
- Check CSRF token validation
- Check scope parameter validation
- Other Oauth hacking techniques
- Basic Auth
- Business loogic issues
- Race conditions
- HTTP request smuggling