module ViteRuby::CLI::FileUtils

def _inject_line_after(path, target, contents, finder)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def _inject_line_after(path, target, contents, finder)
  content = read_lines(path)
  return if content.join.include?(contents)
  i = finder.call(content, path, target)
  content.insert(i + 1, "#{ contents }\n")
  write(path, content)
end

def _inject_line_before(path, target, contents, finder)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def _inject_line_before(path, target, contents, finder)
  content = read_lines(path)
  return if content.join.include?(contents)
  i = finder.call(content, path, target)
  content.insert(i, "#{ contents }\n")
  write(path, content)
end

def append(path, contents)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def append(path, contents)
  content = read_lines(path)
  return if content.join.include?(contents)
  content << "\n" unless content.last&.end_with?("\n")
  content << "#{ contents }\n"
  write(path, content)
end

def cp(source, destination)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def cp(source, destination)
  mkdir_p(destination)
  FileUtils.cp(source, destination) unless File.exist?(destination)
end

def index(content, path, target)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def index(content, path, target)
  content.index { |line| line.include?(target) } ||
    raise(ArgumentError, "Cannot find `#{ target }' inside `#{ path }'.")
end

def inject_line_after(path, target, contents)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def inject_line_after(path, target, contents)
  _inject_line_after(path, target, contents, method(:index))
end

def inject_line_after_last(path, target, contents)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def inject_line_after_last(path, target, contents)
  _inject_line_after(path, target, contents, method(:rindex))
end

def inject_line_before(path, target, contents)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def inject_line_before(path, target, contents)
  _inject_line_before(path, target, contents, method(:index))
end

def mkdir_p(path)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def mkdir_p(path)
  Pathname.new(path).dirname.mkpath
end

def read_lines(path)

Returns an array with lines in the specified file, empty if it doesn't exist.
def read_lines(path)
  File.exist?(path) ? File.readlines(path) : []
end

def replace_first_line(path, target, replacement)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def replace_first_line(path, target, replacement)
  content = read_lines(path)
  content[index(content, path, target)] = "#{ replacement }\n"
  write(path, content)
end

def rindex(content, path, target)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def rindex(content, path, target)
  content.rindex { |line| line.include?(target) } ||
    raise(ArgumentError, "Cannot find `#{ target }' inside `#{ path }'.")
end

def write(path, *content)

Other tags:
    Api: - private

Other tags:
    Since: - 1.2.11
def write(path, *content)
  mkdir_p(path)
  File.open(path, File::CREAT | File::WRONLY | File::TRUNC) do |file|
    file.write(Array(content).flatten.join)
  end
end