unquote resource id to support slash in it

Swift related meters can generate samples with special resource id
which contains slash, such as: 29f809d9-88bb-4c40-b1ba-a77a1fcf8ceb/glance.
If we query such resource directly, pecan will return 404 error,
but even end user encodes that special slash, we cannot response too.

This patch unquotes resource id in case it contains special characters.

Note that end user needs to use %252F to escape % character as well
to avoid pecan map slash to path delimiter.

Change-Id: I744b100524f19fabcc9fa68082c4cd235ca8445f
Close-Bug: #1500890
This commit is contained in:
ZhiQiang Fan 2015-10-20 12:25:23 -06:00
parent 3587ce9fdf
commit 44d57696ec
2 changed files with 31 additions and 0 deletions

View File

@ -19,6 +19,7 @@
# under the License.
import datetime
import urllib
import pecan
from pecan import rest
@ -120,6 +121,10 @@ class ResourcesController(rest.RestController):
"""
rbac.enforce('get_resource', pecan.request)
# In case we have special character in resource id, for example, swift
# can generate samples with resource id like
# 29f809d9-88bb-4c40-b1ba-a77a1fcf8ceb/glance
resource_id = urllib.unquote(resource_id)
authorized_project = rbac.get_limited_to_project(pecan.request.headers)
resources = list(pecan.request.storage_conn.get_resources(

View File

@ -234,6 +234,32 @@ class TestListResources(v2.FunctionalTest,
sources = [r['source'] for r in data]
self.assertEqual(['test_list_resources'], sources)
def test_resource_id_with_slash(self):
s = sample.Sample(
'storage.containers.objects',
'gauge',
'',
1,
'19fbed01c21f4912901057021b9e7111',
'45acc90399134206b3b41f3d3a0a06d6',
'29f809d9-88bb-4c40-b1ba-a77a1fcf8ceb/glance',
timestamp=datetime.datetime(2012, 7, 2, 10, 40).isoformat(),
resource_metadata={},
source='test_show_special_resource',
)
msg = utils.meter_message_from_counter(
s, self.CONF.publisher.telemetry_secret,
)
msg['timestamp'] = datetime.datetime(2012, 7, 2, 10, 40)
self.conn.record_metering_data(msg)
rid_encoded = '29f809d9-88bb-4c40-b1ba-a77a1fcf8ceb%252Fglance'
resp = self.get_json('/resources/%s' % rid_encoded)
self.assertEqual("19fbed01c21f4912901057021b9e7111", resp["user_id"])
self.assertEqual('29f809d9-88bb-4c40-b1ba-a77a1fcf8ceb/glance',
resp["resource_id"])
def test_with_invalid_resource_id(self):
sample1 = sample.Sample(
'instance',