mirror of
https://github.com/outbackdingo/firezone.git
synced 2026-01-27 18:18:55 +00:00
fix(portal): Verify email token identity (#4977)
This commit is contained in:
@@ -100,18 +100,25 @@ defmodule Domain.Auth.Adapters.Email do
|
||||
|
||||
@impl true
|
||||
def verify_secret(%Identity{} = identity, %Context{} = context, encoded_token) do
|
||||
with {:ok, token} <- Tokens.use_token(encoded_token, %{context | type: :email}) do
|
||||
with {:ok, token} <- Tokens.use_token(encoded_token, %{context | type: :email}),
|
||||
true <- token.identity_id == identity.id do
|
||||
{:ok, identity} =
|
||||
Identity.Changeset.update_identity_provider_state(identity, %{
|
||||
last_used_token_id: token.id
|
||||
})
|
||||
|> Repo.update()
|
||||
Identity.Query.not_disabled()
|
||||
|> Identity.Query.by_id(identity.id)
|
||||
|> Repo.fetch_and_update(Identity.Query,
|
||||
with: fn identity ->
|
||||
Identity.Changeset.update_identity_provider_state(identity, %{
|
||||
last_used_token_id: token.id
|
||||
})
|
||||
end
|
||||
)
|
||||
|
||||
{:ok, _count} = Tokens.delete_all_tokens_by_type_and_assoc(:email, identity)
|
||||
|
||||
{:ok, identity, nil}
|
||||
else
|
||||
{:error, :invalid_or_expired_token} -> {:error, :invalid_secret}
|
||||
false -> {:error, :invalid_secret}
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -176,6 +176,22 @@ defmodule Domain.Auth.Adapters.EmailTest do
|
||||
assert token.deleted_at
|
||||
end
|
||||
|
||||
test "returns error when token belongs to a different identity", %{
|
||||
account: account,
|
||||
provider: provider,
|
||||
identity: identity,
|
||||
context: context
|
||||
} do
|
||||
other_identity = Fixtures.Auth.create_identity(account: account, provider: provider)
|
||||
{:ok, other_identity} = request_sign_in_token(other_identity, context)
|
||||
|
||||
nonce = other_identity.provider_virtual_state.nonce
|
||||
fragment = other_identity.provider_virtual_state.fragment
|
||||
token = nonce <> fragment
|
||||
|
||||
assert verify_secret(identity, context, token) == {:error, :invalid_secret}
|
||||
end
|
||||
|
||||
test "returns error when token is expired", %{
|
||||
context: context,
|
||||
identity: identity,
|
||||
|
||||
@@ -2989,6 +2989,26 @@ defmodule Domain.AuthTest do
|
||||
{:error, :unauthorized}
|
||||
end
|
||||
|
||||
test "returns error when secret belongs to a different identity invalid", %{
|
||||
account: account,
|
||||
provider: provider,
|
||||
user_agent: user_agent,
|
||||
remote_ip: remote_ip
|
||||
} do
|
||||
nonce = "test_nonce_for_firezone"
|
||||
context = %Auth.Context{type: :browser, user_agent: user_agent, remote_ip: remote_ip}
|
||||
|
||||
identity = Fixtures.Auth.create_identity(account: account, provider: provider)
|
||||
{:ok, identity} = Domain.Auth.Adapters.Email.request_sign_in_token(identity, context)
|
||||
|
||||
identity2 = Fixtures.Auth.create_identity(account: account, provider: provider)
|
||||
{:ok, identity2} = Domain.Auth.Adapters.Email.request_sign_in_token(identity2, context)
|
||||
secret = identity2.provider_virtual_state.nonce <> identity2.provider_virtual_state.fragment
|
||||
|
||||
assert sign_in(provider, identity.provider_identifier, nonce, secret, context) ==
|
||||
{:error, :unauthorized}
|
||||
end
|
||||
|
||||
test "returns error when nonce is invalid", %{
|
||||
account: account,
|
||||
provider: provider,
|
||||
|
||||
@@ -1,11 +1,13 @@
|
||||
defmodule Firezone.MixProject do
|
||||
use Mix.Project
|
||||
|
||||
@version "VERSION" |> File.read!() |> String.trim()
|
||||
|
||||
def project do
|
||||
[
|
||||
name: :firezone,
|
||||
apps_path: "apps",
|
||||
version: String.trim(File.read!("VERSION")),
|
||||
version: @version,
|
||||
start_permanent: Mix.env() == :prod,
|
||||
test_coverage: [tool: ExCoveralls],
|
||||
preferred_cli_env: [
|
||||
|
||||
Reference in New Issue
Block a user