avatarIvan Franchin

Free AI web copilot to create summaries, insights and extended knowledge, download it at here

1469

Abstract

<p id="5d64" type="7">一言蔽之,在考慮所有利息、手續費、服務費、雜費、還款假期、利息回贈、現金回贈、分期供款等花巧東西後,化繁為簡,變為我們最熟悉的那個利率便是「實際年利率」喇!</p><h1 id="6d4d">認識「實際年利率」的好處</h1><p id="3f62">好處只有一個,因為「實際年利率」是一個化繁為簡後的利率,赤條條無遮無掩無得花巧,<b>所以是一個可以用來 apple-to-apple 用來直接比較不同貸款方案利息平貴的 rate!</b> <b>其他所有 rate 什麼手續費什麼月平息基本上都可以掃開喇!</b></p><h1 id="bf34">APR 很好,但要小心別把優惠 double-count!</h1><p id="752a">根據銀行公會的指示,如果銀行為客戶提供現金回贈時,是有責任<b>同時提供</b>「包括」和「不包括」現金回贈的 APR,但在廣告 tagline 時仍然可以選擇只寫其中一個 (當然是抱括現金回贈的那個,因為那個 APR 較低嘛)。</p><p id="99ae">以大新銀行「分期快應錢」做個例子,貸款額 $100 萬的客戶一般可享 $2,000 的現金回贈,以 12 個還款期計算,當考慮這筆 $2,000 回贈時,APR 為 2.08%,不考慮時則升至 2.45%。</p><figure id="a9d1"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*mq63eY3Knbz21nm0RbCoqw.png"><figcaption>source: <a href="http://www.dahsing.com/html/tc/personal_loan/express_money.html">http://www.dahsing.com/html/tc/personal_loan/express_money.html</a></figcaption></figure><figure id="cb60"><img src="https://cdn-images-1.readmedium.com/v2/resize:fit:800/1*WEIvTX8iHtWCiQ1ZS9cPJg.png"><figcaption>source: <a href="http://www.dahsing.com/tc/pdf/loan/em_T&amp;C_tc.pdf">http://www.dahsing.com/tc/pdf/loan/em_T&amp;C_tc.pdf</a></figcaption></figure><p id="df8b">但當你瀏覽宣傳單張、瀏覽網頁或在分行被銷售的時候,經時會看到 / 聽到類似的話:</p><p id="023a" type="7">好抵架,如果借 $100 萬,APR 低到 2.08%,「仲有」 $2,000 現金回贈添!</p><p id="57dc">留意番,魔鬼就在「仲有」兩隻字嗰度,2.08% 已考慮 $2,000 現金回贈!所以唔應該係「仲有」,而應該係「包括咗」... <b>一個不小心就會把優惠 double-count 了!</b></p><p id="cba2">另外一個可以降低 APR 的方法便是提供「首月還款假期」,即第二個月才開始還款,類似的 tagline 包括:</p><

Options

p id="8889" type="7">好抵架,如果借 $100 萬,APR 低到 2.08%,「仲有」 首月還款假期添!</p><p id="3599">謹記所有優惠也會影響 APR ,<b>分清楚到底廣告/職員說的到底是「優惠前」還是「優惠後」的 APR 就能作出精明選擇了</b></p><p id="166e">版主推介:</p><div id="7d3e" class="link-block"> <a href="https://medium.com/@Watin/%E9%8A%80%E8%A1%8C%E5%B0%8F%E7%9F%A5%E8%AD%98-1-%E8%B2%B8%E6%AC%BE%E5%89%8D%E5%BF%85%E8%A6%81%E6%90%9E%E6%87%82%E7%9A%84-78-%E6%B3%95%E5%89%87-c4fbdc2cd0c3"> <div> <div> <h2>銀行小知識 (1) — 貸款前必要搞懂的「78 法則」</h2> <div><h3>知道了做貸款便有預算了</h3></div> <div><p>medium.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/1*jNn_gXMBUzrq4tf_96JwXA.png)"></div> </div> </div> </a> </div><div id="6ca5" class="link-block"> <a href="https://medium.com/@Watin/%E4%BF%A1%E7%94%A8%E5%8D%A1%E9%96%91%E8%AB%87-11-%E5%B8%B6-2-%E5%BC%B5%E5%85%AB%E9%81%94%E9%80%9A-50b7ca868310"> <div> <div> <h2>信用卡閑談(11) — 如何賺盡八達通回贈?</h2> <div><h3>帶 2 張八達通出街!</h3></div> <div><p>medium.com</p></div> </div> <div> <div style="background-image: url(https://miro.readmedium.com/v2/resize:fit:320/1*acfp_LQv6zcOi9ce0R0-Pg.png)"></div> </div> </div> </a> </div></article></body>

Spring Boot | Star Vote

Building a Single Spring Boot App with Keycloak or Okta as IdP: Enabling Okta as IdP

A step-by-step guide on how to enable Okta as Identity Provider to the StarVote application

Photo by Chris Murray on Unsplash

This article is part of a series that explores the implementation of a Single Spring Boot application called StarVote. The application will use Keycloak or Okta as Identity Provider.

In the introductory article, we outline the sections we will cover:

Here’s a sneak peek of how the StarVote application will be at the end!

In this particular article, we’ll explore how to enable authentication using Okta as an Identity Provider, covering the necessary configurations and integration steps.

So, let’s get started!

Configuring Okta

Access Developer Edition Account

Add Application

  1. In the “Okta Admin Dashboard” main menu on the left, click “Applications” menu and then “Applications” sub-menu;
  2. On the next page, click Create App Integration button;
  3. Select OIDC - OpenID Connect as “Sign on method”, Web Application as “Application type”, and click Next;
  4. In the “New Web App Integration” form:
  • Set star-vote in “App integration name” field;
  • Check Authorization Code and Implicit (hybrid) in “Grant type”;
  • For “Sign-in redirect URIs”, add http://localhost:8080/login/oauth2/code/okta and http://localhost:8080/api/callback/token;
  • For “Sign-out redirect URIs”, add http://localhost:8080;
  • For “Controlled access”, select Skip group assignment for now;
  • Click Save;

5. The Client ID and Client Secret are generated. The Okta Domain can be obtained by clicking the button-menu present on the up-right corner of the screen.

Create groups

  1. In the “Okta Admin Dashboard” main menu on the left, click “Directory” menu and then “Groups” sub-menu;
  2. Let’s create the Admin’s group:
  • Click Add Group;
  • Enter STAR-VOTE-ADMIN for the “Name” text-field;
  • Click Save;

3. Let’s repeat the same process to create the Users’s group:

  • Click Add Group;
  • Enter STAR-VOTE-USER for the “Name” text-field;
  • Click Save;

Add an Admin

  1. In the “Okta Admin Dashboard” main menu on the left, click “Directory” menu and then “People” sub-menu;
  2. Click Add person button;
  3. Enter the following information for the Admin:
  • For “First name”, set App;
  • For “Last name”, set Admin;
  • For “Username”, set [email protected];
  • The “Primary email” will be filled with the same content as the “Username”;
  • In “Groups”, start typing STAR. The STAR-VOTE-ADMIN group will pop up. Select it to add it;
  • In “Password”, select Set by admin;
  • Set a strong password in the text-field that will appear;
  • Uncheck the check-box that says "User must change password on first login";
  • Click Save.

Assign Groups to Application

  1. In the “Okta Admin Dashboard” main menu on the left, click “Directory” menu and then “Groups” sub-menu;
  2. Select the STAR-VOTE-ADMIN group by clicking on its name;
  3. Click “Applications” tab and then, click Assign Applications;
  4. Click the Assign button related to star-vote application and then click Done;
  5. Repeat the same process for the STAR-VOTE-USER group.

Add Claim

  1. In the “Okta Admin Dashboard” main menu on the left, click “Security” menu and then “API” sub-menu;
  2. In “Authorization Servers” tab, select the default by clicking on its name;
  3. In “Claims” tab, click Add Claim;
  4. Enter the following information for the new claim:
  • For the “Name”, type groups;
  • For the “Include in token type” field, select Access Token and keep Always in the right field;
  • For the Value type, select Groups;
  • For the “Filter” field, select Matches regrex and set .* in the right field
  • For the “Include in” select Any scope;
  • Click Create.

Enable the Registration of New Users

  1. In the “Okta Admin Dashboard” main menu on the left, click “Directory” menu and then “Self-Service Registration” sub-menu;
  2. In the “Self-Service Registration” screen, click Enable Registration button or, in case you have already done it before, edit the “Self-Service Registration” form;
  3. Make sure the “Self-service registration” field is set to Enabled;
  4. In “Registration” section, set STAR-VOTE-USER group to the field “Assign to group”;
  5. In “Post-registration” section, “Activation requirements” field, disable the checkbox that says: “User must verify email address to be activated”;
  6. Click Save.

That is it. Okta is configured!

Backend & Frontend Modifications

Update the application.properties

Let’s add the following lines to application.properties file:

jwt.auth.converter.principal-attribute=email

spring.security.oauth2.resourceserver.jwt.issuer-uri=https://${OKTA_DOMAIN}/oauth2/default

spring.security.oauth2.client.provider.okta.issuer-uri=https://${OKTA_DOMAIN}/oauth2/default
spring.security.oauth2.client.provider.okta.user-name-attribute=${jwt.auth.converter.principal-attribute}

spring.security.oauth2.client.registration.okta.clientId=${OKTA_CLIENT_ID}
spring.security.oauth2.client.registration.okta.clientSecret=${OKTA_CLIENT_SECRET}
spring.security.oauth2.client.registration.okta.scope=openid,profile,email
  • The jwt.auth.converter.principal-attribute property configures the principal attribute. It determines how the user is identified in the JWT.
  • The spring.security.oauth2.resourceserver.jwt.issuer-uri property specifies the URI of the issuer for JWT tokens. The issuer URI is used to verify the authenticity and integrity of the JWT token received by the resource server;
  • The spring.security.oauth2.client.provider.okta.issuer-uri specifies the URI of the OpenID Connect (OIDC) provider (in this case, Okta) for the OAuth 2.0 client. This URI is used to configure the client to authenticate and interact with the OIDC provider during the OAuth 2.0 flow;
  • The spring.security.oauth2.client.provider.okta.user-name-attribute specifies the attribute in the JWT token that represents the username or user identifier. The username attribute is used to identify the user in the application;
  • The spring.security.oauth2.client.registration.okta.clientId specifies the client ID for the OAuth 2.0 client.
  • The spring.security.oauth2.client.registration.okta.clientSecret specifies the client secret for the OAuth 2.0 client;
  • The spring.security.oauth2.client.registration.okta.scope specifies the scope requested by the OAuth 2.0 client during the authorization process. Scopes define the permissions and access rights requested by the client. In this configuration, the client requests the openid, profile, and email scopes, which are commonly used to access basic user information and profile details.

Update the login.html

Let’s apply the following change (highlighted in bold) in login.html:

<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
...

<body>

<div class="ui center aligned basic segment">
    ...
    <div class="ui compact labeled icon menu">
        <a class="item" th:href="@{/oauth2/authorization/okta}">
            <i class="openid alternate icon"></i>
            Okta
        </a>
    </div>
</div>

...
</body>
</html>

The th:href="@{/oauth2/authorization/okta}" is a Thymeleaf attribute used in an anchor tag (<a>) to specify the URL for the Okta authentication. This endpoint initiates the OAuth2 authorization flow with the chosen identity provider. When the user clicks on the corresponding link, it triggers the authentication process and redirects them to the appropriate authorization page.

Update the StarAPIController class

Let’s add a new endpoint in StarAPIControlle class:

@RequestMapping("/api")
public class StarAPIController {
    ...

    @PostMapping("/callback/token")
    public Map<String, String> callbackToken(@RequestBody MultiValueMap<String, String> queryMap) {
        return queryMap.toSingleValueMap();
    }
}

The callbackToken method handles a POST request sent to the /api/callback/token endpoint. This endpoint is used to handle the callback from Okta after successful authentication, extracting relevant information from the request.

Update the WebSecurityConfig class

In WebSecurityConfig class, let’s implement the following changes:

  1. Let’s modify the configuration to allow unrestricted access to perform HTTP POST requests to the /api/callback/token endpoint;
  2. Provide the implementation to the extractRoles method.
public class WebSecurityConfig {
    ...

    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
        return http
                .authorizeHttpRequests(authorizeHttpRequests -> authorizeHttpRequests
                        ...
                        .requestMatchers(HttpMethod.POST, "/api/callback/token").permitAll()
                        ...
    }
    
    private Collection<? extends GrantedAuthority> extractRoles(Jwt jwt) {
        Collection<String> groups = jwt.getClaim("groups");
        if (groups == null) {
            return Collections.emptySet();
        }
        return groups.stream()
                .map(role -> new SimpleGrantedAuthority("ROLE_" + role))
                .collect(Collectors.toSet());
    }
}

Testing StarVote application

Start StarVote

Make sure you are in the root folder of the StarVote application in the terminal.

Export to the OKTA_DOMAIN, OKTA_CLIENT_ID and OKTA_CLIENT_SECRET environment variables, the values provided by Okta.

export OKTA_DOMAIN=<your-okta-domain>
export OKTA_CLIENT_ID=<star-vote-client-id-provided-by-okta>
export OKTA_CLIENT_SECRET=<star-vote-client-secret-provided-by-okta>

Then, run the following command:

./mvnw clean spring-boot:run

Testing StarVote UI

Once the application is started, let’s open a browser and access: http://localhost:8080.

Then, click the Login button present on the top-right of the screen and select Okta.

The Okta login page will appear.

Enter [email protected] in the “Username” field, and provide the password you used during the admin creation in the “Password” field.

You are in! 🎉

Feel free to add your favorite movie stars or even register as a new user on StarVote! 😃

Testing StarVote API

Once the application is started, we can submit requests to its endpoints. Let’s try to retrieve all the stars. So, open another terminal and run the following command:

curl -i http://localhost:8080/api/stars

This command will return an HTTP 401 response, as the endpoint is now secured.

In order to access it, we need to provide an Bearer access token.

  1. In a terminal, create the following environment variables:
OKTA_DOMAIN=<your-okta-domain>
OKTA_CLIENT_ID=<star-vote-client-id-provided-by-okta>

2. Then, run the following commands to get “Okta Access Token URL”:

OKTA_ACCESS_TOKEN_URL="https://${OKTA_DOMAIN}/oauth2/default/v1/authorize?\
client_id=${OKTA_CLIENT_ID}\
&redirect_uri=http://localhost:8080/api/callback/token\
&scope=openid\
&response_type=token\
&response_mode=form_post\
&state=state\
&nonce=myNonceValue"

echo $OKTA_ACCESS_TOKEN_URL

3. Copy the “Okta Access Token URL” from the previous step and paste it in a browser;

4. The Okta login page will appear. Provide the app-admin’s Username & Password and click Sign In;

5. It will redirect to api/callback/token endpoint of star-vote application and the Access token will be displayed, together with other information:

{
    "state": "state",
    "access_token": "eyJraWQiOiJ2SnpILThkQlV1X0RuX19fNVJ4MVV...",
    "token_type": "Bearer",
    "expires_in": "3600",
    "scope": "openid"
}

6. Let’s copy and set it to another environment variable called APP_ADMIN_ACCESS_TOKEN

Note: you will get a different access_token!

APP_ADMIN_ACCESS_TOKEN=eyJraWQiOiJ2SnpILThkQlV1X0RuX19fNVJ4MVV...

We can inspect the access token using jwt.io website. After decoding it, we have the following for header and payload:

header

{
  "kid": "vJzH-8dBUu_Dn___5Rx1UzPMUkM0AwwB274iwLgh3eQ",
  "alg": "RS256"
}

payload

{
  "ver": 1,
  "jti": "AT.P9qYWLfFskfDRPGXV5elUejIzlFcHycehWwIGTpf7q0",
  "iss": "https://dev-xxxxxx.okta.com/oauth2/default",
  "aud": "api://default",
  "iat": 1686244166,
  "exp": 1686247766,
  "cid": "0oaszfsj6qbrvYHZ2357",
  "uid": "00uszg1vv6oElxd3z357",
  "scp": [
    "openid"
  ],
  "auth_time": 1686244165,
  "sub": "[email protected]",
  "groups": [
    "Everyone",
    "STAR-VOTE-ADMIN"
  ]
}

Looking closed the payload, we can see the “groups” field. It contains the role STAR-VOTE-ADMIN.

7. Let’s proceed and provide the APP_ADMIN_ACCESS_TOKEN in the next call to the /api/stars endpoint. Here is the updated cURL command:

curl -i http://localhost:8080/api/stars -H "Authorization: Bearer $APP_ADMIN_ACCESS_TOKEN"

This command should return an HTTP 200 response with an array of stars (maybe empty in case you haven’t added any star).

The API is working great! 🎉

8. To shut it down, go to the terminal where it’s running and press Ctrl+C.

Okta Cleanup

Once you no longer require the Okta configuration, let’s clean up the configuration that we have set up.

Delete Admin

  1. In the “Okta Admin Dashboard” main menu on the left, click “Directory” menu and then “People” sub-menu;
  2. Select the App Admin by clicking on its name;
  3. In App Admin profile, click More Actions multi-button and then Deactivate and confirm deactivation;
  4. Still in App Admin profile, click Delete button and confirm deletion;

Delete Groups

  1. In the “Okta Admin Dashboard” main menu on the left, click “Directory” menu and then “Groups” sub-menu;
  2. Select STAR-VOTE-ADMIN group by clicking on its name;
  3. In STAR-VOTE-ADMIN profile, click Actions and then click Delete sub-button. Confirm deletion by clicking Delete Group button;
  4. Do the same process to STAR-VOTE-USER group.

Delete Application

  1. In the “Okta Admin Dashboard” main menu on the left, click “Applications” menu and then “Applications” sub-menu;
  2. In Application list whose status is ACTIVE, click star-vote's gear icon and then click Deactivate; Confirm deactivation by clicking Deactivate Application button;
  3. Now, in Application list whose status is INACTIVE, click star-vote's gear icon and then click Delete. Confirm deletion by clicking Delete Application button;

Delete Claim

  1. In the “Okta Admin Dashboard” main menu on the left, click “Security” menu and then “API” sub-menu;
  2. In “Authorization Servers” tab, select the default by clicking on its name;
  3. In “Claims” tab, click the x icon related to the groups claim created;
  4. Confirm deletion by clicking OK button.

Disable the Registration of New Users

  1. In the “Okta Admin Dashboard” main menu on the left, click “Directory” menu and then “Self-Service Registration” sub-menu;
  2. In the “Self-Service Registration” screen, click the edit link present on the right of the screen;
  3. Select the Disabled for “Self-service registration” field;
  4. Click Save.

That’s it

This concludes the series where we provided detailed explanations on implementing the StarVote application using Spring Boot and securing it with Keycloak or Okta as Identity Provider.

We hope you found it enjoyable and informative.

Support and Engagement

If you enjoyed this article and would like to show your support, please consider taking the following actions:

  • 👏 Engage by clapping, highlighting, and replying to my story. I’ll be happy to answer any of your questions;
  • 🌐 Share my story on Social Media;
  • 🔔 Follow me on: Medium | LinkedIn | Twitter | GitHub;
  • ✉️ Subscribe to my newsletter, so you don’t miss out on my latest posts.
Spring Boot
Keycloak
Okta
Technology
Software Development
Recommended from ReadMedium