[OAuth2.0] Building an OAuth2.0 Authorization Server with ScribeJAVA - 1. What is OAuth2.0?
[OAuth2.0] Building an OAuth2.0 Authorization Server with ScribeJAVA - 1. What is OAuth2.0?
As you browse around the web, you'll frequently run into sites that require login. And most of these sites offer platform login options such as "Log in with Naver." It's not just websites either — most apps released these days also provide authentication services through platforms.
Using this, you can sign up or log in through a very simple process. This kind of service is offered not only by Naver but by most platforms of a certain size, such as Google and Kakao, in the form of a "Log in with [Platform]" feature.
Using a platform's information to perform authentication on another site like this is called the OAuth protocol.
OAuth stands for Open Authentication, a standard protocol for authentication.
The previous approach to authentication was for a user to sign up directly with a site or application, providing their information, and authenticating with a password — the password-based authentication method. Of course, this password authentication method has been used since the early days of the internet up to now, but that doesn't mean it was without problems.
- Chaotic authentication systems that differ from one service to another
- Trust issues with the site
- Authentication information piling up the more you use the internet
Before OAuth, there was no real authentication standard to speak of. With no standard, each service's authentication system was overflowing with its own personality. The information and methods required varied wildly from site to site, which would be very confusing from a user's perspective.
That said, this could arguably serve as a kind of yardstick (?) for distinguishing sites, but the bigger problem is that there's no indicator at all for how trustworthy a given site is. Users who have no way of knowing why their information is being taken or how it's being stored end up reluctantly handing their information over to the service anyway.
If you spend even a little time browsing and interacting with these kinds of sites, account information will pile up before you even realize it. The "me" who is the subject of authentication is one and the same, yet due to the absence of an authentication standard, each service ends up holding multiple different ways to authenticate that same "me."
To break this inefficiency, an authentication standard was established under the leadership of Twitter, and this became the origin of OAuth. With the OAuth standard protocol defined, each service can now request authentication from users through a common interface, and since users enter their credentials into a familiar, trustworthy large platform, this brings benefits both in terms of security and in simplifying the process.
OAuth started with version 1.0, and after a security vulnerability called a session fixation attack was discovered in 1.0, version 2.0 is now used.
The downfall of OAuth1.0
OAuth1.0 has a security vulnerability called a session fixation attack. To resolve this, these issues were fixed in OAuth2.0, and OAuth2.0 completely replaces OAuth1.0.
OAuth2.0 is divided into 4 methods depending on the approach used.
Before explaining this, let's look at the keywords used in OAuth.
| Keyword | Meaning |
|---|---|
| User | The user |
| Consumer | The service that provides OAuth (a website, etc.) |
| Service Provider | The OAuth service provider (NAVER, etc.) |
| Access Token | An authentication code for the Consumer to access the Service Provider's resources |
| Refresh Token | A code used to reissue an Access Token |
Most likely, most of us fall into the User category. Here, the service we're ultimately going to build is the Consumer.
Occasionally, the Service Provider is treated separately as an authorization server and a resource server.
Platforms like NAVER and Google become Service Providers, and through the authentication process, they hand over an Access Token and a Refresh Token.
OAuth2.0 is divided into 4 methods depending on the implementation approach.
- The user authenticates directly with the Service Provider
- If authentication succeeds, the Consumer's Frontend receives an authorization code
- The Consumer sends the authorization code to the Service Provider and receives an Access Token and Refresh Token in return
- Because a step of receiving the authorization code is added before the token is returned, this provides a higher level of security
- Since the token exchange happens on the Consumer's Backend, it is difficult to intercept it in the middle
- This is the most common form of authentication used on the web, and this project also applies the authorization code grant flow
INPUT
GET /auth Host: oauth2.example.com response_type=code &client_id=asj2y93bdjen3 &redirect_url=https://oauth2.example.com/callback &state=6b773c55-b688-4a77-adaf-0bd25f4c4111 &scope=email,profile
| Field | Required | Description |
|---|---|---|
| response_type | Y | The response type; fixed to code |
| client_id | Y | The API KEY provided by the Service Provider |
| redirect_url | Y | The response redirect URL |
| state | N | An arbitrary, unique state value |
| scope | N | The requested permissions |
OUTPUT
GET /callback Host: oauth2.example.com code=dfnY865gHjUbnknt57yGV &state=6b773c55-b688-4a77-adaf-0bd25f4c4111
| Field | Description |
|---|---|
| code | The authorization code |
| state | The unique state value that was sent in the request |
state is a state value arbitrarily generated on the Consumer Backend, and it is typically a single generated UUID.
The code and the state you sent are returned. Using the code, you can make a request to the Service Provider and exchange it for an Access Token.
- Unlike the authorization code grant, if authentication succeeds, the Consumer directly receives the Token
- Implemented using the JavaScript SDK provided by each platform
- Compared to the authorization code grant, no server is required, so implementation is simpler
- Since the Token is passed via GET as a URL parameter, it is vulnerable in terms of security
INPUT
GET /auth Host: oauth2.example.com response_type=token &client_id=asj2y93bdjen3 &redirect_url=https://oauth2.example.com/callback &state=97c66e11-d0e0-4c86-833c-e08bed40748d &scope=email,profile
| Field | Required | Description |
|---|---|---|
| response_type | Y | The response type; fixed to token |
| client_id | Y | The API KEY provided by the Service Provider |
| redirect_url | Y | The response redirect URL |
| state | N | An arbitrary, unique state value |
| scope | N | The requested permissions |
OUTPUT
GET /callback Host: oauth2.example.com #access_token=kr40FkgksmGS92lffkGls &token_type=Bearer &expires_in=3600 &state=97c66e11-d0e0-4c86-833c-e08bed40748d
| Field | Description |
|---|---|
| access_token | The access token |
| token_type | The type of the access token; typically Bearer is used |
| expires_in | The token's validity period (in seconds) |
| state | The unique state value that was sent in the request |
Unlike the authorization code grant, the Access Token is included directly in the response.
Why does the parameter start with #?
# is an identifier called a URI Fragment. Since this identifier is not sent to the server when accessing the URL, this is a measure taken to gain an advantage in terms of security.
- The Token is received by sending an ID and PW to the Service Provider
- Since the security structure relies solely on password-based authentication, the Consumer implementing this must be highly trustworthy
INPUT
POST /auth Host: oauth2.example.com grant_type=password &client_id=asj2y93bdjen3 &username=username123 &password=password123 &scope=email,profile
| Field | Required | Description |
|---|---|---|
| grant_type | Y | The grant type; fixed to password |
| client_id | Y | The API KEY provided by the Service Provider |
| username | Y | The username |
| password | Y | The password |
| scope | N | The requested permissions |
JSON
{ "access_token": "dGkdi93ns2kdkV9dkA3", "token_type": "Bearer", "expires_in": 3600, "scope": "email,profile" }
| Field | Description |
|---|---|
| access_token | The access token |
| token_type | The type of the access token; typically Bearer is used |
| expires_in | The token's validity period (in seconds) |
| scope | The requested permissions |
- A form in which the user receives an Access Token from an external store and authenticates with it
- Since the client itself acts as the means of authentication, the process is very simple
- Typically used to call information about itself only
INPUT
GET /auth Host: oauth2.example.com grant_type=client_credentials &client_id=asj2y93bdjen3 &client_secret=https://oauth2.example.com/callback &scope=email,profile
| Field | Required | Description |
|---|---|---|
| grant_type | Y | The response type; fixed to client_credentials |
| client_id | Y | The API KEY provided by the Service Provider |
| client_secret | Y | The API Secret KEY provided by the Service Provider |
| scope | N | The requested permissions |
JSON
{ "access_token": "dGkdi93ns2kdkV9dkA3", "token_type": "Bearer", "expires_in": 3600, "scope": "email,profile" }
| Field | Description |
|---|---|
| access_token | The access token |
| token_type | The type of the access token; typically Bearer is used |
| expires_in | The token's validity period (in seconds) |
| scope | The requested permissions |
- OAuth2.0 is a standard protocol for authentication, and services that comply with the OAuth protocol can basically use a common API to perform authentication.
- Through the OAuth protocol, the authentication process can be simplified while the level of security is strengthened.
- OAuth methods are divided into 4 types, and the authorization code grant method is the most commonly used.
- The implicit grant is mainly used in serverless services or apps.
- The remaining methods are used in special-purpose environments.
The next chapter covers the composition of the system we're going to build.

![[NextJS] Blog Redesign Journey - 3. Adding SCSS](https://user-images.githubusercontent.com/50317129/134931033-89954c3d-5e00-4b3b-85aa-54a1dfa29e46.png)