Packages
nous
0.15.4
0.17.0
0.16.6
0.16.5
0.16.4
0.16.3
0.16.2
0.16.1
0.16.0
0.15.8
0.15.7
0.15.6
0.15.5
0.15.4
0.15.3
0.15.2
0.15.1
0.15.0
0.14.3
0.14.2
0.14.1
0.14.0
0.13.3
0.13.2
0.13.1
0.13.0
0.12.17
0.12.16
0.12.15
0.12.14
0.12.13
0.12.12
0.12.11
0.12.9
0.12.7
0.12.6
0.12.5
0.12.3
0.12.2
0.12.0
0.11.3
0.11.0
0.10.1
0.10.0
0.9.0
0.8.1
0.8.0
0.7.2
0.7.1
0.7.0
0.5.0
AI agent framework for Elixir with multi-provider LLM support
Current section
Files
Jump to
Current section
Files
lib/nous/tools/file_glob.ex
defmodule Nous.Tools.FileGlob do
@moduledoc """
File pattern matching tool.
Finds files matching glob patterns using `Path.wildcard/2`.
Results are sorted by modification time (most recent first).
"""
@behaviour Nous.Tool.Behaviour
@default_limit 200
@impl true
def metadata do
%{
name: "file_glob",
description: "Find files matching a glob pattern (e.g. \"**/*.ex\", \"lib/**/*.exs\").",
category: :search,
requires_approval: false,
parameters: %{
"type" => "object",
"properties" => %{
"pattern" => %{
"type" => "string",
"description" => "Glob pattern to match files (e.g. \"**/*.ex\")"
},
"path" => %{
"type" => "string",
"description" => "Base directory to search from. Defaults to current directory."
}
},
"required" => ["pattern"]
}
}
end
@impl true
def execute(ctx, %{"pattern" => pattern} = args) do
base = Map.get(args, "path", ".")
case Nous.Tools.PathGuard.validate(base, ctx) do
{:ok, safe_base} ->
full_pattern = Path.join(safe_base, pattern)
files =
full_pattern
|> Path.wildcard(match_dot: false)
# Keep regular files inside the workspace (rejects directories,
# special files, and matches that escaped the workspace via symlink).
|> Enum.filter(fn f ->
File.regular?(f) and match?({:ok, _}, Nous.Tools.PathGuard.validate(f, ctx))
end)
|> sort_by_mtime()
|> Enum.take(@default_limit)
if files == [] do
{:ok, "No files matched pattern: #{pattern}"}
else
{:ok, Enum.join(files, "\n")}
end
{:error, reason} ->
{:error, reason}
end
end
defp sort_by_mtime(files) do
Enum.sort_by(files, fn file ->
case File.stat(file, time: :posix) do
{:ok, %{mtime: mtime}} -> -mtime
_ -> 0
end
end)
end
end