✨ Present nonce in id token
This commit is contained in:
		@@ -3,9 +3,17 @@
 | 
			
		||||
  <database-model serializer="dbm" dbms="POSTGRES" family-id="POSTGRES" format-version="4.52">
 | 
			
		||||
    <root id="1">
 | 
			
		||||
      <DateStyle>mdy</DateStyle>
 | 
			
		||||
      <IntrospectionStateNumber>10192</IntrospectionStateNumber>
 | 
			
		||||
      <Grants>1||-9223372036854775808|c|G
 | 
			
		||||
1||10|c|G
 | 
			
		||||
1||10|C|G
 | 
			
		||||
1||10|T|G
 | 
			
		||||
4||-9223372036854775808|c|G
 | 
			
		||||
4||10|c|G
 | 
			
		||||
4||10|C|G
 | 
			
		||||
4||10|T|G</Grants>
 | 
			
		||||
      <IntrospectionStateNumber>10209</IntrospectionStateNumber>
 | 
			
		||||
      <ServerVersion>16.3</ServerVersion>
 | 
			
		||||
      <StartupTime>1721488981</StartupTime>
 | 
			
		||||
      <StartupTime>1722154972</StartupTime>
 | 
			
		||||
      <TimeZones>true ACDT
 | 
			
		||||
true ACSST
 | 
			
		||||
false ACST
 | 
			
		||||
@@ -800,7 +808,7 @@ false Zulu
 | 
			
		||||
13474||10|C|G
 | 
			
		||||
13474||-9223372036854775808|U|G
 | 
			
		||||
13474||10|U|G</Grants>
 | 
			
		||||
      <IntrospectionStateNumber>10192</IntrospectionStateNumber>
 | 
			
		||||
      <IntrospectionStateNumber>10209</IntrospectionStateNumber>
 | 
			
		||||
      <ObjectId>37312</ObjectId>
 | 
			
		||||
      <OwnerName>postgres</OwnerName>
 | 
			
		||||
    </database>
 | 
			
		||||
@@ -4241,8 +4249,8 @@ false Zulu
 | 
			
		||||
    <schema id="268" parent="2" name="public">
 | 
			
		||||
      <Comment>standard public schema</Comment>
 | 
			
		||||
      <Current>1</Current>
 | 
			
		||||
      <IntrospectionStateNumber>10192</IntrospectionStateNumber>
 | 
			
		||||
      <LastIntrospectionLocalTimestamp>2024-07-24.08:06:15</LastIntrospectionLocalTimestamp>
 | 
			
		||||
      <IntrospectionStateNumber>10209</IntrospectionStateNumber>
 | 
			
		||||
      <LastIntrospectionLocalTimestamp>2024-07-28.12:55:20</LastIntrospectionLocalTimestamp>
 | 
			
		||||
      <ObjectId>2200</ObjectId>
 | 
			
		||||
      <StateNumber>523</StateNumber>
 | 
			
		||||
      <OwnerName>pg_database_owner</OwnerName>
 | 
			
		||||
 
 | 
			
		||||
@@ -1,2 +1,2 @@
 | 
			
		||||
#n:public
 | 
			
		||||
!<md> [10192, 0, null, null, -2147483648, -2147483648]
 | 
			
		||||
!<md> [10209, 0, null, null, -2147483648, -2147483648]
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										5
									
								
								.idea/workspace.xml
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										5
									
								
								.idea/workspace.xml
									
									
									
										generated
									
									
									
								
							@@ -4,7 +4,10 @@
 | 
			
		||||
    <option name="autoReloadType" value="ALL" />
 | 
			
		||||
  </component>
 | 
			
		||||
  <component name="ChangeListManager">
 | 
			
		||||
    <list default="true" id="3fefb2c4-b6f9-466b-a523-53352e8d6f95" name="更改" comment=":bug: Fix permissions in groups" />
 | 
			
		||||
    <list default="true" id="3fefb2c4-b6f9-466b-a523-53352e8d6f95" name="更改" comment=":bug: Fix permissions in groups">
 | 
			
		||||
      <change beforePath="$PROJECT_DIR$/.idea/dataSources/74bcf3ef-a2b9-435b-b9e5-f32902a33b25.xml" beforeDir="false" afterPath="$PROJECT_DIR$/.idea/dataSources/74bcf3ef-a2b9-435b-b9e5-f32902a33b25.xml" afterDir="false" />
 | 
			
		||||
      <change beforePath="$PROJECT_DIR$/.idea/dataSources/74bcf3ef-a2b9-435b-b9e5-f32902a33b25/storage_v2/_src_/database/hy_passport.gNOKQQ/schema/public.abK9xQ.meta" beforeDir="false" afterPath="$PROJECT_DIR$/.idea/dataSources/74bcf3ef-a2b9-435b-b9e5-f32902a33b25/storage_v2/_src_/database/hy_passport.gNOKQQ/schema/public.abK9xQ.meta" afterDir="false" />
 | 
			
		||||
    </list>
 | 
			
		||||
    <option name="SHOW_DIALOG" value="false" />
 | 
			
		||||
    <option name="HIGHLIGHT_CONFLICTS" value="true" />
 | 
			
		||||
    <option name="HIGHLIGHT_NON_ACTIVE_CHANGELIST" value="false" />
 | 
			
		||||
 
 | 
			
		||||
@@ -39,6 +39,7 @@ type AuthTicket struct {
 | 
			
		||||
	ExpiredAt           *time.Time                  `json:"expired_at"`
 | 
			
		||||
	AvailableAt         *time.Time                  `json:"available_at"`
 | 
			
		||||
	LastGrantAt         *time.Time                  `json:"last_grant_at"`
 | 
			
		||||
	Nonce               *string                     `json:"nonce"`
 | 
			
		||||
	ClientID            *uint                       `json:"client_id"`
 | 
			
		||||
	AccountID           uint                        `json:"account_id"`
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -1,10 +1,11 @@
 | 
			
		||||
package api
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"git.solsynth.dev/hydrogen/passport/pkg/internal/server/exts"
 | 
			
		||||
	"strings"
 | 
			
		||||
	"time"
 | 
			
		||||
 | 
			
		||||
	"git.solsynth.dev/hydrogen/passport/pkg/internal/server/exts"
 | 
			
		||||
 | 
			
		||||
	"git.solsynth.dev/hydrogen/passport/pkg/internal/database"
 | 
			
		||||
	"git.solsynth.dev/hydrogen/passport/pkg/internal/models"
 | 
			
		||||
	"git.solsynth.dev/hydrogen/passport/pkg/internal/services"
 | 
			
		||||
@@ -62,6 +63,7 @@ func authorizeThirdClient(c *fiber.Ctx) error {
 | 
			
		||||
	id := c.Query("client_id")
 | 
			
		||||
	response := c.Query("response_type")
 | 
			
		||||
	redirect := c.Query("redirect_uri")
 | 
			
		||||
	nonce := c.Query("nonce")
 | 
			
		||||
	scope := c.Query("scope")
 | 
			
		||||
	if len(scope) <= 0 {
 | 
			
		||||
		return fiber.NewError(fiber.StatusBadRequest, "invalid request params")
 | 
			
		||||
@@ -87,6 +89,7 @@ func authorizeThirdClient(c *fiber.Ctx) error {
 | 
			
		||||
			[]string{"passport", client.Alias},
 | 
			
		||||
			c.IP(),
 | 
			
		||||
			c.Get(fiber.HeaderUserAgent),
 | 
			
		||||
			&nonce,
 | 
			
		||||
		)
 | 
			
		||||
 | 
			
		||||
		if err != nil {
 | 
			
		||||
@@ -107,6 +110,7 @@ func authorizeThirdClient(c *fiber.Ctx) error {
 | 
			
		||||
			[]string{"passport", client.Alias},
 | 
			
		||||
			c.IP(),
 | 
			
		||||
			c.Get(fiber.HeaderUserAgent),
 | 
			
		||||
			&nonce,
 | 
			
		||||
		)
 | 
			
		||||
 | 
			
		||||
		if err != nil {
 | 
			
		||||
 
 | 
			
		||||
@@ -22,6 +22,7 @@ type PayloadClaims struct {
 | 
			
		||||
 | 
			
		||||
	// Additonal Stuff
 | 
			
		||||
	AuthorizedParties string `json:"azp,omitempty"`
 | 
			
		||||
	Nonce             string `json:"nonce,omitempty"`
 | 
			
		||||
	Type              string `json:"typ"`
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -30,7 +31,7 @@ const (
 | 
			
		||||
	JwtRefreshType = "refresh"
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
func EncodeJwt(id string, typ, sub, sed string, aud []string, exp time.Time, idTokenUser ...models.Account) (string, error) {
 | 
			
		||||
func EncodeJwt(id string, typ, sub, sed string, nonce *string, aud []string, exp time.Time, idTokenUser ...models.Account) (string, error) {
 | 
			
		||||
	var azp string
 | 
			
		||||
	for _, item := range aud {
 | 
			
		||||
		if item != InternalTokenAudience {
 | 
			
		||||
@@ -61,6 +62,10 @@ func EncodeJwt(id string, typ, sub, sed string, aud []string, exp time.Time, idT
 | 
			
		||||
		claims.Email = user.GetPrimaryEmail().Content
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if nonce != nil {
 | 
			
		||||
		claims.Nonce = *nonce
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	tk := jwt.NewWithClaims(jwt.SigningMethodHS512, claims)
 | 
			
		||||
 | 
			
		||||
	return tk.SignedString([]byte(viper.GetString("secret")))
 | 
			
		||||
 
 | 
			
		||||
@@ -62,8 +62,12 @@ func NewOauthTicket(
 | 
			
		||||
	user models.Account,
 | 
			
		||||
	client models.ThirdClient,
 | 
			
		||||
	claims, audiences []string,
 | 
			
		||||
	ip, ua string,
 | 
			
		||||
	ip, ua string, nonce *string,
 | 
			
		||||
) (models.AuthTicket, error) {
 | 
			
		||||
	if nonce != nil && len(*nonce) == 0 {
 | 
			
		||||
		nonce = nil
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	ticket := models.AuthTicket{
 | 
			
		||||
		Claims:       claims,
 | 
			
		||||
		Audiences:    audiences,
 | 
			
		||||
@@ -74,6 +78,7 @@ func NewOauthTicket(
 | 
			
		||||
		RefreshToken: lo.ToPtr(uuid.NewString()),
 | 
			
		||||
		AvailableAt:  lo.ToPtr(time.Now()),
 | 
			
		||||
		ExpiredAt:    lo.ToPtr(time.Now().Add(7 * 24 * time.Hour)),
 | 
			
		||||
		Nonce:        nonce,
 | 
			
		||||
		ClientID:     &client.ID,
 | 
			
		||||
		AccountID:    user.ID,
 | 
			
		||||
	}
 | 
			
		||||
 
 | 
			
		||||
@@ -25,11 +25,11 @@ func GetToken(ticket models.AuthTicket) (atk, rtk string, err error) {
 | 
			
		||||
 | 
			
		||||
	sub := strconv.Itoa(int(ticket.AccountID))
 | 
			
		||||
	sed := strconv.Itoa(int(ticket.ID))
 | 
			
		||||
	atk, err = EncodeJwt(*ticket.AccessToken, JwtAccessType, sub, sed, ticket.Audiences, time.Now().Add(atkDeadline))
 | 
			
		||||
	atk, err = EncodeJwt(*ticket.AccessToken, JwtAccessType, sub, sed, nil, ticket.Audiences, time.Now().Add(atkDeadline))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		return
 | 
			
		||||
	}
 | 
			
		||||
	rtk, err = EncodeJwt(*ticket.RefreshToken, JwtRefreshType, sub, sed, ticket.Audiences, time.Now().Add(rtkDeadline))
 | 
			
		||||
	rtk, err = EncodeJwt(*ticket.RefreshToken, JwtRefreshType, sub, sed, nil, ticket.Audiences, time.Now().Add(rtkDeadline))
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		return
 | 
			
		||||
	}
 | 
			
		||||
@@ -89,7 +89,7 @@ func ExchangeOauthToken(clientId, clientSecret, redirectUri, token string) (idk,
 | 
			
		||||
 | 
			
		||||
	sub := strconv.Itoa(int(ticket.AccountID))
 | 
			
		||||
	sed := strconv.Itoa(int(ticket.ID))
 | 
			
		||||
	idk, err = EncodeJwt(*ticket.AccessToken, JwtAccessType, sub, sed, ticket.Audiences, time.Now().Add(24*time.Minute), user)
 | 
			
		||||
	idk, err = EncodeJwt(*ticket.AccessToken, JwtAccessType, sub, sed, ticket.Nonce, ticket.Audiences, time.Now().Add(24*time.Minute), user)
 | 
			
		||||
 | 
			
		||||
	return
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -107,7 +107,7 @@ const requestedClaims = computed(() => {
 | 
			
		||||
const panel = ref("confirm")
 | 
			
		||||
 | 
			
		||||
async function tryAuthorize() {
 | 
			
		||||
  const res = await request(`/api/auth/o/authorize${location.search}`, {
 | 
			
		||||
  const res = await request("/api/auth/o/authorize" + window.location.search, {
 | 
			
		||||
    headers: { Authorization: `Bearer ${getAtk()}` },
 | 
			
		||||
  })
 | 
			
		||||
 | 
			
		||||
@@ -139,19 +139,10 @@ function decline() {
 | 
			
		||||
 | 
			
		||||
async function approve() {
 | 
			
		||||
  loading.value = true
 | 
			
		||||
  const res = await request(
 | 
			
		||||
    "/api/auth/o/authorize?" +
 | 
			
		||||
    new URLSearchParams({
 | 
			
		||||
      client_id: route.query["client_id"] as string,
 | 
			
		||||
      redirect_uri: encodeURIComponent(route.query["redirect_uri"] as string),
 | 
			
		||||
      response_type: "code",
 | 
			
		||||
      scope: route.query["scope"] as string,
 | 
			
		||||
    }),
 | 
			
		||||
    {
 | 
			
		||||
      method: "POST",
 | 
			
		||||
      headers: { Authorization: `Bearer ${getAtk()}` },
 | 
			
		||||
    },
 | 
			
		||||
  )
 | 
			
		||||
  const res = await request("/api/auth/o/authorize" + window.location.search, {
 | 
			
		||||
    method: "POST",
 | 
			
		||||
    headers: { Authorization: `Bearer ${getAtk()}` },
 | 
			
		||||
  })
 | 
			
		||||
 | 
			
		||||
  if (res.status !== 200) {
 | 
			
		||||
    error.value = await res.text()
 | 
			
		||||
@@ -169,11 +160,13 @@ function callback(ticket: any) {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function getClaimDescription(key: string): ClaimType {
 | 
			
		||||
  return Object.prototype.hasOwnProperty.call(claims, key) ? claims[key] : {
 | 
			
		||||
    icon: "mdi-asterisk",
 | 
			
		||||
    name: key,
 | 
			
		||||
    description: "Unknown claim...",
 | 
			
		||||
  }
 | 
			
		||||
  return Object.prototype.hasOwnProperty.call(claims, key)
 | 
			
		||||
    ? claims[key]
 | 
			
		||||
    : {
 | 
			
		||||
        icon: "mdi-asterisk",
 | 
			
		||||
        name: key,
 | 
			
		||||
        description: "Unknown claim...",
 | 
			
		||||
      }
 | 
			
		||||
}
 | 
			
		||||
</script>
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user