Skip to content

Commit 28a1c39

Browse files
authored
Some bug fixes for python client (#29)
* fixed bug with parsing python functions without any types, and bug where functions with multiple deployment receipts were getting mangled * whoops. uncommenting tests * last test fix
1 parent 03fd34c commit 28a1c39

File tree

6 files changed

+42
-13
lines changed

6 files changed

+42
-13
lines changed

polyapi/deployables.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -245,7 +245,7 @@ def update_deployment_comments(file_content: str, deployable: dict) -> str:
245245
if deployable['deployments']:
246246
deployment_comments = write_deploy_comments(deployable['deployments'])
247247
deployable['deploymentCommentRanges'] = [(0, len(deployment_comments) + 1)]
248-
file_content = f"{deployment_comments}{file_content}"
248+
file_content = f"{deployment_comments}\n{file_content}"
249249
return file_content
250250

251251
def update_deployable_function_comments(file_content: str, deployable: dict, disable_docs: bool = False) -> str:

polyapi/function_cli.py

-1
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,6 @@ def function_add_or_update(
5555
"code": code,
5656
"language": "python",
5757
"returnType": get_jsonschema_type(return_type),
58-
"returnTypeSchema": parsed["types"]["returns"]["typeSchema"],
5958
"arguments": [{**p, "key": p["name"], "type": get_jsonschema_type(p["type"]) } for p in parsed["types"]["params"]],
6059
"logsEnabled": logs_enabled,
6160
}

polyapi/parser.py

+7-6
Original file line numberDiff line numberDiff line change
@@ -181,7 +181,7 @@ def _get_schemas(code: str) -> List[Dict]:
181181

182182
def get_jsonschema_type(python_type: str):
183183
if python_type == "Any":
184-
return "Any"
184+
return "any"
185185

186186
if python_type == "List":
187187
return "array"
@@ -338,6 +338,7 @@ def parse_function_code(code: str, name: Optional[str] = "", context: Optional[s
338338
"params": [],
339339
"returns": {
340340
"type": "",
341+
"typeSchema": None,
341342
"description": "",
342343
}
343344
},
@@ -435,13 +436,14 @@ def _extract_docstring_from_function(self, node: ast.FunctionDef):
435436

436437
def _extract_deploy_comments(self):
437438
for i in range(len(self._lines)):
438-
line = self._lines[i].strip()
439+
line = self._lines[i]
439440
if line and not line.startswith("#"):
440441
return
441-
deployment = _parse_deploy_comment(line)
442+
deployment = _parse_deploy_comment(line.strip())
442443
if deployment:
444+
start = self._line_offsets[i]
443445
deployable["deployments"].append(deployment)
444-
deployable["deploymentCommentRanges"].append([self._line_offsets[i], len(line)])
446+
deployable["deploymentCommentRanges"].append([start, start + len(line)])
445447

446448
def visit_Import(self, node: ast.Import):
447449
# TODO maybe handle `import foo.bar` case?
@@ -471,8 +473,7 @@ def visit_FunctionDef(self, node: ast.FunctionDef):
471473
"type": python_type,
472474
"description": "",
473475
}
474-
if type_schema:
475-
json_arg["typeSchema"] = json.dumps(type_schema)
476+
json_arg["typeSchema"] = json.dumps(type_schema) if type_schema else None
476477

477478
if docstring_params:
478479
try:

pyproject.toml

+1-1
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ requires = ["setuptools>=61.2", "wheel"]
33

44
[project]
55
name = "polyapi-python"
6-
version = "0.3.2.dev1"
6+
version = "0.3.2.dev2"
77
description = "The Python Client for PolyAPI, the IPaaS by Developers for Developers"
88
authors = [{ name = "Dan Fellin", email = "dan@polyapi.io" }]
99
dependencies = [

tests/test_deployables.py

+11-1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ def foobar() -> int:
2121

2222
EXPECTED_SERVER_FN_DEPLOYMENTS = '''# Poly deployed @ 2024-11-12T14:43:22.631113 - testing.foobar - https://na1.polyapi.io/canopy/polyui/collections/server-functions/jh23h5g3h5b24jh5b2j3h45v2jhg43v52j3h - 086aedd
2323
# Poly deployed @ 2024-11-11T14:43:22.631113 - testing.foobar - https://dev.polyapi.io/canopy/polyui/collections/server-functions/jh23h5g3h5b24jh5b2j3h45v2jhg43v52j3h - 086aedd
24+
2425
from polyapi.typedefs import PolyServerFunction
2526
2627
polyConfig: PolyServerFunction = {
@@ -76,6 +77,15 @@ def foobar(foo: str, bar: Dict[str, str]) -> int:
7677
'''
7778

7879
class T(unittest.TestCase):
80+
def test_parse_and_write_deployment_comment(self):
81+
test_deployable = parse_function_code(EXPECTED_SERVER_FN_DEPLOYMENTS, "foobar")
82+
deployable_comment_ranges = test_deployable["deploymentCommentRanges"]
83+
updated_file_contents = update_deployment_comments(EXPECTED_SERVER_FN_DEPLOYMENTS, test_deployable)
84+
self.assertEqual(updated_file_contents, EXPECTED_SERVER_FN_DEPLOYMENTS)
85+
# Deployment comment ranges collapsed into one of equal size
86+
self.assertEqual(test_deployable["deploymentCommentRanges"][0][0], deployable_comment_ranges[0][0])
87+
self.assertEqual(test_deployable["deploymentCommentRanges"][0][1], deployable_comment_ranges[1][1])
88+
7989
def test_write_deployment_comment(self):
8090
test_deployable = {
8191
"deployments": [
@@ -98,7 +108,7 @@ def test_write_deployment_comment(self):
98108
'type': 'server-function'
99109
}
100110
],
101-
"deploymentCommentRanges": [[0, 178]]
111+
"deploymentCommentRanges": [[0, 177]]
102112
}
103113
updated_file_contents = update_deployment_comments(INITIAL_SERVER_FN_DEPLOYMENTS, test_deployable)
104114
self.assertEqual(updated_file_contents, EXPECTED_SERVER_FN_DEPLOYMENTS)

tests/test_parser.py

+22-3
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,11 @@
33
from polyapi.parser import parse_function_code
44

55

6+
CODE_NO_TYPES = """
7+
def foobar(a, b):
8+
return a + b
9+
"""
10+
611
SIMPLE_CODE = """
712
def foobar(n: int) -> int:
813
return 9
@@ -124,11 +129,21 @@ def foobar(foo: str, bar: Dict[str, str]) -> int:
124129
'''
125130

126131
class T(unittest.TestCase):
132+
def test_no_types(self):
133+
deployable = parse_function_code(CODE_NO_TYPES, "foobar")
134+
types = deployable["types"]
135+
self.assertEqual(len(types["params"]), 2)
136+
self.assertEqual(types["params"][0], {"name": "a", "type": "Any", "typeSchema": None, "description": ""})
137+
self.assertEqual(types["params"][1], {"name": "b", "type": "Any", "typeSchema": None, "description": ""})
138+
self.assertEqual(types["returns"]["type"], "Any")
139+
self.assertIsNone(types["returns"]["typeSchema"])
140+
self.assertEqual(deployable["dependencies"], [])
141+
127142
def test_simple_types(self):
128143
deployable = parse_function_code(SIMPLE_CODE, "foobar")
129144
types = deployable["types"]
130145
self.assertEqual(len(types["params"]), 1)
131-
self.assertEqual(types["params"][0], {"name": "n", "type": "int", "description": ""})
146+
self.assertEqual(types["params"][0], {"name": "n", "type": "int", "typeSchema": None, "description": ""})
132147
self.assertEqual(types["returns"]["type"], "int")
133148
self.assertIsNone(types["returns"]["typeSchema"])
134149
self.assertEqual(deployable["dependencies"], [])
@@ -137,7 +152,7 @@ def test_complex_return_type(self):
137152
deployable = parse_function_code(COMPLEX_RETURN_TYPE, "foobar")
138153
types = deployable["types"]
139154
self.assertEqual(len(types["params"]), 1)
140-
self.assertEqual(types["params"][0], {"name": "n", "type": "int", "description": ""})
155+
self.assertEqual(types["params"][0], {"name": "n", "type": "int", "typeSchema": None, "description": ""})
141156
self.assertEqual(types["returns"]["type"], "Barbar")
142157
self.assertEqual(types["returns"]["typeSchema"]['title'], "Barbar")
143158

@@ -153,7 +168,7 @@ def test_list_complex_return_type(self):
153168
deployable = parse_function_code(LIST_COMPLEX_RETURN_TYPE, "foobar")
154169
types = deployable["types"]
155170
self.assertEqual(len(types["params"]), 1)
156-
self.assertEqual(types["params"][0], {"name": "n", "type": "int", "description": ""})
171+
self.assertEqual(types["params"][0], {"name": "n", "type": "int", "typeSchema": None, "description": ""})
157172
self.assertEqual(types["returns"]["type"], "List[Barbar]")
158173
self.assertEqual(types["returns"]["typeSchema"]["items"]['title'], "Barbar")
159174

@@ -186,11 +201,13 @@ def test_parse_glide_server_function_bad_docstring(self):
186201
self.assertEqual(deployable["types"]["params"][0], {
187202
"name": "foo",
188203
"type": "Any",
204+
"typeSchema": None,
189205
"description": "The foo in question"
190206
})
191207
self.assertEqual(deployable["types"]["params"][1], {
192208
"name": "bar",
193209
"type": "Any",
210+
"typeSchema": None,
194211
"description": "Configuration of bars"
195212
})
196213
self.assertEqual(deployable["types"]["returns"], {
@@ -205,11 +222,13 @@ def test_parse_glide_server_function_ok_docstring(self):
205222
self.assertEqual(deployable["types"]["params"][0], {
206223
"name": "foo",
207224
"type": "str",
225+
"typeSchema": None,
208226
"description": "The foo in question"
209227
})
210228
self.assertEqual(deployable["types"]["params"][1], {
211229
"name": "bar",
212230
"type": "Dict[str, str]",
231+
"typeSchema": None,
213232
"description": "Configuration of bars"
214233
})
215234
self.assertEqual(deployable["types"]["returns"], {

0 commit comments

Comments
 (0)