class RBS::Collection::Sources::Git

def _install(dest:, name:, version:)

def _install(dest:, name:, version:)
ld checkout that revision to support symlinks
eset", "--hard", resolved_revision)
dest.join(name, version)
path
gem_repo_dir.join(name, version)
rc, dir)
metadata(dir: dir, name: name, version: version)

def commit_hash?

def commit_hash?
on.match?(/\A[a-f0-9]{40}\z/)

def cp_r(src, dest)

def cp_r(src, dest)
ind(src) do |file_src|
_src = Pathname(file_src)
ip file if it starts with _, such as _test/
.prune if file_src.basename.to_s.start_with?('_')
_src_relative = file_src.relative_path_from(src)
_dest = dest.join(file_src_relative)
_dest.dirname.mkpath
Utils.copy_entry(file_src, file_dest, false, true) unless file_src.directory?

def format_config_entry(name, version)

def format_config_entry(name, version)
resolved_revision[0..10]
 "#{name}@#{rev}"
e}:#{version} (#{desc})"

def gem_repo_dir

def gem_repo_dir
r.join @repo_dir

def gems_versions

def gems_versions
versions ||= begin
_path = Pathname(repo_dir)
s = git('ls-tree', '--full-tree', '-dr', '--name-only', '-z', resolved_revision, File.join(repo_dir, "")).split("\0").map {|line| Pathname(line) }
ype var versions: Hash[String, Set[String]]
ions = {}
s.each do |full_path|
th = full_path.relative_path_from(repo_path)
m_name, version = path.descend.take(2)
 gem_name
versions[gem_name.to_s] ||= Set[]
if version && !version.basename.to_s.start_with?('_')
  versions[gem_name.to_s] << version.basename.to_s
end
d
ions

def git(*cmd, **opt)

def git(*cmd, **opt)
it', *cmd, **opt

def git?(*cmd, **opt)

def git?(*cmd, **opt)
md, **opt)
ommandError

def git_dir

def git_dir
ir ||= (
 = Pathname(ENV['XDG_CACHE_HOME'] || File.expand_path("~/.cache"))
e_key = remote.start_with?('.') ? "#{remote}\0#{Dir.pwd}" : remote
= base.join('rbs', Digest::SHA256.hexdigest(cache_key))
mkpath

def has?(name, version)

def has?(name, version)
  setup! do
    if version
      (gems_versions[name] || Set[]).include?(version)
    else
      gems_versions.key?(name)
    end
  end
end

def initialize(name:, revision:, remote:, repo_dir:)

def initialize(name:, revision:, remote:, repo_dir:)
  @name = name
  @remote = remote
  @repo_dir = repo_dir || 'gems'
  @revision = revision
  @need_setup = true
end

def install(dest:, name:, version:, stdout:)

def install(dest:, name:, version:, stdout:)
  setup!()
  gem_dir = dest.join(name, version)
  colored_io = CLI::ColoredIO.new(stdout: stdout)
  case
  when gem_dir.symlink?
    colored_io.puts_green("Updating to #{format_config_entry(name, version)} from a local source")
    gem_dir.unlink
    _install(dest: dest, name: name, version: version)
  when gem_dir.directory?
    prev = load_metadata(dir: gem_dir)
    if prev == metadata_content(name: name, version: version)
      colored_io.puts "Using #{format_config_entry(name, version)}"
    else
      colored_io.puts_green("Updating to #{format_config_entry(name, version)} from #{format_config_entry(prev["name"], prev["version"])}")
      FileUtils.remove_entry_secure(gem_dir.to_s)
      _install(dest: dest, name: name, version: version)
    end
  when !gem_dir.exist?
    colored_io.puts_green("Installing #{format_config_entry(name, version)}")
    _install(dest: dest, name: name, version: version)
  else
    raise
  end
end

def load_metadata(dir:)

def load_metadata(dir:)
  # @type var content: Hash[String, untyped]
  content = YAML.load_file(dir.join(METADATA_FILENAME).to_s)
  _ = content.slice("name", "version", "source")
end

def manifest_of(name, version)

def manifest_of(name, version)
  setup! do
    path = File.join(repo_dir, name, version, 'manifest.yaml')
    content = git('cat-file', '-p', "#{resolved_revision}:#{path}")
    YAML.safe_load(content)
  rescue CommandError
    if has?(name, version)
      nil
    else
      raise
    end
  end
end

def metadata_content(name:, version:)

def metadata_content(name:, version:)
  {
    "name" => name,
    "version" => version,
    "source" => to_lockfile
  }
end

def need_to_fetch?(revision)

def need_to_fetch?(revision)
 true unless commit_hash?
'cat-file', '-e', revision)

def resolved_revision

def resolved_revision
  @resolved_revision ||=
    begin
      if commit_hash?
        revision
      else
        setup! { git('rev-parse', "refs/remotes/origin/#{revision}").chomp }
      end
    end
end

def setup!

def setup!
ed_setup
dir.mkpath
it_dir.join('.git').directory?
 need_to_fetch?(revision)
git 'fetch', 'origin'
d

gin
# git v2.27.0 or greater
git 'clone', '--filter=blob:none', remote, git_dir.to_s, chdir: nil
scue CommandError
git 'clone', remote, git_dir.to_s, chdir: nil
d
d_setup = false
if block_given?

def sh!(*cmd, **opt)

def sh!(*cmd, **opt)
gger.debug "$ #{cmd.join(' ')}"
{ chdir: git_dir }.merge(opt).compact
p__ = Open3.capture3(*cmd, **opt)).then do |out, err, status|
e CommandError, "Unexpected status #{status.exitstatus}\n\n#{err}" unless status.success?

def to_lockfile

def to_lockfile
  {
    'type' => 'git',
    'name' => name,
    'revision' => resolved_revision,
    'remote' => remote,
    'repo_dir' => repo_dir,
  }
end

def versions(name)

def versions(name)
  setup! do
    versions = gems_versions[name] or raise "Git source `#{name}` doesn't have `#{name}`"
    versions.sort
  end
end

def write_metadata(dir:, name:, version:)

def write_metadata(dir:, name:, version:)
  dir.join(METADATA_FILENAME).write(
    YAML.dump(
      metadata_content(name: name, version: version)
    )
  )
end