Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

More convenient way to copy args from built-in formatter #50

Closed
stevearc opened this issue Sep 15, 2023 · 3 comments
Closed

More convenient way to copy args from built-in formatter #50

stevearc opened this issue Sep 15, 2023 · 3 comments

Comments

@stevearc
Copy link
Owner

stevearc commented Sep 15, 2023

Slightly off topic but I would also love a more generalized solution for passing arguments in general. Right now using list_extend works well enough unless a builtin formatter has args or range_args which are of type function(ctx). In this case the user needs to basically copy the original function from the source, modify it to their needs, and then set that new function as the property. If there were some with_args or extra_args property implemented for the formatters this would be really nice, and maybe something similar could be done for this problem.

Originally posted by @ribru17 in #44 (comment)

@stevearc
Copy link
Owner Author

In general, copying the args from the definition is not as bad an idea as people make it out to be. Normally the concern with copying instead of reusing is that you might break compatibility at some point, or lose out on improvements made in the source. In this case, there's not much that could realistically change with the conform API, so the compatibility concerns are really more relevant to the formatter tool itself. But I would make the case that the end user is actually better positioned than conform.nvim to handle any breaking changes from tools, because you have more information and control over exactly which version you're running.

That said, I understand the difficulty of handling the args when they could be a string, list, or function. What do you think of this helper function? If it seems like a reasonable approach I can add it to the recipes documentation

local function extend_args(args, extra_args)
  return function(ctx)
    if type(args) == "function" then
      args = args(ctx)
    end
    if type(args) == "string" then
      if type(extra_args) == "string" then
        return extra_args .. " " .. args
      else
        return table.concat(extra_args, " ") .. " " .. args
      end
    else
      if type(extra_args) == "string" then
        error("extra_args must be a table when args is a table")
      else
        return vim.tbl_flatten({ extra_args, args })
      end
    end
  end
end

-- Used like so:
local prettier = require("conform.formatters.prettier")
local util = require("conform.util")
require("conform").formatters.prettier = vim.tbl_deep_extend("force", prettier, {
  args = util.extend_args(prettier.args, { "--tab", "--indent", "2" }),
  range_args = util.extend_args(prettier.range_args, { "--tab", "--indent", "2" }),
})

@ribru17
Copy link
Contributor

ribru17 commented Sep 15, 2023

Thanks for responding so quickly. I think this solution is great! The only thing is that I'm realizing it is more complicated than I thought: for instance, some formatters like deno fmt require the additional args to be at the end of the command. I was running into errors with this implementation without realizing why, and I found that changing the last return statement to return vim.tbl_flatten({ args, extra_args }) causes it to work. So maybe there could be some param prepend passed to this function that defaults to true? Not sure, I'll leave the implementation up to an expert like yourself

@stevearc
Copy link
Owner Author

Added in cb5f939

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants