Dev.to · 6 min read

How to Implement Ace Data Cloud Login with OAuth 2.0 and PKCE

How to Implement Ace Data Cloud Login with OAuth 2.0 and PKCE

If your app needs to call a user's Ace Data Cloud resources, asking them to copy an API key is usually the worst part of the onboarding flow. A cleaner approach is OAuth 2.0 Authorization Code Flow with PKCE: the user clicks a login button, approves the requested scopes, and your app receives an access token that can call only the resources the user authorized. This guide walks through the practical shape of that integration using the public Ace Data Cloud OAuth documentation. What you can build The OAuth flow is meant for third-party applications, agents, MCP clients, and automation workflows that want a user to sign in with Ace Data Cloud and then access platform resources on that user's behalf. The auth base URL is: https://auth.acedata.cloud The key endpoints are: Purpose Endpoint Discovery document GET /.well-known/oauth-authorization-server Browser authorization GET https://auth.acedata.cloud/oauth2/authorize Token exchange or refresh POST https://auth.acedata.cloud/oauth2/token Revoke token POST https://auth.acedata.cloud/oauth2/revoke User information GET https://auth.acedata.cloud/api/v1/users/me OAuth app management https://auth.acedata.cloud/user/oauth-apps You can fetch the current discovery document with: curl https://auth.acedata.cloud/.well-known/oauth-authorization-server Supported capabilities include response_type=code, grant_types=authorization_code, refresh_token, PKCE challenge methods S256 and plain, and client authentication methods client_secret_post for confidential clients or none for public PKCE clients. Choose scopes with least privilege Scopes are what make the OAuth flow safer than a copied API key. The user sees the permissions you request, and your token is limited to those permissions. For identity, the supported scopes include: openid: returns the user's unique id profile: returns fields such as username, nickname, avatar, is_verified, and date_joined email: returns email phone: returns phone and region For platform resources, the documented scopes include: applications:read and applications:write credentials:read and credentials:write usage:read orders:read and orders:write There are also aggregate scopes. platform:read expands to applications:read, credentials:read, usage:read, and orders:read. platform:write expands to applications:write, credentials:write, and orders:write. platform expands to both read and write groups. A minimal sign-in flow might request only openid profile. An MCP or IDE client that needs to configure keys could request openid profile credentials:read credentials:write. Request offline_access only if you need a refresh token. Register the OAuth application Create the application at: https://auth.acedata.cloud/user/oauth-apps During registration, choose a client type: Confidential: a backend service that can store client_secret Public: frontend, desktop, CLI, or mobile clients that cannot store secrets and must use PKCE You also configure redirect URIs. The redirect URI must exactly match the redirect_uri you send later in the authorization request. After saving, you receive a client_id. Confidential clients also see a client_secret once, so save it immediately. Redirect the user to authorize The browser redirect starts at: https://auth.acedata.cloud/oauth2/authorize A typical authorization URL looks like this: https://auth.acedata.cloud/oauth2/authorize ?response_type=code &client_id= &redirect_uri= &scope=openid%20profile%20credentials:read &state= &code_challenge= &code_challenge_method=S256 Always validate state when the user returns to your redirect URI. It is your CSRF protection value. For PKCE, generate a random code_verifier, then compute: code_challenge = BASE64URL(SHA256(code_verifier)) Send the code_challenge in the authorization URL and keep the code_verifier for the token exchange. After approval, the browser returns to: ?code=&state= If the user denies access, the redirect contains error=access_denied and an error_description. The authorization code is valid for 10 minutes and can be used only once, so exchange it promptly. Exchange the code for tokens Confidential clients exchange the code with client_secret: curl -X POST https://auth.acedata.cloud/oauth2/token \ -d grant_type=authorization_code \ -d code= \ -d client_id= \ -d client_secret= \ -d redirect_uri= Public PKCE clients exchange the code with code_verifier instead: curl -X POST https://auth.acedata.cloud/oauth2/token \ -d grant_type=authorization_code \ -d code= \ -d client_id= \ -d code_verifier= \ -d redirect_uri= A successful response has this shape: { "access_token": "", "token_type": "Bearer", "expires_in": 1296000, "scope": "openid profile credentials:read", "refresh_token": "" } The access token is a JWT with scope claims and is valid for 15 days. The refresh token appears only when offline_access was requested and is valid for 30 days. Call APIs with the access token To read user information, send the token in the Authorization: Bearer header: curl https://auth.acedata.cloud/api/v1/users/me \ -H "Authorization: Bearer " The returned fields depend on the identity scopes the user granted. For platform resource APIs, call api.acedata.cloud with the same bearer token. For example, if credentials:read was granted: curl https://api.acedata.cloud/api/v1/credentials/ \ -H "Authorization: Bearer " The platform backend validates the JWT scopes. If the token tries to access an unauthorized resource, the API returns 403. Refresh and revoke tokens If you requested offline_access, refresh an expired access token with: curl -X POST https://auth.acedata.cloud/oauth2/token \ -d grant_type=refresh_token \ -d refresh_token= The refresh token is rotated after refresh, so store the new one. To revoke an access or refresh token: curl -X POST https://auth.acedata.cloud/oauth2/revoke \ -d token= Handle errors deliberately OAuth errors use this format: { "error": "", "error_description": "" } Common cases include invalid_request, invalid_client, invalid_grant, access_denied, and unsupported_grant_type. In practice, most integration bugs are invalid_grant: an expired code, a reused code, PKCE verification failure, or a redirect_uri mismatch. The docs also note some useful limits: each account can create up to 20 OAuth applications, authorization codes are valid for 10 minutes and single use, access tokens are valid for 15 days, refresh tokens are valid for 30 days and rotated, and redirect_uri must match exactly. If you are building an agent, MCP client, or internal dashboard, this flow gives users a familiar login experience while keeping access scoped and auditable. The original reference is here: https://platform.acedata.cloud/documents/oauth-integration

This is a summary aggregated from Dev.to. Read the complete article on the original site:

Read full article at Dev.to

Related stories