forked from p15670423/monkey
Island: Handle duplicate url parameter edge case in FlaskDIWrapper
This commit is contained in:
parent
108c86d56c
commit
4b9fe6a83d
|
@ -1,4 +1,5 @@
|
||||||
import os
|
import os
|
||||||
|
import re
|
||||||
import uuid
|
import uuid
|
||||||
from datetime import timedelta
|
from datetime import timedelta
|
||||||
from typing import Iterable, Type
|
from typing import Iterable, Type
|
||||||
|
@ -113,6 +114,8 @@ class FlaskDIWrapper:
|
||||||
class URLAlreadyExistsError(Exception):
|
class URLAlreadyExistsError(Exception):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
url_parameter_regex = re.compile(r"<.*?:.*?>")
|
||||||
|
|
||||||
def __init__(self, api: flask_restful.Api, container: DIContainer):
|
def __init__(self, api: flask_restful.Api, container: DIContainer):
|
||||||
self._api = api
|
self._api = api
|
||||||
self._container = container
|
self._container = container
|
||||||
|
@ -125,7 +128,7 @@ class FlaskDIWrapper:
|
||||||
self._api.add_resource(resource, *resource.urls, resource_class_args=dependencies)
|
self._api.add_resource(resource, *resource.urls, resource_class_args=dependencies)
|
||||||
|
|
||||||
def _register_unique_urls(self, urls: Iterable[str]):
|
def _register_unique_urls(self, urls: Iterable[str]):
|
||||||
for url in map(lambda x: x.rstrip("/"), urls):
|
for url in map(FlaskDIWrapper._format_url, urls):
|
||||||
if url in self._registered_urls:
|
if url in self._registered_urls:
|
||||||
raise FlaskDIWrapper.URLAlreadyExistsError(
|
raise FlaskDIWrapper.URLAlreadyExistsError(
|
||||||
f"URL {url} has already been registered!"
|
f"URL {url} has already been registered!"
|
||||||
|
@ -133,6 +136,11 @@ class FlaskDIWrapper:
|
||||||
|
|
||||||
self._registered_urls.add(url)
|
self._registered_urls.add(url)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def _format_url(url: str):
|
||||||
|
new_url = url.rstrip("/")
|
||||||
|
return FlaskDIWrapper.url_parameter_regex.sub("<PARAMETER_PLACEHOLDER>", new_url)
|
||||||
|
|
||||||
|
|
||||||
def init_api_resources(api: FlaskDIWrapper):
|
def init_api_resources(api: FlaskDIWrapper):
|
||||||
api.add_resource(Root)
|
api.add_resource(Root)
|
||||||
|
|
|
@ -35,6 +35,24 @@ def test_duplicate_urls(resource_mng):
|
||||||
resource_mng.add_resource(resource2)
|
resource_mng.add_resource(resource2)
|
||||||
|
|
||||||
|
|
||||||
|
def test_duplicate_urls__parameters(resource_mng):
|
||||||
|
resource1 = get_mock_resource("res1", ["/url/<string:param1>"])
|
||||||
|
resource2 = get_mock_resource("res2", ["/url/<string:param2>"])
|
||||||
|
|
||||||
|
resource_mng.add_resource(resource1)
|
||||||
|
with pytest.raises(FlaskDIWrapper.URLAlreadyExistsError):
|
||||||
|
resource_mng.add_resource(resource2)
|
||||||
|
|
||||||
|
|
||||||
|
def test_duplicate_urls__multiple_parameters(resource_mng):
|
||||||
|
resource1 = get_mock_resource("res1", ["/url/<string:agent_name>/<string:param>"])
|
||||||
|
resource2 = get_mock_resource("res2", ["/url/<int:agent_id>/<string:param>"])
|
||||||
|
|
||||||
|
resource_mng.add_resource(resource1)
|
||||||
|
with pytest.raises(FlaskDIWrapper.URLAlreadyExistsError):
|
||||||
|
resource_mng.add_resource(resource2)
|
||||||
|
|
||||||
|
|
||||||
def test_adding_resources(resource_mng):
|
def test_adding_resources(resource_mng):
|
||||||
resource = get_mock_resource("res1", ["/url"])
|
resource = get_mock_resource("res1", ["/url"])
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue