From 7d424ff02ae1eada8bd7cd67b9e4e9db6066f4b7 Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 11:16:51 +1100
Subject: [PATCH 01/11] Turn TagsLogic into a class

---
 lib/tagfish/tags_command.rb   |  2 +-
 lib/tagfish/tags_logic.rb     | 19 +++++++++++++------
 lib/tagfish/update/updater.rb |  2 +-
 3 files changed, 15 insertions(+), 8 deletions(-)

diff --git a/lib/tagfish/tags_command.rb b/lib/tagfish/tags_command.rb
index e3ccef0..2eda3b8 100644
--- a/lib/tagfish/tags_command.rb
+++ b/lib/tagfish/tags_command.rb
@@ -12,7 +12,7 @@ def execute
       
       docker_uri = DockerURI.parse(repository)
       docker_api = DockerAPI.new(docker_uri)
-      tags = TagsLogic.find_tags_by_repository(docker_api, tags_only)
+      tags = TagsLogic.new(docker_api).find_tags_by_repository(tags_only)
 
       begin
        tags_found = latest? ? tags.latest_tag : tags.tag_names
diff --git a/lib/tagfish/tags_logic.rb b/lib/tagfish/tags_logic.rb
index d3d93fc..52c0e01 100644
--- a/lib/tagfish/tags_logic.rb
+++ b/lib/tagfish/tags_logic.rb
@@ -3,23 +3,30 @@
 
 module Tagfish
   class TagsLogic
-    def self.find_tags_by_repository(docker_api, tags_only=false)
+    
+    attr_reader :docker_api
+    
+    def initialize(docker_api)
+      @docker_api = docker_api
+    end
+    
+    def find_tags_by_repository(tags_only=false)
       if docker_api.api_version == 'v2'
-        tags_list = tags_v2(docker_api, tags_only)
+        tags_list = tags_v2(tags_only)
       else
-        tags_list = tags_v1(docker_api)
+        tags_list = tags_v1
       end
       Tagfish::Tags.new(tags_list)
     end
 
     private
 
-    def self.tags_v1(docker_api)
+    def tags_v1
       tags_json = docker_api.tags_v1
       tags_v1_api(tags_json)
     end
 
-    def self.tags_v1_api(api_response_data)
+    def tags_v1_api(api_response_data)
       case api_response_data
       when Hash
         api_response_data
@@ -32,7 +39,7 @@ def self.tags_v1_api(api_response_data)
       end
     end
 
-    def self.tags_v2(docker_api, tags_only)
+    def tags_v2(tags_only)
       tags = docker_api.tags_v2["tags"]
       if tags.nil?
         abort("No Tags found for this repository")
diff --git a/lib/tagfish/update/updater.rb b/lib/tagfish/update/updater.rb
index d2b5a7d..976a020 100644
--- a/lib/tagfish/update/updater.rb
+++ b/lib/tagfish/update/updater.rb
@@ -39,7 +39,7 @@ def updatable?(uri)
 
       def update_uri(docker_uri)
         docker_api = DockerAPI.new(docker_uri)
-        tags = TagsLogic.find_tags_by_repository(docker_api)
+        tags = TagsLogic.new(docker_api).find_tags_by_repository
         newest_tag_name = tags.latest_tag_to_s
         if newest_tag_name.nil?
           docker_uri

From 22cf04be85e3c59f1282ffebb77fe17e73c21cb2 Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 11:42:53 +1100
Subject: [PATCH 02/11] Move TagsLogic into DockerAPI

---
 lib/tagfish/docker_api.rb     | 46 +++++++++++++++++++++++++++
 lib/tagfish/tags_command.rb   |  4 +--
 lib/tagfish/tags_logic.rb     | 59 -----------------------------------
 lib/tagfish/update/updater.rb |  4 +--
 4 files changed, 50 insertions(+), 63 deletions(-)
 delete mode 100644 lib/tagfish/tags_logic.rb

diff --git a/lib/tagfish/docker_api.rb b/lib/tagfish/docker_api.rb
index b116420..b22558b 100644
--- a/lib/tagfish/docker_api.rb
+++ b/lib/tagfish/docker_api.rb
@@ -2,6 +2,7 @@
 require 'json'
 require 'tagfish/docker_uri'
 require 'tagfish/api_call'
+require 'tagfish/tags'
 
 module Tagfish
   class DockerAPI
@@ -49,6 +50,15 @@ def init_auth(api_version)
       end
     end
     
+    def find_tags_by_repository(tags_only=false)
+      if api_version == 'v2'
+        tags_list = tags_v2_logic(tags_only)
+      else
+        tags_list = tags_v1_logic
+      end
+      Tagfish::Tags.new(tags_list)
+    end
+    
     def tags_v1
       APICall.new(tags_v1_uri).get_json(http_auth)
     end
@@ -69,6 +79,42 @@ def search_v1(keyword)
       APICall.new(search_v1_uri(keyword)).get_json(http_auth)
     end
     
+    private
+    
+    def tags_v1_logic
+      tags_json = tags_v1
+      tags_v1_api(tags_json)
+    end
+
+    def tags_v1_api(api_response_data)
+      case api_response_data
+      when Hash
+        api_response_data
+      when Array
+        api_response_data.reduce({}) do |images, tag|
+          images.merge({tag["name"] => tag["layer"]})
+        end
+      else
+        raise "unexpected type #{api_response_data.class}"
+      end
+    end
+
+    def tags_v2_logic(tags_only)
+      tags = tags_v2["tags"]
+      if tags.nil?
+        abort("No Tags found for this repository")
+      end
+      
+      tags_with_hashes = tags.inject({}) do |dict, tag|
+        if tags_only
+          dict[tag] = "dummy_hash"
+        else
+          dict[tag] = hash_v2(tag)["fsLayers"][0]["blobSum"]
+        end
+        dict
+      end
+    end
+    
     def base_uri
       "#{docker_uri.protocol}#{docker_uri.registry}"
     end
diff --git a/lib/tagfish/tags_command.rb b/lib/tagfish/tags_command.rb
index 2eda3b8..6f39796 100644
--- a/lib/tagfish/tags_command.rb
+++ b/lib/tagfish/tags_command.rb
@@ -1,5 +1,5 @@
-require "tagfish/tags_logic"
 require "tagfish/docker_uri"
+require "tagfish/docker_api"
 
 module Tagfish
   class TagsCommand < Clamp::Command
@@ -12,7 +12,7 @@ def execute
       
       docker_uri = DockerURI.parse(repository)
       docker_api = DockerAPI.new(docker_uri)
-      tags = TagsLogic.new(docker_api).find_tags_by_repository(tags_only)
+      tags = docker_api.find_tags_by_repository(tags_only)
 
       begin
        tags_found = latest? ? tags.latest_tag : tags.tag_names
diff --git a/lib/tagfish/tags_logic.rb b/lib/tagfish/tags_logic.rb
deleted file mode 100644
index 52c0e01..0000000
--- a/lib/tagfish/tags_logic.rb
+++ /dev/null
@@ -1,59 +0,0 @@
-require 'json'
-require 'tagfish/tags'
-
-module Tagfish
-  class TagsLogic
-    
-    attr_reader :docker_api
-    
-    def initialize(docker_api)
-      @docker_api = docker_api
-    end
-    
-    def find_tags_by_repository(tags_only=false)
-      if docker_api.api_version == 'v2'
-        tags_list = tags_v2(tags_only)
-      else
-        tags_list = tags_v1
-      end
-      Tagfish::Tags.new(tags_list)
-    end
-
-    private
-
-    def tags_v1
-      tags_json = docker_api.tags_v1
-      tags_v1_api(tags_json)
-    end
-
-    def tags_v1_api(api_response_data)
-      case api_response_data
-      when Hash
-        api_response_data
-      when Array
-        api_response_data.reduce({}) do |images, tag|
-          images.merge({tag["name"] => tag["layer"]})
-        end
-      else
-        raise "unexpected type #{api_response_data.class}"
-      end
-    end
-
-    def tags_v2(tags_only)
-      tags = docker_api.tags_v2["tags"]
-      if tags.nil?
-        abort("No Tags found for this repository")
-      end
-      
-      tags_with_hashes = tags.inject({}) do |dict, tag|
-        if tags_only
-          dict[tag] = "dummy_hash"
-        else
-          dict[tag] = docker_api.hash_v2(tag)["fsLayers"][0]["blobSum"]
-        end
-        dict
-      end
-    end
-    
-  end
-end
diff --git a/lib/tagfish/update/updater.rb b/lib/tagfish/update/updater.rb
index 976a020..79d4ab5 100644
--- a/lib/tagfish/update/updater.rb
+++ b/lib/tagfish/update/updater.rb
@@ -1,6 +1,6 @@
 require 'tagfish/tokeniser'
 require 'tagfish/docker_uri'
-require 'tagfish/tags_logic'
+require 'tagfish/docker_api'
 
 module Tagfish
   module Update
@@ -39,7 +39,7 @@ def updatable?(uri)
 
       def update_uri(docker_uri)
         docker_api = DockerAPI.new(docker_uri)
-        tags = TagsLogic.new(docker_api).find_tags_by_repository
+        tags = docker_api.find_tags_by_repository
         newest_tag_name = tags.latest_tag_to_s
         if newest_tag_name.nil?
           docker_uri

From ca78a995050124275598e785212f790e45abfab3 Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 11:47:05 +1100
Subject: [PATCH 03/11] Rename DockerAPI into DockerRegistryClient

---
 lib/tagfish/{docker_api.rb => docker_registry_client.rb} | 2 +-
 lib/tagfish/docker_uri.rb                                | 1 -
 lib/tagfish/tags_command.rb                              | 4 ++--
 lib/tagfish/update/updater.rb                            | 4 ++--
 4 files changed, 5 insertions(+), 6 deletions(-)
 rename lib/tagfish/{docker_api.rb => docker_registry_client.rb} (99%)

diff --git a/lib/tagfish/docker_api.rb b/lib/tagfish/docker_registry_client.rb
similarity index 99%
rename from lib/tagfish/docker_api.rb
rename to lib/tagfish/docker_registry_client.rb
index b22558b..355027f 100644
--- a/lib/tagfish/docker_api.rb
+++ b/lib/tagfish/docker_registry_client.rb
@@ -5,7 +5,7 @@
 require 'tagfish/tags'
 
 module Tagfish
-  class DockerAPI
+  class DockerRegistryClient
 
     attr_accessor :docker_uri
     attr_accessor :api_version
diff --git a/lib/tagfish/docker_uri.rb b/lib/tagfish/docker_uri.rb
index ca767f5..e1c26ac 100644
--- a/lib/tagfish/docker_uri.rb
+++ b/lib/tagfish/docker_uri.rb
@@ -1,5 +1,4 @@
 require 'tagfish/docker_http_auth'
-require 'tagfish/docker_api'
 
 module Tagfish
   class DockerURI
diff --git a/lib/tagfish/tags_command.rb b/lib/tagfish/tags_command.rb
index 6f39796..210bd8b 100644
--- a/lib/tagfish/tags_command.rb
+++ b/lib/tagfish/tags_command.rb
@@ -1,5 +1,5 @@
 require "tagfish/docker_uri"
-require "tagfish/docker_api"
+require "tagfish/docker_registry_client"
 
 module Tagfish
   class TagsCommand < Clamp::Command
@@ -11,7 +11,7 @@ def execute
       tags_only = latest? ? false : true
       
       docker_uri = DockerURI.parse(repository)
-      docker_api = DockerAPI.new(docker_uri)
+      docker_api = DockerRegistryClient.new(docker_uri)
       tags = docker_api.find_tags_by_repository(tags_only)
 
       begin
diff --git a/lib/tagfish/update/updater.rb b/lib/tagfish/update/updater.rb
index 79d4ab5..7723f20 100644
--- a/lib/tagfish/update/updater.rb
+++ b/lib/tagfish/update/updater.rb
@@ -1,6 +1,6 @@
 require 'tagfish/tokeniser'
 require 'tagfish/docker_uri'
-require 'tagfish/docker_api'
+require 'tagfish/docker_registry_client'
 
 module Tagfish
   module Update
@@ -38,7 +38,7 @@ def updatable?(uri)
       end
 
       def update_uri(docker_uri)
-        docker_api = DockerAPI.new(docker_uri)
+        docker_api = DockerRegistryClient.new(docker_uri)
         tags = docker_api.find_tags_by_repository
         newest_tag_name = tags.latest_tag_to_s
         if newest_tag_name.nil?

From 0100afa447ef69851bdd75e186b73ac8e7a667a2 Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 12:05:07 +1100
Subject: [PATCH 04/11] MAke DockerRegistryClient a facade in front of what
 will become v1 and v2 API classes

---
 lib/tagfish/docker_registry_client.rb       | 156 +------------------
 lib/tagfish/docker_registry_vboth_client.rb | 159 ++++++++++++++++++++
 lib/tagfish/tags_command.rb                 |   2 +-
 lib/tagfish/update/updater.rb               |   2 +-
 4 files changed, 165 insertions(+), 154 deletions(-)
 create mode 100644 lib/tagfish/docker_registry_vboth_client.rb

diff --git a/lib/tagfish/docker_registry_client.rb b/lib/tagfish/docker_registry_client.rb
index 355027f..28e1bb2 100644
--- a/lib/tagfish/docker_registry_client.rb
+++ b/lib/tagfish/docker_registry_client.rb
@@ -1,158 +1,10 @@
-require 'net/http'
-require 'json'
-require 'tagfish/docker_uri'
-require 'tagfish/api_call'
-require 'tagfish/tags'
+require 'tagfish/docker_registry_vboth_client'
 
 module Tagfish
-  class DockerRegistryClient
+  module DockerRegistryClient
 
-    attr_accessor :docker_uri
-    attr_accessor :api_version
-    attr_accessor :http_auth
-
-    def initialize(docker_uri)
-      @docker_uri = docker_uri
-      retrieve_api_version_and_auth()
-    end
-    
-    def retrieve_api_version_and_auth
-      code = try_api('v1')
-      if code != 200 
-        code = try_api('v2')
-      end
-      if code == 401
-        abort("Authentication failed, please `docker login <REGISTRY>` and try again.")
-      elsif code != 200
-        abort("API version not recognized")
-      end
-    end
-    
-    def try_api(version)
-      code = APICall.new(ping_uri(version)).response_code
-      if code == 200
-        @api_version = version
-      elsif code == 401
-        code = init_auth(version)
-        if code == 200
-          @api_version = version
-        end
-      end
-      return code
-    end
-    
-    def init_auth(api_version)
-      @http_auth = DockerHttpAuth.new(docker_uri.registry)
-      if api_version == 'v2'
-        code = APICall.new(ping_v2_uri).response_code(http_auth)
-      elsif api_version == 'v1'
-        code = APICall.new(ping_v1_uri).response_code(http_auth)
-      end
-    end
-    
-    def find_tags_by_repository(tags_only=false)
-      if api_version == 'v2'
-        tags_list = tags_v2_logic(tags_only)
-      else
-        tags_list = tags_v1_logic
-      end
-      Tagfish::Tags.new(tags_list)
-    end
-    
-    def tags_v1
-      APICall.new(tags_v1_uri).get_json(http_auth)
-    end
-    
-    def tags_v2
-      APICall.new(tags_v2_uri).get_json(http_auth)
-    end
-    
-    def hash_v2(tag)
-      APICall.new(hash_v2_uri(tag)).get_json(http_auth)
-    end
-    
-    def catalog_v2
-      APICall.new(catalog_v2_uri).get_json(http_auth)
-    end
-    
-    def search_v1(keyword)
-      APICall.new(search_v1_uri(keyword)).get_json(http_auth)
-    end
-    
-    private
-    
-    def tags_v1_logic
-      tags_json = tags_v1
-      tags_v1_api(tags_json)
-    end
-
-    def tags_v1_api(api_response_data)
-      case api_response_data
-      when Hash
-        api_response_data
-      when Array
-        api_response_data.reduce({}) do |images, tag|
-          images.merge({tag["name"] => tag["layer"]})
-        end
-      else
-        raise "unexpected type #{api_response_data.class}"
-      end
-    end
-
-    def tags_v2_logic(tags_only)
-      tags = tags_v2["tags"]
-      if tags.nil?
-        abort("No Tags found for this repository")
-      end
-      
-      tags_with_hashes = tags.inject({}) do |dict, tag|
-        if tags_only
-          dict[tag] = "dummy_hash"
-        else
-          dict[tag] = hash_v2(tag)["fsLayers"][0]["blobSum"]
-        end
-        dict
-      end
-    end
-    
-    def base_uri
-      "#{docker_uri.protocol}#{docker_uri.registry}"
-    end
-    
-    def ping_uri(version)
-      if version == 'v1'
-        ping_v1_uri
-      elsif version == 'v2'
-        ping_v2_uri
-      end
-    end
-    
-    def ping_v2_uri
-      "#{base_uri}/v2/"
-    end
-    
-    def ping_v1_uri
-      "#{base_uri}/v1/_ping"
-    end
-    
-    def catalog_v2_uri
-      "#{base_uri}/v2/_catalog"
-    end
-    
-    def search_v1_uri(keyword)
-      "#{base_uri}/v1/search?q=#{keyword}"  
-    end
-    
-    def tags_v1_uri
-      "#{base_uri}/v1/repositories/#{docker_uri.repository}/tags"
-    end
-    
-    def tags_v2_uri
-      "#{base_uri}/v2/#{docker_uri.repository}/tags/list"  
-    end
-    
-    def hash_v2_uri(tag)
-      "#{base_uri}/v2/#{docker_uri.repository}/manifests/#{tag}"
+    def self.for(*args)
+      DockerRegistryVbothClient.new(*args)
     end
     
   end
diff --git a/lib/tagfish/docker_registry_vboth_client.rb b/lib/tagfish/docker_registry_vboth_client.rb
new file mode 100644
index 0000000..fc4fbfd
--- /dev/null
+++ b/lib/tagfish/docker_registry_vboth_client.rb
@@ -0,0 +1,159 @@
+require 'net/http'
+require 'json'
+require 'tagfish/docker_uri'
+require 'tagfish/api_call'
+require 'tagfish/tags'
+
+module Tagfish
+  class DockerRegistryVbothClient
+
+    attr_accessor :docker_uri
+    attr_accessor :api_version
+    attr_accessor :http_auth
+
+    def initialize(docker_uri)
+      @docker_uri = docker_uri
+      retrieve_api_version_and_auth()
+    end
+    
+    def retrieve_api_version_and_auth
+      code = try_api('v1')
+      if code != 200 
+        code = try_api('v2')
+      end
+      if code == 401
+        abort("Authentication failed, please `docker login <REGISTRY>` and try again.")
+      elsif code != 200
+        abort("API version not recognized")
+      end
+    end
+    
+    def try_api(version)
+      code = APICall.new(ping_uri(version)).response_code
+      if code == 200
+        @api_version = version
+      elsif code == 401
+        code = init_auth(version)
+        if code == 200
+          @api_version = version
+        end
+      end
+      return code
+    end
+    
+    def init_auth(api_version)
+      @http_auth = DockerHttpAuth.new(docker_uri.registry)
+      if api_version == 'v2'
+        code = APICall.new(ping_v2_uri).response_code(http_auth)
+      elsif api_version == 'v1'
+        code = APICall.new(ping_v1_uri).response_code(http_auth)
+      end
+    end
+    
+    def find_tags_by_repository(tags_only=false)
+      if api_version == 'v2'
+        tags_list = tags_v2_logic(tags_only)
+      else
+        tags_list = tags_v1_logic
+      end
+      Tagfish::Tags.new(tags_list)
+    end
+    
+    def tags_v1
+      APICall.new(tags_v1_uri).get_json(http_auth)
+    end
+    
+    def tags_v2
+      APICall.new(tags_v2_uri).get_json(http_auth)
+    end
+    
+    def hash_v2(tag)
+      APICall.new(hash_v2_uri(tag)).get_json(http_auth)
+    end
+    
+    def catalog_v2
+      APICall.new(catalog_v2_uri).get_json(http_auth)
+    end
+    
+    def search_v1(keyword)
+      APICall.new(search_v1_uri(keyword)).get_json(http_auth)
+    end
+    
+    private
+    
+    def tags_v1_logic
+      tags_json = tags_v1
+      tags_v1_api(tags_json)
+    end
+
+    def tags_v1_api(api_response_data)
+      case api_response_data
+      when Hash
+        api_response_data
+      when Array
+        api_response_data.reduce({}) do |images, tag|
+          images.merge({tag["name"] => tag["layer"]})
+        end
+      else
+        raise "unexpected type #{api_response_data.class}"
+      end
+    end
+
+    def tags_v2_logic(tags_only)
+      tags = tags_v2["tags"]
+      if tags.nil?
+        abort("No Tags found for this repository")
+      end
+      
+      tags_with_hashes = tags.inject({}) do |dict, tag|
+        if tags_only
+          dict[tag] = "dummy_hash"
+        else
+          dict[tag] = hash_v2(tag)["fsLayers"][0]["blobSum"]
+        end
+        dict
+      end
+    end
+    
+    def base_uri
+      "#{docker_uri.protocol}#{docker_uri.registry}"
+    end
+    
+    def ping_uri(version)
+      if version == 'v1'
+        ping_v1_uri
+      elsif version == 'v2'
+        ping_v2_uri
+      end
+    end
+    
+    def ping_v2_uri
+      "#{base_uri}/v2/"
+    end
+    
+    def ping_v1_uri
+      "#{base_uri}/v1/_ping"
+    end
+    
+    def catalog_v2_uri
+      "#{base_uri}/v2/_catalog"
+    end
+    
+    def search_v1_uri(keyword)
+      "#{base_uri}/v1/search?q=#{keyword}"  
+    end
+    
+    def tags_v1_uri
+      "#{base_uri}/v1/repositories/#{docker_uri.repository}/tags"
+    end
+    
+    def tags_v2_uri
+      "#{base_uri}/v2/#{docker_uri.repository}/tags/list"  
+    end
+    
+    def hash_v2_uri(tag)
+      "#{base_uri}/v2/#{docker_uri.repository}/manifests/#{tag}"
+    end
+    
+  end
+end
diff --git a/lib/tagfish/tags_command.rb b/lib/tagfish/tags_command.rb
index 210bd8b..44dfb86 100644
--- a/lib/tagfish/tags_command.rb
+++ b/lib/tagfish/tags_command.rb
@@ -11,7 +11,7 @@ def execute
       tags_only = latest? ? false : true
       
       docker_uri = DockerURI.parse(repository)
-      docker_api = DockerRegistryClient.new(docker_uri)
+      docker_api = DockerRegistryClient.for(docker_uri)
       tags = docker_api.find_tags_by_repository(tags_only)
 
       begin
diff --git a/lib/tagfish/update/updater.rb b/lib/tagfish/update/updater.rb
index 7723f20..d9ad995 100644
--- a/lib/tagfish/update/updater.rb
+++ b/lib/tagfish/update/updater.rb
@@ -38,7 +38,7 @@ def updatable?(uri)
       end
 
       def update_uri(docker_uri)
-        docker_api = DockerRegistryClient.new(docker_uri)
+        docker_api = DockerRegistryClient.for(docker_uri)
         tags = docker_api.find_tags_by_repository
         newest_tag_name = tags.latest_tag_to_s
         if newest_tag_name.nil?

From a52425e3d31e40c8ffa42d4150c64b3fcd42618d Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 14:40:20 +1100
Subject: [PATCH 05/11] Create DockerRegistryClient sub-classes (empty for now)

---
 lib/tagfish/docker_registry_client.rb       | 17 +++++++-
 lib/tagfish/docker_registry_v1_client.rb    | 11 ++++++
 lib/tagfish/docker_registry_v2_client.rb    | 11 ++++++
 lib/tagfish/docker_registry_vboth_client.rb | 44 +++++----------------
 4 files changed, 46 insertions(+), 37 deletions(-)
 create mode 100644 lib/tagfish/docker_registry_v1_client.rb
 create mode 100644 lib/tagfish/docker_registry_v2_client.rb

diff --git a/lib/tagfish/docker_registry_client.rb b/lib/tagfish/docker_registry_client.rb
index 28e1bb2..7b23f6e 100644
--- a/lib/tagfish/docker_registry_client.rb
+++ b/lib/tagfish/docker_registry_client.rb
@@ -1,10 +1,23 @@
-require 'tagfish/docker_registry_vboth_client'
+require 'tagfish/docker_registry_v1_client'
+require 'tagfish/docker_registry_v2_client'
 
 module Tagfish
   module DockerRegistryClient
 
     def self.for(*args)
-      DockerRegistryVbothClient.new(*args)
+      [DockerRegistryV2Client, DockerRegistryV1Client].each do |client_class|
+        begin 
+          return client_class.new(*args)
+        rescue APIVersionError
+        end
+      end
+      raise APIVersionError, "API version unrecognized!"
+    end
+    
+    class AuthenticationError < StandardError
+    end
+    
+    class APIVersionError < StandardError
     end
     
   end
diff --git a/lib/tagfish/docker_registry_v1_client.rb b/lib/tagfish/docker_registry_v1_client.rb
new file mode 100644
index 0000000..9583e39
--- /dev/null
+++ b/lib/tagfish/docker_registry_v1_client.rb
@@ -0,0 +1,11 @@
+require 'tagfish/docker_registry_vboth_client'
+
+module Tagfish
+  class DockerRegistryV1Client < DockerRegistryVbothClient
+    
+    def api_version
+      'v1'
+    end
+    
+  end
+end
diff --git a/lib/tagfish/docker_registry_v2_client.rb b/lib/tagfish/docker_registry_v2_client.rb
new file mode 100644
index 0000000..6244ad2
--- /dev/null
+++ b/lib/tagfish/docker_registry_v2_client.rb
@@ -0,0 +1,11 @@
+require 'tagfish/docker_registry_vboth_client'
+
+module Tagfish
+  class DockerRegistryV2Client < DockerRegistryVbothClient
+    
+    def api_version
+      'v2'
+    end
+
+  end
+end
diff --git a/lib/tagfish/docker_registry_vboth_client.rb b/lib/tagfish/docker_registry_vboth_client.rb
index fc4fbfd..d16dc88 100644
--- a/lib/tagfish/docker_registry_vboth_client.rb
+++ b/lib/tagfish/docker_registry_vboth_client.rb
@@ -8,45 +8,19 @@ module Tagfish
   class DockerRegistryVbothClient
 
     attr_accessor :docker_uri
-    attr_accessor :api_version
     attr_accessor :http_auth
 
     def initialize(docker_uri)
       @docker_uri = docker_uri
-      retrieve_api_version_and_auth()
-    end
-    
-    def retrieve_api_version_and_auth
-      code = try_api('v1')
-      if code != 200 
-        code = try_api('v2')
+      code = APICall.new(ping_uri).response_code
+      if code == 401
+        @http_auth = DockerHttpAuth.new(docker_uri.registry)
+        code = APICall.new(ping_uri).response_code(http_auth)
       end
       if code == 401
-        abort("Authentication failed, please `docker login <REGISTRY>` and try again.")
+        raise DockerRegistryClient::AuthenticationError, "Please `docker login <REGISTRY>` and try again"
       elsif code != 200
-        abort("API version not recognized")
-      end
-    end
-    
-    def try_api(version)
-      code = APICall.new(ping_uri(version)).response_code
-      if code == 200
-        @api_version = version
-      elsif code == 401
-        code = init_auth(version)
-        if code == 200
-          @api_version = version
-        end
-      end
-      return code
-    end
-    
-    def init_auth(api_version)
-      @http_auth = DockerHttpAuth.new(docker_uri.registry)
-      if api_version == 'v2'
-        code = APICall.new(ping_v2_uri).response_code(http_auth)
-      elsif api_version == 'v1'
-        code = APICall.new(ping_v1_uri).response_code(http_auth)
+        raise DockerRegistryClient::APIVersionError, "Not recognized"
       end
     end
     
@@ -119,10 +93,10 @@ def base_uri
       "#{docker_uri.protocol}#{docker_uri.registry}"
     end
     
-    def ping_uri(version)
-      if version == 'v1'
+    def ping_uri
+      if api_version == 'v1'
         ping_v1_uri
-      elsif version == 'v2'
+      elsif api_version == 'v2'
         ping_v2_uri
       end
     end

From ed952c28b1923f802ae626e20ab1d5a35b48f8a8 Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 15:02:54 +1100
Subject: [PATCH 06/11] Make tags_found consistent

---
 lib/tagfish/tags.rb           | 16 +++++++---------
 lib/tagfish/tags_command.rb   | 26 ++++++++++++--------------
 lib/tagfish/update/updater.rb |  2 +-
 3 files changed, 20 insertions(+), 24 deletions(-)

diff --git a/lib/tagfish/tags.rb b/lib/tagfish/tags.rb
index 23ec8ab..3e97a5e 100644
--- a/lib/tagfish/tags.rb
+++ b/lib/tagfish/tags.rb
@@ -4,23 +4,21 @@
 module Tagfish
   class Tags
 
-    def initialize(tags)
-      @tags = tags
+    attr_reader :tag_map 
+    
+    def initialize(tag_map)
+      @tag_map = tag_map
     end
 
     def tag_names
-      @tags.keys.sort
+      tag_map.keys.sort
     end
 
     def latest_tag
-      tag_names.select do |tag_name|
-        (@tags[tag_name] == @tags["latest"]) && (tag_name != 'latest')
+      tag_names.detect do |tag_name|
+        (tag_map[tag_name] == tag_map["latest"]) && (tag_name != "latest")
       end
     end
 
-    def latest_tag_to_s
-      latest_tag.empty? ? nil : latest_tag[0]
-    end
-
   end
 end
diff --git a/lib/tagfish/tags_command.rb b/lib/tagfish/tags_command.rb
index 44dfb86..7383615 100644
--- a/lib/tagfish/tags_command.rb
+++ b/lib/tagfish/tags_command.rb
@@ -8,23 +8,21 @@ class TagsCommand < Clamp::Command
     option ["-s", "--short"], :flag, "only return tag, not full image path"
 
     def execute
-      tags_only = latest? ? false : true
       
       docker_uri = DockerURI.parse(repository)
       docker_api = DockerRegistryClient.for(docker_uri)
-      tags = docker_api.find_tags_by_repository(tags_only)
-
-      begin
-       tags_found = latest? ? tags.latest_tag : tags.tag_names
-      rescue Exception => e
-        puts e.message
-        return
-      end
-
-      if tags_found.size == 0
-        puts "ERROR: No image explicitly tagged in this Repository, " +
-                "only `latest` tag available."
-        return
+      
+      if latest?
+        tags = docker_api.find_tags_by_repository(false)
+        latest_tag = tags.latest_tag
+        if latest_tag.nil?
+          signal_error "No image explicitly tagged in this Repository, " +
+                  "only `latest` tag available."
+        end
+        tags_found = [latest_tag]
+      else
+        tags = docker_api.find_tags_by_repository(true)
+        tags_found = tags.tag_names
       end
 
       pretty_tags = tags_found.map do |tag_name|
diff --git a/lib/tagfish/update/updater.rb b/lib/tagfish/update/updater.rb
index d9ad995..e2252d1 100644
--- a/lib/tagfish/update/updater.rb
+++ b/lib/tagfish/update/updater.rb
@@ -40,7 +40,7 @@ def updatable?(uri)
       def update_uri(docker_uri)
         docker_api = DockerRegistryClient.for(docker_uri)
         tags = docker_api.find_tags_by_repository
-        newest_tag_name = tags.latest_tag_to_s
+        newest_tag_name = tags.latest_tag
         if newest_tag_name.nil?
           docker_uri
         else

From 782a8c625fccfcda1be323ff731f6a1e811f781b Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 15:31:31 +1100
Subject: [PATCH 07/11] Split v1 and v2 logic

---
 lib/tagfish/docker_registry_v1_client.rb    |  44 +++++++++
 lib/tagfish/docker_registry_v2_client.rb    |  50 ++++++++++
 lib/tagfish/docker_registry_vboth_client.rb | 102 --------------------
 3 files changed, 94 insertions(+), 102 deletions(-)

diff --git a/lib/tagfish/docker_registry_v1_client.rb b/lib/tagfish/docker_registry_v1_client.rb
index 9583e39..295b2fd 100644
--- a/lib/tagfish/docker_registry_v1_client.rb
+++ b/lib/tagfish/docker_registry_v1_client.rb
@@ -7,5 +7,49 @@ def api_version
       'v1'
     end
     
+    def find_tags_by_repository(tags_only=false)
+      tags_list = tags_v1_logic
+      Tagfish::Tags.new(tags_list)
+    end
+    
+    def tags_v1
+      APICall.new(tags_v1_uri).get_json(http_auth)
+    end
+    
+    def search_v1(keyword)
+      APICall.new(search_v1_uri(keyword)).get_json(http_auth)
+    end
+    
+    private
+    
+    def tags_v1_logic
+      tags_json = tags_v1
+      tags_v1_api(tags_json)
+    end
+    
+    def tags_v1_api(api_response_data)
+      case api_response_data
+        when Hash
+        api_response_data
+      when Array
+        api_response_data.reduce({}) do |images, tag|
+          images.merge({tag["name"] => tag["layer"]})
+        end
+      else
+        raise "unexpected type #{api_response_data.class}"
+      end
+    end
+    
+    def ping_uri
+      "#{base_uri}/v1/_ping"
+    end
+    
+    def search_v1_uri(keyword)
+      "#{base_uri}/v1/search?q=#{keyword}"  
+    end
+    
+    def tags_v1_uri
+      "#{base_uri}/v1/repositories/#{docker_uri.repository}/tags"
+    end
   end
 end
diff --git a/lib/tagfish/docker_registry_v2_client.rb b/lib/tagfish/docker_registry_v2_client.rb
index 6244ad2..09be6bb 100644
--- a/lib/tagfish/docker_registry_v2_client.rb
+++ b/lib/tagfish/docker_registry_v2_client.rb
@@ -6,6 +6,56 @@ class DockerRegistryV2Client < DockerRegistryVbothClient
     def api_version
       'v2'
     end
+    
+    def find_tags_by_repository(tags_only=false)
+      tags_list = tags_v2_logic(tags_only)
+      Tagfish::Tags.new(tags_list)
+    end
+    
+    def tags_v2
+      APICall.new(tags_v2_uri).get_json(http_auth)
+    end
+    
+    def hash_v2(tag)
+      APICall.new(hash_v2_uri(tag)).get_json(http_auth)
+    end
+    
+    def catalog_v2
+      APICall.new(catalog_v2_uri).get_json(http_auth)
+    end
 
+    private
+    
+    def tags_v2_logic(tags_only)
+      tags = tags_v2["tags"]
+      if tags.nil?
+        abort("No Tags found for this repository")
+      end
+      
+      tags_with_hashes = tags.inject({}) do |dict, tag|
+        if tags_only
+          dict[tag] = "dummy_hash"
+        else
+          dict[tag] = hash_v2(tag)["fsLayers"][0]["blobSum"]
+        end
+        dict
+      end
+    end
+      
+    def ping_uri
+      "#{base_uri}/v2/"
+    end
+
+    def catalog_v2_uri
+      "#{base_uri}/v2/_catalog"
+    end
+    
+    def tags_v2_uri
+      "#{base_uri}/v2/#{docker_uri.repository}/tags/list"  
+    end
+    
+    def hash_v2_uri(tag)
+      "#{base_uri}/v2/#{docker_uri.repository}/manifests/#{tag}"
+    end
   end
 end
diff --git a/lib/tagfish/docker_registry_vboth_client.rb b/lib/tagfish/docker_registry_vboth_client.rb
index d16dc88..9fdcf1d 100644
--- a/lib/tagfish/docker_registry_vboth_client.rb
+++ b/lib/tagfish/docker_registry_vboth_client.rb
@@ -24,110 +24,8 @@ def initialize(docker_uri)
       end
     end
     
-    def find_tags_by_repository(tags_only=false)
-      if api_version == 'v2'
-        tags_list = tags_v2_logic(tags_only)
-      else
-        tags_list = tags_v1_logic
-      end
-      Tagfish::Tags.new(tags_list)
-    end
-    
-    def tags_v1
-      APICall.new(tags_v1_uri).get_json(http_auth)
-    end
-    
-    def tags_v2
-      APICall.new(tags_v2_uri).get_json(http_auth)
-    end
-    
-    def hash_v2(tag)
-      APICall.new(hash_v2_uri(tag)).get_json(http_auth)
-    end
-    
-    def catalog_v2
-      APICall.new(catalog_v2_uri).get_json(http_auth)
-    end
-    
-    def search_v1(keyword)
-      APICall.new(search_v1_uri(keyword)).get_json(http_auth)
-    end
-    
-    private
-    
-    def tags_v1_logic
-      tags_json = tags_v1
-      tags_v1_api(tags_json)
-    end
-
-    def tags_v1_api(api_response_data)
-      case api_response_data
-      when Hash
-        api_response_data
-      when Array
-        api_response_data.reduce({}) do |images, tag|
-          images.merge({tag["name"] => tag["layer"]})
-        end
-      else
-        raise "unexpected type #{api_response_data.class}"
-      end
-    end
-
-    def tags_v2_logic(tags_only)
-      tags = tags_v2["tags"]
-      if tags.nil?
-        abort("No Tags found for this repository")
-      end
-      
-      tags_with_hashes = tags.inject({}) do |dict, tag|
-        if tags_only
-          dict[tag] = "dummy_hash"
-        else
-          dict[tag] = hash_v2(tag)["fsLayers"][0]["blobSum"]
-        end
-        dict
-      end
-    end
-    
     def base_uri
       "#{docker_uri.protocol}#{docker_uri.registry}"
     end
-    
-    def ping_uri
-      if api_version == 'v1'
-        ping_v1_uri
-      elsif api_version == 'v2'
-        ping_v2_uri
-      end
-    end
-    
-    def ping_v2_uri
-      "#{base_uri}/v2/"
-    end
-    
-    def ping_v1_uri
-      "#{base_uri}/v1/_ping"
-    end
-    
-    def catalog_v2_uri
-      "#{base_uri}/v2/_catalog"
-    end
-    
-    def search_v1_uri(keyword)
-      "#{base_uri}/v1/search?q=#{keyword}"  
-    end
-    
-    def tags_v1_uri
-      "#{base_uri}/v1/repositories/#{docker_uri.repository}/tags"
-    end
-    
-    def tags_v2_uri
-      "#{base_uri}/v2/#{docker_uri.repository}/tags/list"  
-    end
-    
-    def hash_v2_uri(tag)
-      "#{base_uri}/v2/#{docker_uri.repository}/manifests/#{tag}"
-    end
-    
   end
 end

From 6b91c98711ae93fb8024cd4302c8c4c62fbfa146 Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 15:42:52 +1100
Subject: [PATCH 08/11] Remove references to specific versions in sub-classes

---
 lib/tagfish/docker_registry_v1_client.rb | 21 +++++++----------
 lib/tagfish/docker_registry_v2_client.rb | 30 ++++++++++++------------
 2 files changed, 23 insertions(+), 28 deletions(-)

diff --git a/lib/tagfish/docker_registry_v1_client.rb b/lib/tagfish/docker_registry_v1_client.rb
index 295b2fd..fa82c56 100644
--- a/lib/tagfish/docker_registry_v1_client.rb
+++ b/lib/tagfish/docker_registry_v1_client.rb
@@ -8,26 +8,21 @@ def api_version
     end
     
     def find_tags_by_repository(tags_only=false)
-      tags_list = tags_v1_logic
+      tags_list = tags_api(tags)
       Tagfish::Tags.new(tags_list)
     end
     
-    def tags_v1
-      APICall.new(tags_v1_uri).get_json(http_auth)
+    def tags
+      APICall.new(tags_uri).get_json(http_auth)
     end
     
-    def search_v1(keyword)
-      APICall.new(search_v1_uri(keyword)).get_json(http_auth)
+    def search(keyword)
+      APICall.new(search_uri(keyword)).get_json(http_auth)
     end
     
     private
     
-    def tags_v1_logic
-      tags_json = tags_v1
-      tags_v1_api(tags_json)
-    end
-    
-    def tags_v1_api(api_response_data)
+    def tags_api(api_response_data)
       case api_response_data
         when Hash
         api_response_data
@@ -44,11 +39,11 @@ def ping_uri
       "#{base_uri}/v1/_ping"
     end
     
-    def search_v1_uri(keyword)
+    def search_uri(keyword)
       "#{base_uri}/v1/search?q=#{keyword}"  
     end
     
-    def tags_v1_uri
+    def tags_uri
       "#{base_uri}/v1/repositories/#{docker_uri.repository}/tags"
     end
   end
diff --git a/lib/tagfish/docker_registry_v2_client.rb b/lib/tagfish/docker_registry_v2_client.rb
index 09be6bb..7a187b1 100644
--- a/lib/tagfish/docker_registry_v2_client.rb
+++ b/lib/tagfish/docker_registry_v2_client.rb
@@ -8,35 +8,35 @@ def api_version
     end
     
     def find_tags_by_repository(tags_only=false)
-      tags_list = tags_v2_logic(tags_only)
+      tags_list = tags_logic(tags_only)
       Tagfish::Tags.new(tags_list)
     end
     
-    def tags_v2
-      APICall.new(tags_v2_uri).get_json(http_auth)
+    def tags
+      APICall.new(tags_uri).get_json(http_auth)
     end
     
-    def hash_v2(tag)
-      APICall.new(hash_v2_uri(tag)).get_json(http_auth)
+    def hash(tag)
+      APICall.new(hash_uri(tag)).get_json(http_auth)
     end
     
-    def catalog_v2
-      APICall.new(catalog_v2_uri).get_json(http_auth)
+    def catalog
+      APICall.new(catalog_uri).get_json(http_auth)
     end
 
     private
     
-    def tags_v2_logic(tags_only)
-      tags = tags_v2["tags"]
-      if tags.nil?
+    def tags_logic(tags_only)
+      tag_names = tags["tags"]
+      if tag_names.nil?
         abort("No Tags found for this repository")
       end
       
-      tags_with_hashes = tags.inject({}) do |dict, tag|
+      tags_with_hashes = tag_names.inject({}) do |dict, tag|
         if tags_only
           dict[tag] = "dummy_hash"
         else
-          dict[tag] = hash_v2(tag)["fsLayers"][0]["blobSum"]
+          dict[tag] = hash(tag)["fsLayers"][0]["blobSum"]
         end
         dict
       end
@@ -46,15 +46,15 @@ def ping_uri
       "#{base_uri}/v2/"
     end
 
-    def catalog_v2_uri
+    def catalog_uri
       "#{base_uri}/v2/_catalog"
     end
     
-    def tags_v2_uri
+    def tags_uri
       "#{base_uri}/v2/#{docker_uri.repository}/tags/list"  
     end
     
-    def hash_v2_uri(tag)
+    def hash_uri(tag)
       "#{base_uri}/v2/#{docker_uri.repository}/manifests/#{tag}"
     end
   end

From 9244bbc0e61c6c8bfe2a092cbef1cceb4d554e96 Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 16:18:39 +1100
Subject: [PATCH 09/11] Introduce tag_map and tag_names

---
 lib/tagfish/docker_registry_v1_client.rb    | 16 ++++++++--------
 lib/tagfish/docker_registry_vboth_client.rb |  9 +++++++++
 lib/tagfish/tags_command.rb                 |  5 ++---
 lib/tagfish/update/updater.rb               |  2 +-
 4 files changed, 20 insertions(+), 12 deletions(-)

diff --git a/lib/tagfish/docker_registry_v1_client.rb b/lib/tagfish/docker_registry_v1_client.rb
index fa82c56..87e3822 100644
--- a/lib/tagfish/docker_registry_v1_client.rb
+++ b/lib/tagfish/docker_registry_v1_client.rb
@@ -7,21 +7,21 @@ def api_version
       'v1'
     end
     
+    def search(keyword)
+      APICall.new(search_uri(keyword)).get_json(http_auth)
+    end
+    
+    private
+
     def find_tags_by_repository(tags_only=false)
       tags_list = tags_api(tags)
       Tagfish::Tags.new(tags_list)
     end
-    
+
     def tags
       APICall.new(tags_uri).get_json(http_auth)
     end
-    
-    def search(keyword)
-      APICall.new(search_uri(keyword)).get_json(http_auth)
-    end
-    
-    private
-    
+        
     def tags_api(api_response_data)
       case api_response_data
         when Hash
diff --git a/lib/tagfish/docker_registry_vboth_client.rb b/lib/tagfish/docker_registry_vboth_client.rb
index 9fdcf1d..ac9c688 100644
--- a/lib/tagfish/docker_registry_vboth_client.rb
+++ b/lib/tagfish/docker_registry_vboth_client.rb
@@ -27,5 +27,14 @@ def initialize(docker_uri)
     def base_uri
       "#{docker_uri.protocol}#{docker_uri.registry}"
     end
+
+    def tag_names
+      find_tags_by_repository(true).tag_names
+    end
+
+    def tag_map
+      find_tags_by_repository(false)
+    end
+    
   end
 end
diff --git a/lib/tagfish/tags_command.rb b/lib/tagfish/tags_command.rb
index 7383615..25d387a 100644
--- a/lib/tagfish/tags_command.rb
+++ b/lib/tagfish/tags_command.rb
@@ -13,7 +13,7 @@ def execute
       docker_api = DockerRegistryClient.for(docker_uri)
       
       if latest?
-        tags = docker_api.find_tags_by_repository(false)
+        tags = docker_api.tag_map
         latest_tag = tags.latest_tag
         if latest_tag.nil?
           signal_error "No image explicitly tagged in this Repository, " +
@@ -21,8 +21,7 @@ def execute
         end
         tags_found = [latest_tag]
       else
-        tags = docker_api.find_tags_by_repository(true)
-        tags_found = tags.tag_names
+        tags_found = docker_api.tag_names
       end
 
       pretty_tags = tags_found.map do |tag_name|
diff --git a/lib/tagfish/update/updater.rb b/lib/tagfish/update/updater.rb
index e2252d1..a90fe73 100644
--- a/lib/tagfish/update/updater.rb
+++ b/lib/tagfish/update/updater.rb
@@ -39,7 +39,7 @@ def updatable?(uri)
 
       def update_uri(docker_uri)
         docker_api = DockerRegistryClient.for(docker_uri)
-        tags = docker_api.find_tags_by_repository
+        tags = docker_api.tag_map
         newest_tag_name = tags.latest_tag
         if newest_tag_name.nil?
           docker_uri

From 117c9b421b1fecea588ddfa625ea1ad3c7bdb60c Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 16:22:44 +1100
Subject: [PATCH 10/11] Privatise

---
 lib/tagfish/docker_registry_v2_client.rb | 14 +++++++-------
 1 file changed, 7 insertions(+), 7 deletions(-)

diff --git a/lib/tagfish/docker_registry_v2_client.rb b/lib/tagfish/docker_registry_v2_client.rb
index 7a187b1..1ada972 100644
--- a/lib/tagfish/docker_registry_v2_client.rb
+++ b/lib/tagfish/docker_registry_v2_client.rb
@@ -7,10 +7,11 @@ def api_version
       'v2'
     end
     
-    def find_tags_by_repository(tags_only=false)
-      tags_list = tags_logic(tags_only)
-      Tagfish::Tags.new(tags_list)
+    def catalog
+      APICall.new(catalog_uri).get_json(http_auth)
     end
+
+    private
     
     def tags
       APICall.new(tags_uri).get_json(http_auth)
@@ -20,11 +21,10 @@ def hash(tag)
       APICall.new(hash_uri(tag)).get_json(http_auth)
     end
     
-    def catalog
-      APICall.new(catalog_uri).get_json(http_auth)
+    def find_tags_by_repository(tags_only=false)
+      tags_list = tags_logic(tags_only)
+      Tagfish::Tags.new(tags_list)
     end
-
-    private
     
     def tags_logic(tags_only)
       tag_names = tags["tags"]

From 79c23dc5cc12b1be9d65f89776f4305b40a9d536 Mon Sep 17 00:00:00 2001
From: clabbe <clement.labbe@rea-group.com>
Date: Thu, 25 Feb 2016 16:30:43 +1100
Subject: [PATCH 11/11] Push tag_names and tag_map into subclasses

---
 lib/tagfish/docker_registry_v1_client.rb    |  8 ++++++--
 lib/tagfish/docker_registry_v2_client.rb    | 22 ++++++++++-----------
 lib/tagfish/docker_registry_vboth_client.rb |  8 --------
 3 files changed, 16 insertions(+), 22 deletions(-)

diff --git a/lib/tagfish/docker_registry_v1_client.rb b/lib/tagfish/docker_registry_v1_client.rb
index 87e3822..e32a9b0 100644
--- a/lib/tagfish/docker_registry_v1_client.rb
+++ b/lib/tagfish/docker_registry_v1_client.rb
@@ -11,12 +11,16 @@ def search(keyword)
       APICall.new(search_uri(keyword)).get_json(http_auth)
     end
     
-    private
+    def tag_names
+      tag_map.tag_names
+    end
 
-    def find_tags_by_repository(tags_only=false)
+    def tag_map
       tags_list = tags_api(tags)
       Tagfish::Tags.new(tags_list)
     end
+    
+    private
 
     def tags
       APICall.new(tags_uri).get_json(http_auth)
diff --git a/lib/tagfish/docker_registry_v2_client.rb b/lib/tagfish/docker_registry_v2_client.rb
index 1ada972..9109665 100644
--- a/lib/tagfish/docker_registry_v2_client.rb
+++ b/lib/tagfish/docker_registry_v2_client.rb
@@ -10,6 +10,14 @@ def api_version
     def catalog
       APICall.new(catalog_uri).get_json(http_auth)
     end
+    
+    def tag_names
+      tags["tags"]
+    end
+
+    def tag_map
+      Tagfish::Tags.new(tags_logic)
+    end
 
     private
     
@@ -21,23 +29,13 @@ def hash(tag)
       APICall.new(hash_uri(tag)).get_json(http_auth)
     end
     
-    def find_tags_by_repository(tags_only=false)
-      tags_list = tags_logic(tags_only)
-      Tagfish::Tags.new(tags_list)
-    end
-    
-    def tags_logic(tags_only)
-      tag_names = tags["tags"]
+    def tags_logic
       if tag_names.nil?
         abort("No Tags found for this repository")
       end
       
       tags_with_hashes = tag_names.inject({}) do |dict, tag|
-        if tags_only
-          dict[tag] = "dummy_hash"
-        else
-          dict[tag] = hash(tag)["fsLayers"][0]["blobSum"]
-        end
+        dict[tag] = hash(tag)["fsLayers"][0]["blobSum"]
         dict
       end
     end
diff --git a/lib/tagfish/docker_registry_vboth_client.rb b/lib/tagfish/docker_registry_vboth_client.rb
index ac9c688..627f85f 100644
--- a/lib/tagfish/docker_registry_vboth_client.rb
+++ b/lib/tagfish/docker_registry_vboth_client.rb
@@ -28,13 +28,5 @@ def base_uri
       "#{docker_uri.protocol}#{docker_uri.registry}"
     end
 
-    def tag_names
-      find_tags_by_repository(true).tag_names
-    end
-
-    def tag_map
-      find_tags_by_repository(false)
-    end
-    
   end
 end