Secure Quarkus application with ezto
Tags: ezto, quarkus, keycloak, authentication
Published: 2024-03-24 14:30:26

In this blog, we will learn how to create a secured API using Quarkus, Java, and ezto auth

### Authentication and Authorization

#### Authentication:

Authentication is the process of verifying the identity of a user or system. It ensures that the user or system is who they claim to be before granting access to resources or functionalities. Think of authentication as confirming your identity to gain access to a system or application.

Imagine you work in an office building with a security entrance. Before you can enter the office and access your workspace, you need to prove that you're an employee by presenting your ID card to the security guard. In this scenario:

- The office building represents the system or resource you want to access.

- Your ID card represents your credentials, similar to a username and password.

- Presenting your ID card to the security guard is the process of authentication.

- If the security guard verifies that your ID card is valid and belongs to you, you are authenticated, and you're allowed to enter the office.

#### Authorization:

Authorization, is about determining what actions or resources a user or system is allowed to access after authentication. It involves verifying the permissions and privileges associated with the authenticated identity. Authorization controls what you can do or see within a system or application based on your role or level of access.

Now, let's say there are different areas within the office building, each with restricted access based on your job role. Before you can enter certain areas, the security guard checks your ID card to see if you're authorized to enter those areas. In this scenario:

- The restricted areas represent the authorization rules.

- Your authorization level, determined by your job role, is encoded on your ID card.

- The security guard checks your ID card to verify your authorization.

- Once your authorization is confirmed, you're allowed to enter the specific areas you're authorized for, but not others.

In summary, authentication verifies your identity (presenting your ID card), while authorization determines what you're allowed to access (which areas of the office you're allowed to enter based on your job role).

### What is ezto auth?
- ezto auth, as an IAM solution, encompasses both CIAM (Customer Identity and Access Management) and WIAM (Workforce Identity and Access Management) functionalities. For CIAM, ezto auth provides seamless customer authentication, enhancing user experience and security in digital interactions. In WIAM, ezto auth streamlines workforce identity verification and access management, enabling organizations to efficiently manage employee access to resources while ensuring compliance and security standards.
- For more information about ezto, visit the [ezto Auth page](https://www.eztoauth.com/). Explore the features and benefits of ezto auth, including user management, role-based access control, and secure authentication methods.

### Create Authentication flow in ezto auth

**1. Create Your Workspace**

Start by setting up your workspace in ezto auth. Just visit [this page](https://docs.ezto.io/auth/docs/wiam/Set%20up%20workspace/) for simple instructions.

**2. Craft Your Application**

Next, create an application within ezto auth to manage authentication. Visit [this page](https://docs.ezto.io/auth/docs/wiam/applications/Browser%20Based/) for a straightforward guide. You can use the default authentication flow or customize it to suit your needs.

> Enable the 'Confidential' option for your application in Ezto. This option signifies that the application requires client authentication using a client ID and client secret. After enabling 'Confidential', copy both the App ID and App Secret provided by Ezto. We will utilize these credentials later in this blog for authentication purposes
 
**3. Create user and role**

- Create admin, and user(this will be available by default) roles in ezto auth, Refer [this page](https://docs.ezto.io/auth/docs/wiam/authorization/roles/Create%20Role/) for create a role

- Create a user and assign the admin role to that user. Refer [this page](https://docs.ezto.io/auth/docs/wiam/user%20management/Overview/) for create and assign role for user.
- And create another user with user role.
- Verify users by confirming their email through the verification link provided via email.


**4. Trigger Authentication Flow**

Once your application is set up, click "try" to trigger the authentication process. This generates a special link users can use to verify their identity. It's as simple as clicking a button!

**5. Get Your Access Token**

Use that link to trigger the authentication flow, they'll be asked for their username and password(default authentication flow). After successful authentication, they'll be redirected to Ezto's debugger page, where an access token is generated. We will use that token in later this blog

### Authorization in a Quarkus API

**1.Initializing Your Quarkus Project**

- Visit [code.quarkus.io](https://code.quarkus.io/) to begin your Quarkus project. This site helps you set up your Quarkus application and find useful extensions.
- Choose the build tool that convenient for you(In this blog we will use Maven)
- Search for the "quarkus-resteasy-reactive","quarkus-oidc" dependency and add them to your project. These dependencies enable you to use RESTful web services and OpenID Connect for authentication in your Quarkus application.
- Click "Generate your application", it will create a zip of your project, download, extract, and open it in IntelliJ

**2. Developing API Endpoints** 

In this section, we'll dive into implementing authorization in our Quarkus API using role-based access control (RBAC). 

- Go to your project, set up a new API endpoint accessible at "/api/user". Name the endpoint class "UsersResource". This endpoint will only be accessible to users with the "user" role.

```
package org.sample.blog.resource;

import jakarta.annotation.security.RolesAllowed;
import jakarta.inject.Inject;
import jakarta.ws.rs.*;

import org.jboss.resteasy.reactive.NoCache;
import io.quarkus.security.identity.SecurityIdentity;

@Path("/api/user")
public class UsersResource {

    @Inject
    SecurityIdentity securityIdentity;

    @GET
    @RolesAllowed("user")
    @NoCache
    public String user() {
        return "user";
    }
}
```

- Create a new API endpoint accessible at "/api/admin" and name the class "AdminResource". This endpoint will only be accessible to users with the "admin" role.
```
package org.sample.blog.resource;

import jakarta.annotation.security.RolesAllowed;
import jakarta.ws.rs.GET;
import jakarta.ws.rs.Path;
import jakarta.ws.rs.Produces;
import jakarta.ws.rs.core.MediaType;

@Path("/api/admin")
public class AdminResource {

    @GET
    @RolesAllowed("admin")
    @Produces(MediaType.TEXT_PLAIN)
    public String admin() {
        return "admin";
    }
}
```

- We define security constraints using annotations such as @RolesAllowed("user") and @RolesAllowed("admin"). These annotations specify which user roles are allowed to access certain API endpoints.
- Go to the 'resources/application.properties' file in your project to add the necessary configuration settings

```
# Set the base URL of the OpenID Connect (OIDC) server
quarkus.oidc.auth-server-url=https://<your-workspace>.eztoauth.com/auth/realms/<your-workspace>

# Set a client ID to identify the application (copied from application settings)
quarkus.oidc.client-id=<your-app-id-that>

# Set the client secret, used by the client_secret_basic authentication method
quarkus.oidc.credentials.secret=<your-app-secret>

# Define permissions for authenticated users
quarkus.http.auth.permission.authenticated.paths=/*
quarkus.http.auth.permission.authenticated.policy=authenticated
```

#### Explanation:

- quarkus.oidc.auth-server-url: This property sets the base URL of the OIDC server. It specifies the location where authentication requests should be sent.

- quarkus.oidc.client-id: This property sets a client ID that uniquely identifies your application to the OIDC server. It's used during the authentication process to identify the client.

- quarkus.oidc.credentials.secret: This property sets the client secret, which is a confidential value shared between the client and the OIDC server. It's used to authenticate the client to the server.

- quarkus.http.auth.permission.authenticated.paths: This property defines the paths that should be protected and require authentication. In this case, all paths (represented by '/*') are protected.

- quarkus.http.auth.permission.authenticated.policy: This property specifies the policy to apply to the protected paths. The 'authenticated' policy ensures that only authenticated users can access the protected paths.

> Ensure to replace "your-workspace", "your-app-id", and "your-app-secret" with the appropriate values for your application.

### 3. Testing Authentication Flow
For build and run your qurkus application run below comment(if you use maven)
```
./mvnw quarkus:dev --debug 
```

#### Hit Endpoints without Authentication:

1. Start by attempting to access the endpoints http://localhost:8080/api/user or http://localhost:8080/api/admin in Postman. You will receive a "401 Unauthorized" status because you don't have a valid authentication token.

2. Trigger Authentication Flow:
 - Go to your ezto auth application and copy the provided authentication URL.
 - Paste the URL into your browser's address bar and trigger the authentication flow.
 - Log in using a user who has the "user" role (not the admin role). This will generate an authentication token.

3. Access User Endpoint:
 - Copy the generated authentication token.
 - Use this token to hit the http://localhost:8080/api/user endpoint in Postman. You should receive a successful response.

4. Access Admin Endpoint:
 - Attempt to access the http://localhost:8080/api/admin endpoint using the same token. You will receive a "403 Forbidden" response because the user does not have the necessary permissions to access this endpoint.

5. Repeat the Process with Admin Role:
 - Repeat the process with a user who has admin privileges in your Ezto application.
 - Generate a new authentication token for this user.
 - Use the token to access both the http://localhost:8080/api/user and http://localhost:8080/api/admin endpoints in Postman.

By following these steps, you can verify that your authentication flow is functioning correctly, and access to endpoints is properly restricted based on user roles.

### Conclusion:

In this blog post, we explored how to create a secure API using Quarkus, Java, and ezto auth. By leveraging ezto auth's authentication and authorization capabilities, we ensure that our APIs are protected and accessible only to authorized users.

Ezto auth simplifies the authentication process, offering robust features such as role-based access control and secure client authentication. With ezto auth, developers can streamline user management, enhance security, and ensure compliance with industry standards.

By integrating ezto auth with Quarkus, developers can accelerate the development of secure APIs while focusing on building innovative solutions. Whether you're developing internal tools or customer-facing applications, ezto provides the flexibility and scalability needed to succeed in today's digital landscape.

Unlock the full potential of your applications with Ezto - the trusted choice for authentication and access management.