Packages
fnord
0.8.41
0.9.40
0.9.39
0.9.38
0.9.37
0.9.36
0.9.35
0.9.34
0.9.33
0.9.32
0.9.31
0.9.30
0.9.29
0.9.28
0.9.27
0.9.26
0.9.25
0.9.24
0.9.23
0.9.22
0.9.21
0.9.20
0.9.19
0.9.18
0.9.17
0.9.16
0.9.15
0.9.14
0.9.13
0.9.12
0.9.11
0.9.10
0.9.9
0.9.8
0.9.7
0.9.6
0.9.5
0.9.4
0.9.3
0.9.2
0.9.1
0.9.0
0.8.99
0.8.98
0.8.97
0.8.96
0.8.95
0.8.94
0.8.93
0.8.92
0.8.91
0.8.90
0.8.89
0.8.88
0.8.87
0.8.86
0.8.85
0.8.84
0.8.83
0.8.82
0.8.81
0.8.80
0.8.79
0.8.78
0.8.77
0.8.76
0.8.75
0.8.74
0.8.73
0.8.72
0.8.71
0.8.70
0.8.69
0.8.68
0.8.67
0.8.66
0.8.65
0.8.64
0.8.63
0.8.62
0.8.61
0.8.60
0.8.59
0.8.58
0.8.57
0.8.56
0.8.55
0.8.54
0.8.53
0.8.52
0.8.51
0.8.50
0.8.49
0.8.48
0.8.47
0.8.46
0.8.45
0.8.44
0.8.43
0.8.42
0.8.41
0.8.40
0.8.39
0.8.38
0.8.37
0.8.36
0.8.35
0.8.34
0.8.33
0.8.32
0.8.31
0.8.30
0.8.29
0.8.27
0.8.26
0.8.25
0.8.24
0.8.23
0.8.22
0.8.21
0.8.20
0.8.19
0.8.18
0.8.17
0.8.16
0.8.15
0.8.14
0.8.13
0.8.12
0.8.11
0.8.1
0.8.0
0.7.24
0.7.23
0.7.22
0.7.21
0.7.20
0.7.19
0.7.18
0.7.17
0.7.16
0.7.15
0.7.14
0.7.13
0.7.12
0.7.11
0.7.10
0.7.9
0.7.8
0.7.7
0.7.6
0.7.5
0.7.3
0.7.2
0.7.1
0.7.0
0.6.9
0.6.8
0.6.7
0.6.6
0.6.5
0.6.4
0.6.3
0.6.1
0.6.0
0.5.9
0.5.8
0.5.7
0.5.6
0.5.5
0.5.4
0.5.3
0.5.2
0.5.1
0.5.0
0.4.44
0.4.43
0.4.42
0.4.41
0.4.40
0.4.39
0.4.38
0.4.37
0.4.36
0.4.35
0.4.34
0.4.33
0.4.32
0.4.30
0.4.29
0.4.28
0.4.27
0.4.26
0.4.25
0.4.24
0.4.23
0.4.22
0.4.21
0.4.20
0.4.19
0.4.18
0.4.17
0.4.16
0.4.15
0.4.14
0.4.13
0.4.12
0.4.11
0.4.10
0.4.9
0.4.8
0.4.7
0.4.6
0.4.5
0.4.4
0.4.3
0.4.2
0.4.1
0.4.0
0.3.0
0.2.0
0.1.0
AI code archaeology
Current section
Files
Jump to
Current section
Files
lib/cmd/config.ex
defmodule Cmd.Config do
@behaviour Cmd
@impl Cmd
def requires_project?(), do: false
@impl Cmd
def spec do
[
config: [
name: "config",
about: "Manage configuration settings",
subcommands: [
list: [
name: "list",
about: "List configuration settings (global or project-specific)",
options: [
project: Cmd.project_arg()
]
],
set: [
name: "set",
about: "Set a configuration directive for a project",
options: [
project: Cmd.project_arg(),
root: [
value_name: "ROOT",
long: "--root",
short: "-r",
help: "Root directory for the project",
required: false
],
exclude: [
value_name: "EXCLUDE",
long: "--exclude",
short: "-x",
help: "Exclude files from the project",
required: false,
multiple: true
]
]
],
approvals: [
name: "approvals",
about: "List approval patterns (global or project)",
options: [
project: Cmd.project_arg()
],
flags: [
global: [
long: "--global",
short: "-g",
help: "Use global approvals",
required: false
]
]
],
approve: [
name: "approve",
about: "Add an approval regex under a kind (scope: global|project)",
args: [
pattern: [
value_name: "PATTERN",
help: "Regex to approve",
required: true
]
],
options: [
project: Cmd.project_arg(),
kind: [
value_name: "KIND",
long: "--kind",
short: "-k",
help: "Approval kind",
required: true
]
],
flags: [
global: [
long: "--global",
short: "-g",
help: "Add to global scope. If not set, new patterns are added to project scope.",
required: false
]
]
],
mcp: [
name: "mcp",
about: "Manage MCP server configuration",
subcommands: [
list: [
name: "list",
about: "List MCP config (global, project, or effective merge)",
options: [
project: Cmd.project_arg()
],
flags: [
global: [
long: "--global",
short: "-g",
help: "Use global scope",
required: false
],
effective: [
long: "--effective",
short: "-e",
help: "Show merged effective config",
required: false
]
]
],
add: [
name: "add",
about: "Add an MCP server (global or project)",
args: [
name: [value_name: "NAME", help: "Server identifier", required: true]
],
options: [
project: Cmd.project_arg(),
transport: [
value_name: "TRANSPORT",
long: "--transport",
short: "-t",
help: "Transport type (stdio|streamable_http|websocket)",
default: "stdio"
],
command: [
value_name: "CMD",
long: "--command",
short: "-c",
help: "Command for stdio transport",
required: false
],
arg: [
value_name: "ARG",
long: "--arg",
short: "-a",
help: "Argument for stdio transport (repeatable)",
required: false,
multiple: true
],
base_url: [
value_name: "URL",
long: "--base-url",
short: "-u",
help: "Base URL for HTTP/WebSocket transports",
required: false
],
header: [
value_name: "HEADER",
long: "--header",
short: "-h",
help: "Header for HTTP/WebSocket transports (KEY=VALUE, repeatable)",
required: false,
multiple: true
],
env: [
value_name: "ENV",
long: "--env",
short: "-e",
help: "Environment variable for stdio transport (KEY=VALUE, repeatable)",
required: false,
multiple: true
],
timeout_ms: [
value_name: "MS",
long: "--timeout-ms",
short: "-T",
help: "Timeout in milliseconds",
required: false
]
],
flags: [
global: [
long: "--global",
short: "-g",
help: "Add server to global configuration",
required: false
]
]
],
update: [
name: "update",
about: "Update an MCP server configuration",
args: [
name: [value_name: "NAME", help: "Server identifier", required: true]
],
options: [
project: Cmd.project_arg(),
transport: [
value_name: "TRANSPORT",
long: "--transport",
short: "-t",
help: "Transport type (stdio|streamable_http|websocket)",
default: "stdio"
],
command: [
value_name: "CMD",
long: "--command",
short: "-c",
help: "Command for stdio transport",
required: false
],
arg: [
value_name: "ARG",
long: "--arg",
short: "-a",
help: "Argument for stdio transport (repeatable)",
required: false,
multiple: true
],
base_url: [
value_name: "URL",
long: "--base-url",
short: "-u",
help: "Base URL for HTTP/WebSocket transports",
required: false
],
header: [
value_name: "HEADER",
long: "--header",
short: "-h",
help: "Header for HTTP/WebSocket transports (KEY=VALUE, repeatable)",
required: false,
multiple: true
],
env: [
value_name: "ENV",
long: "--env",
short: "-e",
help: "Environment variable for stdio transport (KEY=VALUE, repeatable)",
required: false,
multiple: true
],
timeout_ms: [
value_name: "MS",
long: "--timeout-ms",
short: "-T",
help: "Timeout in milliseconds",
required: false
]
],
flags: [
global: [
long: "--global",
short: "-g",
help: "Update server in global configuration",
required: false
]
]
],
remove: [
name: "remove",
about: "Remove an MCP server (global or project)",
args: [
name: [value_name: "NAME", help: "Server identifier", required: true]
],
options: [
project: Cmd.project_arg()
],
flags: [
global: [
long: "--global",
short: "-g",
help: "Remove server from global configuration",
required: false
]
]
],
check: [
name: "check",
about: "Validate configured MCP servers and show discovered tools",
options: [
project: Cmd.project_arg()
],
flags: [
global: [
long: "--global",
short: "-g",
help: "Use global scope",
required: false
]
]
]
]
]
]
]
]
end
@impl Cmd
def run(_opts, [:list], _unknown) do
settings = Settings.new()
global = %{
"approvals" => Settings.Approvals.get_approvals(settings, :global)
}
with {:ok, project} <- Store.get_project() do
case Settings.get_project_data(settings, project.name) do
nil ->
UI.error("Project not found")
config ->
global
|> Map.merge(config)
|> Jason.encode!(pretty: true)
|> IO.puts()
end
else
{:error, _} -> UI.error("Project not found")
end
end
def run(opts, [:set], _unknown) do
case opts[:project] do
nil ->
UI.error("Project option is required for set command. Use --project PROJECT_NAME.")
project_name ->
Settings.set_project(project_name)
with {:ok, project} <- Store.get_project() do
if !Store.Project.exists_in_store?(project) do
UI.error("""
Project '#{project.name}' does not exist.
Please create it with: `fnord index`
""")
else
Store.Project.save_settings(project, opts[:root], opts[:exclude])
run(opts, [:list], [])
end
else
{:error, _} -> UI.error("Project not found")
end
end
end
@impl Cmd
def run(opts, [:approvals], args), do: Cmd.Config.Approvals.run(opts, [:approvals], args)
def run(opts, [:approve], args), do: Cmd.Config.Approvals.run(opts, [:approve], args)
def run(opts, [:mcp, :list], args), do: Cmd.Config.MCP.run(opts, [:mcp, :list], args)
def run(opts, [:mcp, :add], args), do: Cmd.Config.MCP.run(opts, [:mcp, :add], args)
def run(opts, [:mcp, :update], args), do: Cmd.Config.MCP.run(opts, [:mcp, :update], args)
def run(opts, [:mcp, :remove], args), do: Cmd.Config.MCP.run(opts, [:mcp, :remove], args)
def run(opts, [:mcp, :check], args), do: Cmd.Config.MCP.run(opts, [:mcp, :check], args)
def run(_opts, [], _unknown) do
UI.error("No subcommand specified. Use 'fnord help config' for help.")
end
def run(_opts, _subcommands, _unknown) do
UI.error("Unknown subcommand. Use 'fnord help config' for help.")
end
end