How to handle paths for exclusion within a custom Plug

good day folks !

I’m writing a small custom plug with plain elixir and I’m with a small pickle I’m not sure how to tackle. Turns I have could have a small Router that might look as follows:

defmodule MyRouter do
  use Plug.Router
  
  plug(:match)
  plug(MyCustomPlug, excluded: ["my/namespace/internal"])
  plug(:dispatch)

  get "/hello", do: send_resp(conn, 200, "world")
  forward("my/namespace", to: AnotherRouter)
end

and my custom plug as this:

defmodule MyCustomPlug do
  use Plug.Builder

  def call(%Plug.Conn{} = conn, opts) do
    excluded_paths = Keyword.get(opts, :excluded, [])
    if ~c(what should I check here to exclude?), do: halt(conn), else: conn
  end
end

as you can see, I’m enabling the plug via options to set an exclusion list, where if it’s included, just halt the pipeline.

My problem? I’m not sure what should I check to make sure the path `conn` is seeing is included in the excluded path.

am I making this more complicated than expected?

There’s conn.path_info being a list of all the path segments. Either split your full path to compare or join the segments to a full path.

but that path info is the raw one, no? so if I have something like `/my/namespace/:user` or `/:user` I need to double parse it, basically?

Basically, I want to do something like this in any router:

plug(MyCustomPlug, excluded: ["/:users", "/another-path"])

and it gracefully detects if it’s within a forward or not and exclude when it arrives.

Those wildcards are not something the conn deals with. That’s a plain router concern for matching and if you want to include based on it you’d need to implement that on your own or reuse what routers might make public. Though at least the Phoenix.Router compiles to binary pattern matches, so there’s no good way to reuse that.