Module: SupermarketSync::Sync

Defined in:
lib/supermarket_sync/sync.rb

Overview

> Supermarket Synchronization Logic Controller

Class Method Summary collapse

Class Method Details

.run!Object

rubocop: disable AbcSize, CyclomaticComplexity, MethodLength, PerceivedComplexity

[View source]

26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
# File 'lib/supermarket_sync/sync.rb', line 26

def run! # rubocop: disable AbcSize, CyclomaticComplexity, MethodLength, PerceivedComplexity
  Config.supermarkets.each do |name, cfg| # rubocop: disable BlockLength
    puts "Synchronizing #{name}"

    # => Set Configuration
    configure(cfg)

    # => Parse the Cookbooks List
    cookbooks = Array(Util.parse_json(Config.cookbooks_file)[:cookbooks])

    cookbooks.each do |cookbook| # rubocop: disable BlockLength
      cookbook = cookbook.keys.first if cookbook.is_a?(Hash)
      puts "Checking #{cookbook}"
      # => Grab Source Metadata
      source_meta = begin
                      src.get("/api/v1/cookbooks/#{cookbook}")
                    rescue Net::HTTPServerException => e
                      raise e unless e.response.code == '404'
                      puts 'Cookbook not available on Source Supermarket'
                      next
                    end
      # => Grab Latest Available Version Number
      latest = ::Gem::Version.new(::File.basename(source_meta['latest_version']))

      # => Grab Destination Metadata
      dest_meta = begin
                    dest.get("/api/v1/cookbooks/#{cookbook}")
                  rescue Net::HTTPServerException => e
                    raise e unless e.response.code == '404'
                    # => Cookbook not found -- Initial Upload
                    { 'latest_version' => '0.0.0' }
                  end
      # => Determine Current Version
      current = ::Gem::Version.new(::File.basename(dest_meta['latest_version']))

      if latest > current
        puts 'Updating...'
        puts "Source: #{latest}"
        puts "Destination: #{current}"

        # => Retrieve the Cookbook
        tgz = src.streaming_request("/api/v1/cookbooks/#{cookbook}/versions/#{latest}/download")

        # => Upload the Cookbook
        upload('other', tgz) unless Config.read_only

        # => Remove the Tempfile
        begin
          retries ||= 2
          ::File.delete(tgz)
        rescue => e # rubocop: disable RescueStandardError
          raise e if (retries -= 1).negative?
          puts "#{e.class}::#{e.message}"
          puts 'Could not delete Tempfile... Retrying'
          sleep 2
          retry
        end
        @notify&.updated&.push(source: source_meta, dest: dest_meta)
      end
      # => Identify Deprecated Cookbooks
      next unless source_meta['deprecated'] && !dest_meta['deprecated']
      @notify&.deprecated&.push(source: source_meta, dest: dest_meta)
    end
  ensure
    # => Send Notifications
    @notify&.send!
  end
end

.src(url = nil) ⇒ Object

> API Clients

Raises:

  • (ArgumentError)
[View source]

122
123
124
125
126
127
# File 'lib/supermarket_sync/sync.rb', line 122

def src(url = nil)
  url ||= @src&.url
  raise ArgumentError, 'No URL supplied!' unless url
  return @src if @src&.url == url
  @src = Chef::HTTP::SimpleJSON.new(url)
end