Uh oh!
There was an error while loading.Please reload this page.
- Notifications
You must be signed in to change notification settings - Fork105
The Refactoring library based off the Refactoring book by Martin Fowler
License
ThePrimeagen/refactoring.nvim
Folders and files
| Name | Name | Last commit message | Last commit date | |
|---|---|---|---|---|
Repository files navigation
- Installation
- Features
- Configuration
- Neovim 0.10
- Treesitter
- Plenary
use {"ThePrimeagen/refactoring.nvim",requires= { {"nvim-lua/plenary.nvim"}, {"nvim-treesitter/nvim-treesitter"} }}
{"ThePrimeagen/refactoring.nvim",dependencies= {"nvim-lua/plenary.nvim","nvim-treesitter/nvim-treesitter", },lazy=false,opts= {}, },require('refactoring').setup()
Given that this is a work in progress, the languages supported for theoperations listed below isconstantly changing. As of now, these languagesare supported (with individual support for each function may vary):
- TypeScript
- JavaScript
- Lua
- C/C++
- Golang
- Python
- Java
- PHP
- Ruby
- C#
- Vimscript (only debugging features)
- Powershell (only debugging features)
- Support for various common refactoring operations
- 106: Extract Function
- Extracts the last highlighted code from visual mode to a separate function
- Optionally prompts for function param types and return types (seeconfiguration for type prompt operations)
- Also possible to Extract Block.
- Both Extract Function and Extract Block have the capability to extract toa separate file.
- 115: Inline Function
- Inverse of extract function
- In normal mode, inline occurrences of the function under the cursor
- The function under the cursor has to be the declaration of the function
- 119: Extract Variable
- In visual mode, extracts occurrences of a selected expression to its ownvariable, replacing occurrences of that expression with the variable
- 123: Inline Variable
- Inverse of extract variable
- Replaces all occurrences of a variable with its value
- Can be used in normal mode or visual mode
- Using this function in normal mode will automatically find the variableunder the cursor and inline it
- Using this function in visual mode will find the variable(s) in thevisual selection.
- If there is more than one variable in the selection, the plugin willprompt for which variable to inline,
- If there is only one variable in the visual selection, it willautomatically inline that variable
- 106: Extract Function
- Also comes with various useful features for debugging
- Printf: Automated insertion of print statement to mark the calling of afunction
- dot-repeatable
- Print var: Automated insertion of print statement to print a variableat a given point in the code. This map can be made with either visual ornormal mode:
- Using this function in visual mode will print out whatever is in thevisual selection.
- Using this function in normal mode will print out the identifierunder the cursor
- dot-repeatable
- Cleanup: Automated cleanup of all print statements generated by theplugin
- Printf: Automated insertion of print statement to mark the calling of afunction
There are many ways to configure this plugin. Below are some example configurations.
Setup Function
No matter which configuration option you use, you must first call thesetup function.
require('refactoring').setup({})
Here are all the available options for the setup function and their defaults:
require('refactoring').setup({prompt_func_return_type= {go=false,java=false,cpp=false,c=false,h=false,hpp=false,cxx=false, },prompt_func_param_type= {go=false,java=false,cpp=false,c=false,h=false,hpp=false,cxx=false, },printf_statements= {},print_var_statements= {},show_success_message=false,-- shows a message with information about the refactor on success-- i.e. [Refactor] Inlined 3 variable occurrences})
See each of the sections below for details on each configuration option.
The plugin offers the:Refactor command as an alternative to the Lua API.
The first argument to the command selects the type of refactor to perform.Additional arguments will be passed to each refactor if needed (e.g. the nameof the extracted function forextract).
The first argument can be tab completed, so there is no need to memorize them all.(e.g.:Refactor e<tab> will suggestextract_block_to_file,extract,extract_block,extract_var andextract_to_file).
The main advantage of using an Ex command instead of the Lua API is that youwill be able to preview the changes made by the refactor before committing tothem.
command_showcase.mp4
The command can also be used in mappings:
vim.keymap.set("x","<leader>re",":Refactor extract")vim.keymap.set("x","<leader>rf",":Refactor extract_to_file")vim.keymap.set("x","<leader>rv",":Refactor extract_var")vim.keymap.set({"n","x"},"<leader>ri",":Refactor inline_var")vim.keymap.set("n","<leader>rI",":Refactor inline_func")vim.keymap.set("n","<leader>rb",":Refactor extract_block")vim.keymap.set("n","<leader>rbf",":Refactor extract_block_to_file")
The (space) at the end of some mappings is intentional because thosemappings expect an additional argument (all of these mappings leave the user incommand mode to utilize the preview command feature).
If you want to make remaps for a specific refactoring operation, you can do soby configuring the plugin like this:
vim.keymap.set({"n","x"},"<leader>re",function()returnrequire('refactoring').refactor('Extract Function')end, {expr=true })vim.keymap.set({"n","x"},"<leader>rf",function()returnrequire('refactoring').refactor('Extract Function To File')end, {expr=true })vim.keymap.set({"n","x"},"<leader>rv",function()returnrequire('refactoring').refactor('Extract Variable')end, {expr=true })vim.keymap.set({"n","x"},"<leader>rI",function()returnrequire('refactoring').refactor('Inline Function')end, {expr=true })vim.keymap.set({"n","x"},"<leader>ri",function()returnrequire('refactoring').refactor('Inline Variable')end, {expr=true })vim.keymap.set({"n","x"},"<leader>rbb",function()returnrequire('refactoring').refactor('Extract Block')end, {expr=true })vim.keymap.set({"n","x"},"<leader>rbf",function()returnrequire('refactoring').refactor('Extract Block To File')end, {expr=true })
IMPORTANT: the keymapsMUST to be created using the{ expr = true } option and return the value of therequire('refactoring').refactor function (like in the example above).
You can also set up the plugin to prompt for a refactoring operation to applyusing Neovim's built in selection API (:h vim.ui.select(), thekind"refactoring.nvim" is used to allow user customization). Here is an example remap to demonstratethis functionality:
-- prompt for a refactor to apply when the remap is triggeredvim.keymap.set( {"n","x"},"<leader>rr",function()require('refactoring').select_refactor()end)-- Note that not all refactor support both normal and visual mode
select_refactor() usesvim.ui.input by default to input the arguments (ifneeded). If you want to use the Ex command to get the preview of the changesyou can use theprefer_ex_cmd option.
require('refactoring').select_refactor({prefer_ex_cmd=true})
If you would prefer to use Telescope to choose a refactor, you can do sousing theTelescope extension. Here is an exampleconfig for this setup:
-- load refactoring Telescope extensionrequire("telescope").load_extension("refactoring")vim.keymap.set({"n","x"},"<leader>rr",function()require('telescope').extensions.refactoring.refactors()end)
Finally, you can configure remaps for the debug operations of this plugin likethis:
-- You can also use below = true here to to change the position of the printf-- statement (or set two remaps for either one). This remap must be made in normal mode.vim.keymap.set("n","<leader>rp",function()require('refactoring').debug.printf({below=false})end)-- Print varvim.keymap.set({"x","n"},"<leader>rv",function()require('refactoring').debug.print_var()end)-- Supports both visual and normal modevim.keymap.set("n","<leader>rc",function()require('refactoring').debug.cleanup({})end)-- Supports only normal mode
It is possible to override the statements used in the printf and print varfunctionalities.
You can add to the printf statements for any language by adding something likethe below to your configuration:
require('refactoring').setup({-- overriding printf statement for cppprintf_statements= {-- add a custom printf statement for cppcpp= {'std::cout << "%s" << std::endl;' } }})
In any custom printf statement, it is possible to optionally add a max ofone %s pattern, which is where the debug path will go. For an example customprintf statement, go tothis folder,select your language, and click onmultiple-statements/printf.config.
The print var functionality can also be extended for any given language,as shown below:
require('refactoring').setup({-- overriding printf statement for cppprint_var_statements= {-- add a custom print var statement for cppcpp= {'printf("a custom statement %%s %s", %s)' } }})
In any custom print var statement, it is possible to optionally add a max oftwo %s patterns, which is where the debug path and the actual variablereference will go, respectively. To add a literal "%s" to the string, escape thesequence like this:%%s. For an example custom print var statement, go tothis folder, select your language, andviewmultiple-statements/print_var.config.
Note: for either of these functions, if you have multiple customstatements, the plugin will prompt for which one should be inserted. If youjust have one custom statement in your config, it will override the defaultautomatically.
When performing anextract_var refactor operation, you can custom how the newvariable would be declared by setting configuration like the below example.
require('refactoring').setup({-- overriding extract statement for goextract_var_statements= {go="%s := %s // poggers" }})
For certain languages like Golang, types are required for functions that returnan object(s) and parameters of functions. Unfortunately, for some parametersand functions there is no way to automatically find their type. In thoseinstances, we want to provide a way to input a type instead of inserting aplaceholder value.
By default all prompts are turned off. The configuration below shows how toenable prompts for all the languages currently supported.
require('refactoring').setup({-- prompt for return typeprompt_func_return_type= {go=true,cpp=true,c=true,java=true, },-- prompt for function parametersprompt_func_param_type= {go=true,cpp=true,c=true,java=true, },})
About
The Refactoring library based off the Refactoring book by Martin Fowler
Resources
License
Contributing
Uh oh!
There was an error while loading.Please reload this page.
Stars
Watchers
Forks
Releases
Sponsor this project
Uh oh!
There was an error while loading.Please reload this page.
Packages0
Uh oh!
There was an error while loading.Please reload this page.