Repository: docker/docker-py

Issue:
Fixed in #605 - Client.inspect_image("") behaves like Client.images()
``` py
>>> from os import environ
>>> from docker import Client
>>> c = Client(environ['DOCKER_HOST'])
>>> type(c.images())
<type 'list'>
>>> >>> len(c.images()) > 0
True
>>> c.inspect_image('') == c.images()
True
```

This isn't hard to see why. `inspect_image()` calls `/images/{image_id}/json`. `images()` calls `/images/json`. Where the `{image_id}` is an empty string, the [resulting URL](https://github.com/docker/docker-py/blob/bf00acf854a3b78335c1157f4a1a83488e611bb8/docker/client.py#L751) for the call to `inspect_image()` is `/images//json`:

``` sh
% [ "$( curl --location --post30{1,2,3} --silent 'http://<host>:2375/images//json' -H 'Content-Type: application/json' -H 'Accept: application/json' -X GET )" \
> = "$( curl --location --post30{1,2,3} --silent 'http://<host>:2375/images/json' -H 'Content-Type: application/json' -H 'Accept: application/json' -X GET )" ] \
> && echo 'SAME' || echo 'NOT THE SAME'
SAME
```

By analogy, I suspect the `inspect_container()` and `containers()` methods suffer from a similar problem.

The expected format of the `inspect_*()` methods (a detailed object) is different from the corresponding `*s()` methods (an array of summary objects), so it seems to me calling `inspect_*("")` should probably raise an exception. Maybe something like:

``` py
    @check_resource
    def inspect_container(self, container):
        ...
        if not container:
            raise ValueError('container ID required')
        ...

    @check_resource
    def inspect_image(self, image):
        ...
        if not image:
            raise ValueError('image ID required')
        ...
```

I can create a PR if desired.



Discussion:
Seems reasonable. Feel free to send a PR!


Resolving patch:
diff --git a/docker/client.py b/docker/client.py
--- a/docker/client.py
+++ b/docker/client.py
@@ -747,6 +747,8 @@ def inspect_container(self, container):
 
     @check_resource
     def inspect_image(self, image):
+        if isinstance(image, dict):
+            image = image.get('Id')
         return self._result(
             self._get(self._url("/images/{0}/json".format(image))),
             True
diff --git a/docker/utils/decorators.py b/docker/utils/decorators.py
--- a/docker/utils/decorators.py
+++ b/docker/utils/decorators.py
@@ -12,5 +12,7 @@ def wrapped(self, resource_id=None, *args, **kwargs):
                 raise errors.NullResource(
                     'image or container param is undefined'
                 )
+        if not resource_id:
+            raise ValueError('image or container param is empty')
         return f(self, resource_id, *args, **kwargs)
     return wrapped


Test patch:
diff --git a/tests/test.py b/tests/test.py
--- a/tests/test.py
+++ b/tests/test.py
@@ -1782,6 +1782,12 @@ def test_inspect_container(self):
         except Exception as e:
             self.fail('Command should not raise exception: {0}'.format(e))
 
+        try:
+            self.client.inspect_container('')
+        except ValueError as e:
+            self.assertEqual(e.args[0],
+                             'image or container param is empty')
+
         fake_request.assert_called_with(
             url_prefix + 'containers/3cc2351ab11b/json',
             timeout=DEFAULT_TIMEOUT_SECONDS
@@ -1953,6 +1959,12 @@ def test_inspect_image(self):
         except Exception as e:
             self.fail('Command should not raise exception: {0}'.format(e))
 
+        try:
+            self.client.inspect_image('')
+        except ValueError as e:
+            self.assertEqual(e.args[0],
+                             'image or container param is empty')
+
         fake_request.assert_called_with(
             url_prefix + 'images/test_image/json',
             timeout=DEFAULT_TIMEOUT_SECONDS