Ragex.Editor.Refactor.Elixir
(Ragex v0.10.1)
View Source
Elixir-specific AST manipulation for semantic refactoring.
Provides functions to rename functions and modules by parsing and transforming Elixir AST, preserving comments and formatting where possible.
Summary
Functions
Changes a function signature by adding, removing, reordering, or renaming parameters.
Converts function visibility between public (def) and private (defp).
Extracts a range of lines from a function into a new function.
Extracts multiple functions from a module into a new module.
Finds all function calls to a specific function in the AST.
Inlines a function by replacing all its calls with the function body.
Adds, removes, or updates module attributes.
Moves a function from one module to another.
Renames a function definition and all its calls within a source file.
Renames a module and all references to it.
Renames a function parameter and all its references within the function body.
Functions
@spec change_signature( String.t(), atom(), atom(), non_neg_integer(), map(), keyword() ) :: {:ok, String.t()} | {:error, term()}
Changes a function signature by adding, removing, reordering, or renaming parameters.
Parameters
content: Source code as stringmodule_name: Module containing the functionfunction_name: Function to modifyold_arity: Current function aritysignature_changes: Map describing the changesopts: Options (currently unused)
Signature Changes Format
The signature_changes map can contain:
:add_params- List of params to add:[%{name: atom, position: integer, default: any}]:remove_params- List of param positions to remove (0-indexed):[0, 2]:reorder_params- New param order (0-indexed positions):[2, 0, 1]:rename_params- List of renames:[{old_name, new_name}]
Returns
{:ok, new_content}on success{:error, reason}on failure
Examples
# Add a parameter with default value
changes = %{add_params: [%{name: :opts, position: 2, default: []}]}
change_signature(content, :MyModule, :process, 2, changes)
# Remove second parameter (position 1)
changes = %{remove_params: [1]}
change_signature(content, :MyModule, :calculate, 3, changes)
# Reorder parameters: swap first and second
changes = %{reorder_params: [1, 0, 2]}
change_signature(content, :MyModule, :transform, 3, changes)
# Rename parameters
changes = %{rename_params: [{:x, :input}, {:y, :output}]}
change_signature(content, :MyModule, :convert, 2, changes)
# Combine multiple operations
changes = %{
add_params: [%{name: :config, position: 0, default: %{}}],
remove_params: [2],
rename_params: [{:data, :payload}]
}
change_signature(content, :MyModule, :handler, 3, changes)
@spec convert_visibility( String.t(), atom(), atom(), non_neg_integer(), :public | :private, keyword() ) :: {:ok, String.t()} | {:error, term()}
Converts function visibility between public (def) and private (defp).
Parameters
content: Source code as stringmodule_name: Module containing the functionfunction_name: Function to modifyarity: Function arityvisibility: :public or :privateopts: Options:add_doc- Add documentation when making public (default: false)
Returns
{:ok, new_content}on success{:error, reason}on failure
@spec extract_function( String.t(), atom(), atom(), non_neg_integer(), atom(), {pos_integer(), pos_integer()}, keyword() ) :: {:ok, String.t()} | {:error, term()}
Extracts a range of lines from a function into a new function.
Parameters
content: Source code as stringmodule_name: Module containing the functionsource_function: Function to extract fromsource_arity: Arity of source functionnew_function_name: Name for the extracted functionline_range: {start_line, end_line} tuple (1-indexed)opts: Options:placement- :after_source | :before_source | :end_of_module (default: :after_source):visibility- :public | :private (default: :private):add_doc- boolean (default: false)
Returns
{:ok, new_content}on success{:error, reason}on failure
@spec extract_module( String.t(), atom(), atom(), [{atom(), non_neg_integer()}], keyword() ) :: {:ok, %{source: String.t(), target: String.t()}} | {:error, term()}
Extracts multiple functions from a module into a new module.
Parameters
source_content: Source module codesource_module: Source module namenew_module: New module namefunctions: List of {function_name, arity} tuples to extractopts: Options:add_moduledoc- boolean (default: true):update_aliases- boolean (default: true)
Returns
{:ok, %{source: new_source, target: new_module_content}}on success{:error, reason}on failure
Examples
functions = [{:helper, 1}, {:process, 2}]
extract_module(content, :MyModule, :MyModule.Helpers, functions)
@spec find_function_calls(String.t(), atom() | String.t(), non_neg_integer() | nil) :: {:ok, [non_neg_integer()]} | {:error, term()}
Finds all function calls to a specific function in the AST.
Returns a list of line numbers where the function is called.
@spec inline_function( String.t(), atom(), atom(), non_neg_integer(), keyword() ) :: {:ok, String.t()} | {:error, term()}
Inlines a function by replacing all its calls with the function body.
Parameters
content: Source code as stringmodule_name: Module containing the functionfunction_name: Function to inlinearity: Function arityopts: Options:remove_definition- Remove function definition after inlining (default: true)
Returns
{:ok, new_content}on success{:error, reason}on failure
Examples
iex> content = """
...> defmodule Test do
...> defp helper(x), do: x * 2
...> def main(a), do: helper(a) + 1
...> end
...> """
iex> Elixir.inline_function(content, :Test, :helper, 1)
{:ok, "defmodule Test dodef main(a), do: a * 2 + 1 end"}
@spec modify_attributes(String.t(), atom(), list(), keyword()) :: {:ok, String.t()} | {:error, term()}
Adds, removes, or updates module attributes.
Parameters
content: Source code as stringmodule_name: Module to modify (currently unused, modifies all modules)changes: List of change tuples:{:add, attribute_name, value}- Add new attribute{:remove, attribute_name}- Remove attribute{:update, attribute_name, new_value}- Update existing attribute
opts: Options (currently unused)
Returns
{:ok, new_content}on success{:error, reason}on failure
Examples
iex> changes = [
...> {:add, :vsn, "1.0.0"},
...> {:remove, :deprecated},
...> {:update, :moduledoc, "Updated documentation"}
...> ]
iex> modify_attributes(content, :MyModule, changes)
{:ok, updated_content}
@spec move_function( String.t(), String.t() | nil, atom(), atom(), atom(), non_neg_integer(), keyword() ) :: {:ok, %{source: String.t(), target: String.t()}} | {:error, term()}
Moves a function from one module to another.
Parameters
source_content: Source module codetarget_content: Target module code (or nil for new module)source_module: Source module nametarget_module: Target module namefunction_name: Function to movearity: Function arityopts: Options:placement- :start | :end (default: :end):update_references- boolean (default: true)
Returns
{:ok, %{source: new_source, target: new_target}}on success{:error, reason}on failure
@spec rename_function( String.t(), atom() | String.t(), atom() | String.t(), non_neg_integer() | nil ) :: {:ok, String.t()} | {:error, term()}
Renames a function definition and all its calls within a source file.
Parameters
content: Source code as stringold_name: Current function name (atom or string)new_name: New function name (atom or string)arity: Function arity (nil to rename all arities)
Returns
{:ok, new_content}on success{:error, reason}on failure
Examples
iex> content = "def old_func(x), do: x + 1"
iex> Elixir.rename_function(content, :old_func, :new_func, 1)
{:ok, "def new_func(x), do: x + 1"}
@spec rename_module(String.t(), atom() | String.t(), atom() | String.t()) :: {:ok, String.t()} | {:error, term()}
Renames a module and all references to it.
Parameters
content: Source code as stringold_name: Current module name (atom or string)new_name: New module name (atom or string)
Returns
{:ok, new_content}on success{:error, reason}on failure
@spec rename_parameter( String.t(), atom(), atom(), non_neg_integer(), atom(), atom(), keyword() ) :: {:ok, String.t()} | {:error, term()}
Renames a function parameter and all its references within the function body.
Parameters
content: Source code as stringmodule_name: Module containing the functionfunction_name: Function to modifyarity: Function arityold_param_name: Current parameter namenew_param_name: New parameter nameopts: Options (currently unused)
Returns
{:ok, new_content}on success{:error, reason}on failure