Class: Omnibus::GitCache

Inherits:
Object
  • Object
show all
Includes:
Logging, Util
Defined in:
lib/omnibus/git_cache.rb

Constant Summary collapse

REQUIRED_GIT_FILES =
[
  'HEAD',
  'description',
  'hooks',
  'info',
  'objects',
  'refs',
].freeze

Constants included from Util

Util::SHELLOUT_OPTIONS

Instance Attribute Summary collapse

Instance Method Summary collapse

Methods included from Logging

included

Methods included from Util

#copy_file, #create_directory, #create_file, #create_link, included, #remove_directory, #remove_file, #shellout, #shellout!, #windows_safe_path

Constructor Details

#initialize(software) ⇒ GitCache

Returns a new instance of GitCache

Parameters:

  • software (Software)

    the software this git cache is for


43
44
45
# File 'lib/omnibus/git_cache.rb', line 43

def initialize(software)
  @software = software
end

Instance Attribute Details

#softwareSoftware (readonly)

Returns:


37
38
39
# File 'lib/omnibus/git_cache.rb', line 37

def software
  @software
end

Instance Method Details

#cache_pathString

The path to the full install_dir cache for the project.

Returns:

  • (String)

52
53
54
# File 'lib/omnibus/git_cache.rb', line 52

def cache_path
  @cache_path ||= File.join(Config.git_cache_dir, install_dir)
end

#create_cache_pathtrue, false

Creates the full path if it does not exist already.

Returns:

  • (true, false)

    true if the path was created, false otherwise


62
63
64
65
66
67
68
69
70
# File 'lib/omnibus/git_cache.rb', line 62

def create_cache_path
  if File.directory?(cache_path)
    false
  else
    create_directory(File.dirname(cache_path))
    shellout!("git --git-dir=#{cache_path} init -q")
    true
  end
end

#incrementalObject

Create an incremental install path cache for the software step


110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
# File 'lib/omnibus/git_cache.rb', line 110

def incremental
  log.internal(log_key) { 'Performing incremental cache' }

  create_cache_path
  remove_git_dirs

  shellout!(%Q(git --git-dir=#{cache_path} --work-tree=#{install_dir} add -A -f))

  begin
    shellout!(%Q(git --git-dir=#{cache_path} --work-tree=#{install_dir} commit -q -m "Backup of #{tag}"))
  rescue CommandFailed => e
    raise unless e.message.include?('nothing to commit')
  end

  shellout!(%Q(git --git-dir=#{cache_path} --work-tree=#{install_dir} tag -f "#{tag}"))
end

#remove_git_dirstrue

Git caching will attempt to version embedded git directories, partially versioning them. This causes failures on subsequent runs. This method will find git directories and remove them to prevent those errors.

Returns:

  • (true)

155
156
157
158
159
160
161
162
163
164
165
166
167
168
# File 'lib/omnibus/git_cache.rb', line 155

def remove_git_dirs
  log.internal(log_key) { "Removing git directories" }

  Dir.glob("#{install_dir}/**/{,.*}/config").reject do |path|
    REQUIRED_GIT_FILES.any? do |required_file|
      !File.exist?(File.join(File.dirname(path), required_file))
    end
  end.each do |path|
    log.internal(log_key) { "Removing git dir `#{path}'" }
    FileUtils.rm_rf(File.dirname(path))
  end

  true
end

#restoreObject


127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
# File 'lib/omnibus/git_cache.rb', line 127

def restore
  log.internal(log_key) { 'Performing cache restoration' }

  create_cache_path

  cmd = shellout(%Q(git --git-dir=#{cache_path} --work-tree=#{install_dir} tag -l "#{tag}"))

  restore_me = false
  cmd.stdout.each_line do |line|
    restore_me = true if tag == line.chomp
  end

  if restore_me
    log.internal(log_key) { "Detected tag `#{tag}' can be restored, restoring" }
    shellout!(%Q(git --git-dir=#{cache_path} --work-tree=#{install_dir} checkout -f "#{tag}"))
    true
  else
    log.internal(log_key) { "Could not find tag `#{tag}', skipping restore" }
    false
  end
end

#tagString

Computes the tag for this cache entry.

Returns:

  • (String)

77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
# File 'lib/omnibus/git_cache.rb', line 77

def tag
  return @tag if @tag

  log.internal(log_key) { "Calculating tag" }

  # Accumulate an array of all the software projects that come before
  # the name and version we are tagging. So if you have
  #
  # build_order = [ 1, 2, 3, 4, 5 ]
  #
  # And we are tagging 3, you would get dep_list = [ 1, 2 ]
  dep_list = software.project.library.build_order.take_while do |dep|
    if dep.name == software.name && dep.version == software.version
      false
    else
      true
    end
  end

  log.internal(log_key) { "dep_list: #{dep_list.map(&:name).inspect}" }

  # This is the list of all the unqiue shasums of all the software build
  # dependencies, including the on currently being acted upon.
  shasums = [dep_list.map(&:shasum), software.shasum].flatten
  suffix  = Digest::SHA256.hexdigest(shasums.join('|'))
  @tag    = "#{software.name}-#{suffix}"

  log.internal(log_key) { "tag: #{@tag}" }

  @tag
end