Security changes in v0.10
View SourceThis release introduces a small but important, and breaking, change to how Oaskit handles security. The goal is to make it easier to build “secure by default” setups when you opt into a security plug.
Summary
Oaskit.Plugs.ValidateRequestnow always calls the configured:securityplug (when present), even if the OpenAPI operation has no security requirements (security: nil).- This only affects projects that have configured a
:securityplug.
Previous behaviour
Before v0.10:
- If an operation had no
securitydefined and there was no global security requirement,ValidateRequestwould not run any security logic for that route. - Forgetting to add
securityto an operation could therefore leave an endpoint unintentionally open.
New behaviour
From v0.10:
- As soon as you configure a security plug on
ValidateRequest, it will run on every request handled with that plug. - When an operation has no security defined, the plug receives
nilas the:securityoption and can decide how to handle it.
Deny-by-default with a security plug
One common use case is to treat “no security defined” as “deny access unless explicitly marked as public”.
Here’s a simple example of rejecting any route that hasn’t been explicitly marked as public:
defmodule MyApp.SecurityPlug do
@behaviour Plug
@impl true
def init(opts), do: opts
@impl true
def call(conn, opts) do
case Keyword.fetch!(opts, :security) do
nil ->
conn
|> Conn.send_resp(401, "unauthorized")
|> Conn.halt()
requirements ->
validate_requirements(conn, requirements)
end
end
defp validate_requirements(conn, requirements) do
# your auth logic here
end
endYou can invert that logic (treat nil as public, and only enforce checks when
requirements are present) if that better matches your application.
Backwards-compatibility
- If you don’t configure a
:securityplug in yourValidateRequestoptions, behaviour is unchanged: routes without security definitions remain accessible. - The new behaviour only applies once a security plug is configured, at which point it is invoked for every request.