What is the difference between a public client and a confidential client in OAuth?
A confidential client runs in an environment the end user cannot access and can keep a client secret safe (a backend server, an API); a public client runs on the user's device (browser, mobile app, IoT) and cannot keep any secret.
| Public client | Confidential client | |
|---|---|---|
| Runs in | An untrusted environment the user controls: a single-page app in the browser, a mobile app, an IoT device | A secure environment the end user has no access to: a web backend, an API, a managed device |
| Client secret | Cannot protect one: anything shipped in the app can be extracted | Can store a client secret (or a private key) securely |
| At the token endpoint | Only identifies itself with its client ID | Authenticates itself with its secret or key |
| Protection for the code exchange | PKCE is essential | PKCE is still recommended on top of the secret |
The reason this distinction matters is that any secret compiled into a mobile app or JavaScript bundle is public: an attacker can decompile the app or read the source and impersonate the client. Public clients therefore need protection that does not depend on a static secret, which is why PKCE was invented. Public is the default assumption: unless you can show the client runs somewhere the user cannot reach, treat it as public.
Go deeper:
oauth.net: Confidential and Public Clients — short explanation with examples of each type.
RFC 6749, Section 2.1: Client Types — the normative definitions and client profiles.