feat(doit): uri-template generation works

This doesn't mean it's correctly implemented, but we are on our way.
It does compile, at least
This commit is contained in:
Sebastian Thiel
2015-03-17 18:27:25 +01:00
parent 863a98c0d7
commit 54eb784a55
2 changed files with 38 additions and 4 deletions

View File

@@ -415,11 +415,26 @@ match result {
seen = set()
replacements = list()
all_required_param_name = set(p.name for p in params if is_required_property(p))
MULTI_SLASH = 'multi-slash-prefix'
URL_ENCODE = 'url-encode'
special_cases = set()
for possible_url in possible_urls:
for s in re_find_replacements.findall(possible_url):
if s in seen: continue
seen.add(s)
sn = s[1:-1]
# NOTE: We only handle the cases that are actually used in the schemas. If this shouldn't
# be worth it anymore (i.e. too many cases), then we should use a uri-template library
# to handle this at runtime, possibly, or use a python uri-template library, to more easily
# handle the required cases. Whatever is less work, I guess.
if sn.startswith('/') and sn.endswith('*'):
sn = sn[1:-1]
special_cases.add(MULTI_SLASH)
elif sn.startswith('+'):
sn = sn[1:]
special_cases.add(URL_ENCODE)
assert sn in all_required_param_name, "Expected param '%s' to be in required parameter list for substitution" % sn
replacements.append((s, sn))
# end for each found substitution
@@ -429,6 +444,12 @@ match result {
assert '{' not in possible_url, "Failed to replace all fields in '%s', have to parse expressions" % possible_url
# end for each possible url
del seen
def add_to_params(p):
for s, pname in replacements:
if pname == p.name:
return False
return True
%>
/// Perform the operation you have build so far.
${action_fn} {
@@ -439,6 +460,7 @@ match result {
pname = 'self.' + property(p.name) # property identifier
%>\
## parts can also be derived from the request, but we do that only if it's not set
% if add_to_params(p):
% if p.name == 'part' and request_value:
% if not is_required_property(p):
if ${pname}.is_none() {
@@ -448,8 +470,8 @@ match result {
if ${pname}.len() == 0 {
${pname} = self.${property(REQUEST_VALUE_PROPERTY_NAME)}.to_parts();
}
% endif
% endif
% endif ## not is_required_property(p):
% endif ## p.name == 'part' and request_value:
% if p.get('repeated', False):
if ${pname}.len() > 0 {
let mut s = String::new();
@@ -465,6 +487,7 @@ match result {
% else:
params.push(("${p.name}", ${pname}.to_string()));
% endif
% endif ## add_to_params(p)
% endfor
## Additional params - may not overlap with optional params
for &field in [${', '.join(enclose_in('"', (p.name for p in field_params)))}].iter() {

View File

@@ -10,7 +10,7 @@ re_linestart = re.compile('^', flags=re.MULTILINE)
re_first_4_spaces = re.compile('^ {1,4}', flags=re.MULTILINE)
re_desc_parts = re.compile("((the part (names|properties) that you can include in the parameter value are)|(supported values are ))(.*?)\.", flags=re.IGNORECASE|re.MULTILINE)
re_find_replacements = re.compile("\{\w+\}")
re_find_replacements = re.compile("\{[/\+]?\w+\*?\}")
@@ -330,7 +330,7 @@ def to_rust_type(schemas, sn, pn, t, allow_optionals=True):
rust_type = 'i64'
elif rust_type == USE_FORMAT:
rust_type = TYPE_MAP[t.format]
if t.get('repeated', False):
rust_type = 'Vec<%s>' % rust_type
else:
@@ -938,6 +938,17 @@ if __name__ == '__main__':
assert ms[0].group(0) == '{groupId}'
assert ms[1].group(0) == '{foo}'
url = "customer/{customerId}/orgunits{/orgUnitPath*}"
ms = list(re_find_replacements.findall(url))
assert len(ms) == 2
assert ms[0] == '{customerId}'
assert ms[1] == '{/orgUnitPath*}'
url = "{+project}/subscriptions"
ms = list(re_find_replacements.findall(url))
assert len(ms) == 1
assert ms[0] == '{+project}'
test_to_version()
test_library_name()
test_url_substitution()