blob: 430858953979e133ded26ac75a4d164b06ce1433 [file] [log] [blame]
ZhiQiang Fan39f97222013-09-20 04:49:44 +08001# Copyright 2012 OpenStack Foundation
dwalleck5d734432012-10-04 01:11:47 -05002# All Rights Reserved.
3#
4# Licensed under the Apache License, Version 2.0 (the "License"); you may
5# not use this file except in compliance with the License. You may obtain
6# a copy of the License at
7#
8# http://www.apache.org/licenses/LICENSE-2.0
9#
10# Unless required by applicable law or agreed to in writing, software
11# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13# License for the specific language governing permissions and limitations
14# under the License.
15
16import json
Matthew Treinish26dd0fa2012-12-04 17:14:37 -050017import urllib
dwalleck5d734432012-10-04 01:11:47 -050018
19from tempest.common.rest_client import RestClient
Matthew Treinish684d8992014-01-30 16:27:40 +000020from tempest import config
21
22CONF = config.CONF
dwalleck5d734432012-10-04 01:11:47 -050023
24
25class ContainerClient(RestClient):
Matthew Treinish684d8992014-01-30 16:27:40 +000026 def __init__(self, username, password, auth_url, tenant_name=None):
27 super(ContainerClient, self).__init__(username, password,
dwalleck5d734432012-10-04 01:11:47 -050028 auth_url, tenant_name)
29
Attila Fazekasa8b5fe72013-08-01 16:59:06 +020030 # Overwrites json-specific header encoding in RestClient
dwalleck5d734432012-10-04 01:11:47 -050031 self.headers = {}
Matthew Treinish684d8992014-01-30 16:27:40 +000032 self.service = CONF.object_storage.catalog_type
dwalleck5d734432012-10-04 01:11:47 -050033 self.format = 'json'
34
35 def create_container(self, container_name, metadata=None,
36 metadata_prefix='X-Container-Meta-'):
37 """
38 Creates a container, with optional metadata passed in as a
Chang Bo Guocc1623c2013-09-13 20:11:27 -070039 dictionary
dwalleck5d734432012-10-04 01:11:47 -050040 """
Matthew Treinish26dd0fa2012-12-04 17:14:37 -050041 url = str(container_name)
dwalleck5d734432012-10-04 01:11:47 -050042 headers = {}
43
44 if metadata is not None:
45 for key in metadata:
46 headers[metadata_prefix + key] = metadata[key]
47
48 resp, body = self.put(url, body=None, headers=headers)
49 return resp, body
50
51 def delete_container(self, container_name):
Sean Daguef237ccb2013-01-04 15:19:14 -050052 """Deletes the container (if it's empty)."""
Matthew Treinish26dd0fa2012-12-04 17:14:37 -050053 url = str(container_name)
dwalleck5d734432012-10-04 01:11:47 -050054 resp, body = self.delete(url)
55 return resp, body
56
57 def update_container_metadata(self, container_name, metadata,
58 metadata_prefix='X-Container-Meta-'):
Sean Daguef237ccb2013-01-04 15:19:14 -050059 """Updates arbitrary metadata on container."""
Matthew Treinish26dd0fa2012-12-04 17:14:37 -050060 url = str(container_name)
dwalleck5d734432012-10-04 01:11:47 -050061 headers = {}
62
63 if metadata is not None:
64 for key in metadata:
65 headers[metadata_prefix + key] = metadata[key]
66
67 resp, body = self.post(url, body=None, headers=headers)
Larisa Ustalov6c3c7802012-11-05 12:25:19 +020068 return resp, body
dwalleck5d734432012-10-04 01:11:47 -050069
Larisa Ustalov6c3c7802012-11-05 12:25:19 +020070 def delete_container_metadata(self, container_name, metadata,
71 metadata_prefix='X-Remove-Container-Meta-'):
Sean Daguef237ccb2013-01-04 15:19:14 -050072 """Deletes arbitrary metadata on container."""
Matthew Treinish26dd0fa2012-12-04 17:14:37 -050073 url = str(container_name)
Larisa Ustalov6c3c7802012-11-05 12:25:19 +020074 headers = {}
75
76 if metadata is not None:
77 for item in metadata:
78 headers[metadata_prefix + item] = 'x'
79
80 resp, body = self.post(url, body=None, headers=headers)
81 return resp, body
82
83 def list_container_metadata(self, container_name):
84 """
85 Retrieves container metadata headers
86 """
Matthew Treinish26dd0fa2012-12-04 17:14:37 -050087 url = str(container_name)
Chmouel Boudjnahdcf40ea2014-01-06 18:35:34 -080088 resp, body = self.head(url)
Larisa Ustalov6c3c7802012-11-05 12:25:19 +020089 return resp, body
dwalleck5d734432012-10-04 01:11:47 -050090
91 def list_all_container_objects(self, container, params=None):
92 """
93 Returns complete list of all objects in the container, even if
94 item count is beyond 10,000 item listing limit.
Chang Bo Guocc1623c2013-09-13 20:11:27 -070095 Does not require any parameters aside from container name.
dwalleck5d734432012-10-04 01:11:47 -050096 """
Chang Bo Guocc1623c2013-09-13 20:11:27 -070097 # TODO(dwalleck): Rewrite using json format to avoid newlines at end of
Attila Fazekasa8b5fe72013-08-01 16:59:06 +020098 # obj names. Set limit to API limit - 1 (max returned items = 9999)
dwalleck5d734432012-10-04 01:11:47 -050099 limit = 9999
dwalleck5d734432012-10-04 01:11:47 -0500100 if params is not None:
101 if 'limit' in params:
102 limit = params['limit']
103
104 if 'marker' in params:
105 limit = params['marker']
106
107 resp, objlist = self.list_container_contents(container,
108 params={'limit': limit})
109 return objlist
110 """tmp = []
111 for obj in objlist:
112 tmp.append(obj['name'])
113 objlist = tmp
114
115 if len(objlist) >= limit:
116
Attila Fazekasa8b5fe72013-08-01 16:59:06 +0200117 # Increment marker
dwalleck5d734432012-10-04 01:11:47 -0500118 marker = objlist[len(objlist) - 1]
119
Attila Fazekasa8b5fe72013-08-01 16:59:06 +0200120 # Get the next chunk of the list
dwalleck5d734432012-10-04 01:11:47 -0500121 objlist.extend(_list_all_container_objects(container,
122 params={'marker': marker,
123 'limit': limit}))
124 return objlist
125 else:
Attila Fazekasa8b5fe72013-08-01 16:59:06 +0200126 # Return final, complete list
dwalleck5d734432012-10-04 01:11:47 -0500127 return objlist"""
128
129 def list_container_contents(self, container, params=None):
130 """
131 List the objects in a container, given the container name
132
133 Returns the container object listing as a plain text list, or as
134 xml or json if that option is specified via the 'format' argument.
135
136 Optional Arguments:
137 limit = integer
138 For an integer value n, limits the number of results to at most
139 n values.
140
141 marker = 'string'
142 Given a string value x, return object names greater in value
143 than the specified marker.
144
145 prefix = 'string'
146 For a string value x, causes the results to be limited to names
147 beginning with the substring x.
148
149 format = 'json' or 'xml'
150 Specify either json or xml to return the respective serialized
151 response.
152 If json, returns a list of json objects
153 if xml, returns a string of xml
154
155 path = 'string'
156 For a string value x, return the object names nested in the
157 pseudo path (assuming preconditions are met - see below).
158
159 delimiter = 'character'
160 For a character c, return all the object names nested in the
161 container (without the need for the directory marker objects).
162 """
163
164 url = str(container)
Matthew Treinish26dd0fa2012-12-04 17:14:37 -0500165 url += '?format=%s' % self.format
166 if params:
167 url += '&%s' % urllib.urlencode(params)
dwalleck5d734432012-10-04 01:11:47 -0500168
169 resp, body = self.get(url)
170 body = json.loads(body)
171 return resp, body