aplos-nca-saas-sdk 0.0.11__py3-none-any.whl → 0.0.12__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (28) hide show
  1. aplos_nca_saas_sdk/aws_resources/aws_cognito.py +11 -5
  2. aplos_nca_saas_sdk/integration_testing/configs/{app_settings.py → app_settings_config.py} +8 -8
  3. aplos_nca_saas_sdk/integration_testing/configs/config_sample.json +27 -14
  4. aplos_nca_saas_sdk/integration_testing/configs/file_upload_config.py +94 -0
  5. aplos_nca_saas_sdk/integration_testing/configs/{login.py → login_config.py} +23 -11
  6. aplos_nca_saas_sdk/integration_testing/configs/nca_execution_config.py +186 -0
  7. aplos_nca_saas_sdk/integration_testing/files/executions/config1.json +46 -0
  8. aplos_nca_saas_sdk/integration_testing/integration_test_base.py +8 -1
  9. aplos_nca_saas_sdk/integration_testing/integration_test_configurations.py +10 -6
  10. aplos_nca_saas_sdk/integration_testing/main.py +1 -2
  11. aplos_nca_saas_sdk/integration_testing/tests/app_login_test.py +1 -1
  12. aplos_nca_saas_sdk/integration_testing/tests/file_upload_test.py +13 -10
  13. aplos_nca_saas_sdk/integration_testing/tests/nca_analysis_test.py +89 -0
  14. aplos_nca_saas_sdk/nca_resources/{nca_executions.py → nca_analysis.py} +148 -87
  15. aplos_nca_saas_sdk/nca_resources/nca_file_upload.py +5 -5
  16. aplos_nca_saas_sdk/nca_resources/nca_login.py +4 -4
  17. aplos_nca_saas_sdk/utilities/commandline_args.py +6 -28
  18. aplos_nca_saas_sdk/utilities/environment_vars.py +7 -0
  19. aplos_nca_saas_sdk/utilities/file_utility.py +33 -0
  20. aplos_nca_saas_sdk/utilities/http_utility.py +22 -6
  21. aplos_nca_saas_sdk/version.py +1 -1
  22. {aplos_nca_saas_sdk-0.0.11.dist-info → aplos_nca_saas_sdk-0.0.12.dist-info}/METADATA +1 -1
  23. {aplos_nca_saas_sdk-0.0.11.dist-info → aplos_nca_saas_sdk-0.0.12.dist-info}/RECORD +26 -23
  24. aplos_nca_saas_sdk/integration_testing/configs/file_upload.py +0 -104
  25. aplos_nca_saas_sdk/integration_testing/tests/app_validation_test.py +0 -5
  26. /aplos_nca_saas_sdk/integration_testing/tests/{app_execution_test.py → validation_test.py} +0 -0
  27. {aplos_nca_saas_sdk-0.0.11.dist-info → aplos_nca_saas_sdk-0.0.12.dist-info}/WHEEL +0 -0
  28. {aplos_nca_saas_sdk-0.0.11.dist-info → aplos_nca_saas_sdk-0.0.12.dist-info}/licenses/LICENSE +0 -0
@@ -36,13 +36,12 @@ def main():
36
36
  )
37
37
  # load it so we can see what it looks like
38
38
  config.load(file_path=config_file)
39
-
39
+
40
40
  # override the configuration
41
41
  # override_config(config)
42
42
 
43
43
  its.test(test_config=config)
44
44
 
45
-
46
45
  def override_config(config: TestConfiguration):
47
46
  """Override the configuration for the tests"""
48
47
  username = os.getenv("TEST_USERNAME")
@@ -39,7 +39,7 @@ class TestAppLogin(IntegrationTestBase):
39
39
  token = nca_login.authenticate(
40
40
  username=login.username, password=login.password
41
41
  )
42
- test_response.response = token
42
+
43
43
  if not token:
44
44
  test_response.error = "Failed to authenticate"
45
45
 
@@ -6,11 +6,11 @@ Property of Aplos Analytics, Utah, USA
6
6
 
7
7
  import time
8
8
  from datetime import datetime, timedelta
9
- from typing import Any, Dict
9
+ from typing import Any, Dict, List
10
10
 
11
11
  import requests
12
12
  from aws_lambda_powertools import Logger
13
- from aplos_nca_saas_sdk.integration_testing.configs.login import Login
13
+ from aplos_nca_saas_sdk.integration_testing.configs.login_config import LoginConfig
14
14
  from aplos_nca_saas_sdk.integration_testing.integration_test_base import (
15
15
  IntegrationTestBase,
16
16
  )
@@ -35,28 +35,31 @@ class FileUploadTest(IntegrationTestBase):
35
35
 
36
36
  self.results.clear()
37
37
 
38
- for fileupload in self.config.file_uploads.list:
38
+ for file_upload in self.config.file_uploads.list:
39
39
  test_response: IntegrationTestResponse = IntegrationTestResponse()
40
40
  test_response.name = self.name
41
41
  try:
42
42
  # Confirm Login
43
- nca_login = self.__login(fileupload.login)
43
+ nca_login = self.__login(file_upload.login)
44
44
  if not nca_login.jwt:
45
45
  test_response.error = "Failed to authenticate"
46
46
  else:
47
47
  # Confirm Upload
48
48
  upload_response: Dict[str, Any] = self.__upload(
49
- nca_login, fileupload.filepath
49
+ nca_login, file_upload.file_path
50
50
  )
51
51
  if upload_response is None:
52
52
  test_response.error = "Failed to upload"
53
53
  else:
54
54
  # Confirm conversion and download
55
55
  # Allow time buffer so file data is available
56
+ file_id: str = upload_response.get("file_id", "")
57
+ if not file_id:
58
+ raise RuntimeError(
59
+ "Failed to get a file_id from the upload"
60
+ )
56
61
  time.sleep(3)
57
- self.__download(
58
- nca_login, upload_response.get("file_id"), test_response
59
- )
62
+ self.__download(nca_login, file_id, test_response)
60
63
 
61
64
  except Exception as e: # pylint: disable=w0718
62
65
  test_response.error = str(e)
@@ -65,7 +68,7 @@ class FileUploadTest(IntegrationTestBase):
65
68
 
66
69
  return self.success()
67
70
 
68
- def __login(self, login: Login) -> NCALogin:
71
+ def __login(self, login: LoginConfig) -> NCALogin:
69
72
  nca_login = NCALogin(aplos_saas_domain=login.domain)
70
73
  nca_login.authenticate(username=login.username, password=login.password)
71
74
  return nca_login
@@ -108,7 +111,7 @@ class FileUploadTest(IntegrationTestBase):
108
111
  while not complete:
109
112
  response = requests.get(file_info_endpoint, headers=headers, timeout=60)
110
113
  json_response: dict = response.json()
111
- errors = []
114
+ errors: List[Dict[str, Any]] = []
112
115
  errors.extend(json_response.get("errors") or [])
113
116
  status = json_response.get("workable_state")
114
117
  complete = status == "ready"
@@ -0,0 +1,89 @@
1
+ """
2
+ Copyright 2024 Aplos Analytics
3
+ All Rights Reserved. www.aplosanalytics.com LICENSED MATERIALS
4
+ Property of Aplos Analytics, Utah, USA
5
+ """
6
+
7
+ from pathlib import Path
8
+
9
+ from aws_lambda_powertools import Logger
10
+
11
+ from aplos_nca_saas_sdk.integration_testing.integration_test_base import (
12
+ IntegrationTestBase,
13
+ )
14
+ from aplos_nca_saas_sdk.integration_testing.integration_test_response import (
15
+ IntegrationTestResponse,
16
+ )
17
+ from aplos_nca_saas_sdk.nca_resources.nca_analysis import NCAAnalysis
18
+ from aplos_nca_saas_sdk.utilities.file_utility import FileUtility
19
+
20
+ logger = Logger(service="NCAAnalysisTest")
21
+
22
+
23
+ class NCAAnalysisTest(IntegrationTestBase):
24
+ """NCA Execution Test Container"""
25
+
26
+ def __init__(self):
27
+ super().__init__("nca-execution")
28
+
29
+ def test(self) -> bool:
30
+ """Test Engine Execution"""
31
+
32
+ self.results.clear()
33
+
34
+ for nca_execution_config in self.config.nca_executions.list:
35
+ test_response: IntegrationTestResponse = IntegrationTestResponse()
36
+ test_response.name = self.name
37
+
38
+ input_file_path = (
39
+ FileUtility.load_filepath(nca_execution_config.input_file_path),
40
+ )
41
+ logger.info(
42
+ {
43
+ "message": "Creating NCA Analysis Execution for input file.",
44
+ "path": input_file_path,
45
+ "path2": nca_execution_config.input_file_path,
46
+ }
47
+ )
48
+ try:
49
+ # Create new NCA Execution
50
+ nca_execution: NCAAnalysis = NCAAnalysis(
51
+ nca_execution_config.login.domain
52
+ )
53
+
54
+ # Initialize Configuration Data
55
+
56
+ # Execute, the execution should raise errors that will fail the test
57
+ logger.info({"message": "Invoking Execution"})
58
+ execution_response = nca_execution.execute(
59
+ username=nca_execution_config.login.username,
60
+ password=nca_execution_config.login.password,
61
+ input_file_path=FileUtility.load_filepath(
62
+ nca_execution_config.input_file_path
63
+ ),
64
+ config_data=nca_execution_config.config_data,
65
+ meta_data=nca_execution_config.meta_data,
66
+ wait_for_results=True,
67
+ output_directory=nca_execution_config.output_dir,
68
+ unzip_after_download=False,
69
+ )
70
+
71
+ # Verify Download
72
+ logger.info(
73
+ {"message": "Execution complete. Verifying results download."}
74
+ )
75
+
76
+ expected_output_file = execution_response.get("results", {}).get("file")
77
+ if expected_output_file is None:
78
+ raise RuntimeError(
79
+ "Expected populated output_file from NCAExecution was None."
80
+ )
81
+ elif not Path(expected_output_file).is_file():
82
+ raise RuntimeError("Expected downloaded file does not exist.")
83
+
84
+ except Exception as e: # pylint: disable=w0718
85
+ test_response.error = str(e)
86
+
87
+ self.results.append(test_response)
88
+
89
+ return self.success()
@@ -11,52 +11,61 @@ import zipfile
11
11
  from datetime import datetime, timedelta
12
12
  from pathlib import Path
13
13
  from typing import Any, Dict
14
-
14
+ from aws_lambda_powertools import Logger
15
15
  import requests
16
16
 
17
- from aplos_nca_saas_sdk.aws_resources.aws_cognito import CognitoAuthenication
17
+ from aplos_nca_saas_sdk.aws_resources.aws_cognito import CognitoAuthentication
18
18
  from aplos_nca_saas_sdk.aws_resources.aws_s3_presigned_upload import (
19
19
  S3PresignedUpload,
20
20
  )
21
21
  from aplos_nca_saas_sdk.utilities.commandline_args import CommandlineArgs
22
22
  from aplos_nca_saas_sdk.utilities.http_utility import HttpUtilities, Routes
23
+ from aplos_nca_saas_sdk.utilities.environment_vars import EnvironmentVars
24
+
25
+ logger = Logger()
26
+
27
+
28
+ class NCAAnalysis:
29
+ """NCA Analysis API Access"""
23
30
 
31
+ def __init__(self, api_domain: str) -> None:
32
+ self.__jwt: str
24
33
 
25
- class NCAEngine:
26
- """NCA Engine Access"""
34
+ if not api_domain:
35
+ raise ValueError("Missing Aplos Api Domain")
27
36
 
28
- def __init__(
29
- self, api_domain: str | None, cognito_client_id: str | None, region: str | None
30
- ) -> None:
31
- self.jwt: str
32
- self.access_token: str | None = None
33
- self.refresh_token: str | None = None
34
- self.__api_domain: str | None = api_domain
37
+ self.__api_domain: str = api_domain
35
38
  self.verbose: bool = False
39
+ self.__cognito: CognitoAuthentication | None = None
36
40
 
37
- self.cognito: CognitoAuthenication = CognitoAuthenication(
38
- client_id=cognito_client_id, region=region
39
- )
41
+ @property
42
+ def cognito(self) -> CognitoAuthentication:
43
+ """Gets the cognito authentication object"""
40
44
 
41
45
  if not self.__api_domain:
42
46
  raise RuntimeError(
43
- "Missing Aplos Api Domain. "
44
- "Pass in the api_domain as a command arg or set the APLOS_API_DOMAIN environment var."
47
+ "Missing Aplos Api Domain. Set the internal property of __api_domain first."
48
+ "This is required to make an authentication connection"
45
49
  )
46
50
 
51
+ if self.__cognito is None:
52
+ self.__cognito = CognitoAuthentication(
53
+ client_id=None, region=None, aplos_domain=self.__api_domain
54
+ )
55
+
56
+ return self.__cognito
57
+
47
58
  @property
48
59
  def api_root(self) -> str:
49
60
  """Gets the base url"""
50
61
  if self.__api_domain is None:
51
62
  raise RuntimeError("Missing Aplos Api Domain")
52
63
 
53
- url = HttpUtilities.build_url(self.__api_domain)
54
- if isinstance(url, str):
55
- return (
56
- f"{url}/tenants/{self.cognito.tenant_id}/users/{self.cognito.user_id}"
57
- )
64
+ url = HttpUtilities.build_url(
65
+ self.__api_domain, self.cognito.tenant_id, self.cognito.user_id
66
+ )
58
67
 
59
- raise RuntimeError("Missing Aplos Api Domain")
68
+ return url
60
69
 
61
70
  def execute(
62
71
  self,
@@ -67,59 +76,101 @@ class NCAEngine:
67
76
  *,
68
77
  meta_data: str | dict | None = None,
69
78
  wait_for_results: bool = True,
79
+ max_wait_in_seconds: int = 900,
70
80
  output_directory: str | None = None,
71
81
  unzip_after_download: bool = False,
72
- ) -> None:
73
- """_summary_
82
+ ) -> Dict[str, Any]:
83
+ """
84
+ Executes an analsysis.
85
+ - Uploads an analysis file.
86
+ - Adds the execution to the queue.
74
87
 
75
88
  Args:
76
89
  username (str): the username
77
90
  password (str): the users password
78
- input_file_path (str): the path to the input (anlysis) file
79
- config_data (dict): analysis configuration infomration
91
+ input_file_path (str): the path to the input (analysis) file
92
+ config_data (dict): analysis configuration information
80
93
  meta_data (str | dict | None, optional): meta data attached to the execution. Defaults to None.
81
94
  wait_for_results (bool, optional): should the program wait for results. Defaults to True.
82
- output_directory (str, optional): the output directory. Defaults to None (the local directy is used)
95
+ max_wait_in_seconds (int optional): the max time to wait for a download
96
+ output_directory (str, optional): the output directory. Defaults to None (the local directory is used)
83
97
  unzip_after_download (bool): Results are downloaded as a zip file, this option will unzip them automatically. Defaults to False
98
+
99
+ Returns:
100
+ Dict[str, Any]: The execution response. If you wait for the completion
84
101
  """
85
- if self.verbose:
86
- print("\tLogging in.")
87
- self.jwt = self.cognito.login(username=username, password=password)
88
102
 
89
- if self.verbose:
90
- print("\tUploading the analysis file.")
91
- uploader: S3PresignedUpload = S3PresignedUpload(self.jwt, str(self.api_root))
103
+ self.log(f"\tLogging into {self.__api_domain}.")
104
+
105
+ if not username:
106
+ raise ValueError("Missing username. Please provide a valid username.")
107
+ if not password:
108
+ raise ValueError("Missing password. Please provide a valid password.")
109
+
110
+ self.__jwt = self.cognito.login(username=username, password=password)
111
+
112
+ self.log("\tUploading the analysis file.")
113
+ uploader: S3PresignedUpload = S3PresignedUpload(self.__jwt, str(self.api_root))
92
114
  upload_response: Dict[str, Any] = uploader.upload_file(input_file_path)
93
115
 
94
- if self.verbose:
95
- print("\tStarting the execution.")
96
- execution_id = self.run_analysis(
97
- file_id=upload_response.get("file_id", ""),
116
+ file_id: str = upload_response.get("file_id", "")
117
+ if not file_id:
118
+ raise RuntimeError(
119
+ "Unexpected empty file_id when attempting to upload file."
120
+ )
121
+
122
+ self.log("\tAdding analyis to the queue.")
123
+ execution_response: Dict[str, Any] = self.__add_to_queue(
124
+ file_id=file_id,
98
125
  config_data=config_data,
99
126
  meta_data=meta_data,
100
127
  )
101
128
 
102
- if execution_id and wait_for_results:
129
+ execution_id: str = execution_response.get("execution_id", "")
130
+
131
+ response = {
132
+ "execution": execution_response,
133
+ "upload": upload_response,
134
+ "results": {"file": None},
135
+ }
136
+
137
+ if not execution_id:
138
+ raise RuntimeError(
139
+ "Unexpected empty execution_id when attempting to execute analysis."
140
+ )
141
+
142
+ if wait_for_results:
103
143
  # wait for it
104
- download_url = self.wait_for_results(execution_id=execution_id)
144
+ download_url = self.wait_for_results(
145
+ execution_id=execution_id, max_wait_in_seconds=max_wait_in_seconds
146
+ )
105
147
  # download the files
106
- if download_url:
107
- if self.verbose:
108
- print("\tDownloading the results.")
109
- self.download_file(
148
+ if download_url is None:
149
+ raise RuntimeError(
150
+ "Unexpected empty download_url when attempting to download results."
151
+ )
152
+ else:
153
+ self.log("\tDownloading the results.")
154
+ file_path = self.download_file(
110
155
  download_url,
111
156
  output_directory=output_directory,
112
157
  do_unzip=unzip_after_download,
113
158
  )
114
159
 
115
- def run_analysis(
160
+ response["results"]["file"] = file_path
161
+ else:
162
+ self.log("Bypassed results download.")
163
+
164
+ return response
165
+
166
+ def __add_to_queue(
116
167
  self,
117
168
  file_id: str,
118
169
  config_data: dict,
119
170
  meta_data: str | dict | None = None,
120
- ) -> str:
171
+ ) -> Dict[str, Any]:
121
172
  """
122
- Run the analysis
173
+ Adds the analysis to the execution queue.
123
174
 
124
175
  Args:
125
176
  bucket_name (str): s3 bucket name for your organization. this is returned to you
@@ -127,7 +178,7 @@ class NCAEngine:
127
178
  config_data (dict): the config_data for the analysis file
128
179
  meta_data (str | dict): Optional. Any meta data you'd like attached to this execution
129
180
  Returns:
130
- str: the execution id
181
+ Dict[str, Any]: the api response
131
182
  """
132
183
 
133
184
  if not file_id:
@@ -137,7 +188,7 @@ class NCAEngine:
137
188
  raise ValueError(
138
189
  "Missing config_data. Please provide a valid config_data."
139
190
  )
140
- headers = HttpUtilities.get_headers(self.jwt)
191
+ headers = HttpUtilities.get_headers(self.__jwt)
141
192
  # to start a new execution we need the location of the file (s3 bucket and object key)
142
193
  # you basic configuration
143
194
  # optional meta data
@@ -166,13 +217,13 @@ class NCAEngine:
166
217
  )
167
218
 
168
219
  execution_id = str(json_response.get("execution_id"))
169
- if self.verbose:
170
- print(f"\tExecution {execution_id} started.")
171
220
 
172
- return execution_id
221
+ self.log(f"\tExecution {execution_id} started.")
222
+
223
+ return json_response
173
224
 
174
225
  def wait_for_results(
175
- self, execution_id: str, max_wait_in_minutes: int = 15
226
+ self, execution_id: str, max_wait_in_seconds: float = 900
176
227
  ) -> str | None:
177
228
  """
178
229
  Wait for results
@@ -185,10 +236,10 @@ class NCAEngine:
185
236
 
186
237
  url = f"{self.api_root}/{Routes.NCA_EXECUTIONS}/{execution_id}"
187
238
 
188
- headers = HttpUtilities.get_headers(self.jwt)
239
+ headers = HttpUtilities.get_headers(self.__jwt)
189
240
  current_time = datetime.now()
190
241
  # Create a timedelta object representing 15 minutes
191
- time_delta = timedelta(minutes=max_wait_in_minutes)
242
+ time_delta = timedelta(seconds=max_wait_in_seconds)
192
243
 
193
244
  # Add the timedelta to the current time
194
245
  max_time = current_time + time_delta
@@ -205,8 +256,7 @@ class NCAEngine:
205
256
  if status == "failed" or complete:
206
257
  break
207
258
  if not complete:
208
- if self.verbose:
209
- print(f"\t\twaiting for results.... {status}: {elapsed}")
259
+ self.log(f"\t\twaiting for results.... {status}: {elapsed}")
210
260
  time.sleep(5)
211
261
  if datetime.now() > max_time:
212
262
  status = "timeout"
@@ -217,16 +267,13 @@ class NCAEngine:
217
267
  break
218
268
 
219
269
  if status == "complete":
220
- if self.verbose:
221
- print("\tExecution complete.")
222
- print(f"\tExecution duration = {elapsed}.")
270
+ self.log("\tExecution complete.")
271
+ self.log(f"\tExecution duration = {elapsed}.")
223
272
  return json_response["presigned"]["url"]
224
273
  else:
225
- if self.verbose:
226
- print(
227
- f"\tExecution failed. Execution ID = {execution_id}. reason: {json_response.get('errors')}"
228
- )
229
- return None
274
+ raise RuntimeError(
275
+ f"\tExecution failed. Execution ID = {execution_id}. reason: {json_response.get('errors')}"
276
+ )
230
277
 
231
278
  def download_file(
232
279
  self,
@@ -249,31 +296,47 @@ class NCAEngine:
249
296
  output_directory = str(Path(__file__).parent.parent)
250
297
  output_directory = os.path.join(output_directory, ".aplos-nca-output")
251
298
 
252
- if presigned_download_url:
253
- output_file = f"results-{time.strftime('%Y-%m-%d-%Hh%Mm%Ss')}.zip"
299
+ if EnvironmentVars.is_running_in_aws_lambda():
300
+ # /tmp is the only directory we can write to unless we mount an external drive
301
+ # TODO: allow for external mapped drives, perhaps test if we can write to it
254
302
 
255
- output_file = os.path.join(output_directory, output_file)
256
- os.makedirs(output_directory, exist_ok=True)
303
+ output_directory = os.path.join("/tmp", ".aplos-nca-output")
257
304
 
258
- response = requests.get(presigned_download_url, timeout=60)
259
- # write the zip to a file
260
- with open(output_file, "wb") as f:
261
- f.write(response.content)
305
+ self.log(
306
+ f"\t\tRunning in AWS Lambda. Setting output directory to {output_directory}"
307
+ )
262
308
 
263
- # optionally, extract all the files from the zip
264
- if do_unzip:
265
- with zipfile.ZipFile(output_file, "r") as zip_ref:
266
- zip_ref.extractall(output_file.replace(".zip", ""))
309
+ output_file = f"results-{time.strftime('%Y-%m-%d-%Hh%Mm%Ss')}.zip"
267
310
 
268
- unzipped_state = "and unzipped" if do_unzip else "in zip format"
311
+ output_file = os.path.join(output_directory, output_file)
312
+ os.makedirs(output_directory, exist_ok=True)
269
313
 
270
- if self.verbose:
271
- print(f"\tResults file downloaded {unzipped_state}.")
272
- print(f"\t\tResults are available in: {output_directory}")
314
+ response = requests.get(presigned_download_url, timeout=60)
315
+ # write the zip to a file
316
+ with open(output_file, "wb") as f:
317
+ f.write(response.content)
273
318
 
274
- return output_directory
275
- else:
276
- return None
319
+ # optionally, extract all the files from the zip
320
+ if do_unzip:
321
+ with zipfile.ZipFile(output_file, "r") as zip_ref:
322
+ zip_ref.extractall(output_file.replace(".zip", ""))
323
+
324
+ unzipped_state = "and unzipped" if do_unzip else "in zip format"
325
+
326
+ self.log(f"\tResults file downloaded {unzipped_state}.")
327
+ self.log(f"\t\tResults are available in: {output_directory}")
328
+
329
+ return output_file
330
+
331
+ def log(self, message: str | Dict[str, Any]):
332
+ """Log the message"""
333
+ logger.debug(message)
334
+
335
+ if isinstance(message, dict):
336
+ message = json.dumps(message, indent=2)
337
+
338
+ if self.verbose:
339
+ print(message)
277
340
 
278
341
 
279
342
  def main():
@@ -292,10 +355,8 @@ def main():
292
355
  print("Missing some arguments.")
293
356
  exit()
294
357
 
295
- engine = NCAEngine(
296
- api_domain=args.api_domain,
297
- cognito_client_id=args.cognito_client_id,
298
- region=args.aws_region,
358
+ engine = NCAAnalysis(
359
+ api_domain=str(args.api_domain),
299
360
  )
300
361
 
301
362
  print("\tLoading analysis configurations")
@@ -17,7 +17,7 @@ class NCAFileUpload:
17
17
  if nca_login is None or nca_login.jwt is None or not nca_login.jwt:
18
18
  raise ValueError("Authenticated nca_login is required.")
19
19
 
20
- self.__api_domain: str = nca_login.domain
20
+ self.__api_domain: str = nca_login.domain or ""
21
21
  self.__tenant_id: str = nca_login.cognito.tenant_id
22
22
  self.__user_id: str = nca_login.cognito.user_id
23
23
  self.__jwt: str = nca_login.jwt
@@ -29,11 +29,11 @@ class NCAFileUpload:
29
29
  if self.__api_domain is None:
30
30
  raise RuntimeError("Missing Aplos Api Domain")
31
31
 
32
- url = HttpUtilities.build_url(self.__api_domain)
33
- if isinstance(url, str):
34
- return f"{url}/tenants/{self.__tenant_id}/users/{self.__user_id}"
32
+ url = HttpUtilities.build_url(
33
+ self.__api_domain, self.__tenant_id, self.__user_id
34
+ )
35
35
 
36
- raise RuntimeError("Missing Aplos Api Domain")
36
+ return url
37
37
 
38
38
  def upload(self, input_file_path: str) -> Dict[str, Any]:
39
39
  """
@@ -5,7 +5,7 @@ Property of Aplos Analytics, Utah, USA
5
5
  """
6
6
 
7
7
  from typing import Optional
8
- from aplos_nca_saas_sdk.aws_resources.aws_cognito import CognitoAuthenication
8
+ from aplos_nca_saas_sdk.aws_resources.aws_cognito import CognitoAuthentication
9
9
  from aplos_nca_saas_sdk.nca_resources.nca_app_configuration import (
10
10
  NCAAppConfiguration,
11
11
  )
@@ -39,18 +39,18 @@ class NCALogin:
39
39
  self.__cognito_client_id = cognito_client_id
40
40
  self.__region = cognito_region
41
41
  self.__domain: Optional[str] = aplos_saas_domain
42
- self.__cognito: Optional[CognitoAuthenication] = None
42
+ self.__cognito: Optional[CognitoAuthentication] = None
43
43
  self.__config: Optional[NCAAppConfiguration] = None
44
44
 
45
45
  @property
46
- def cognito(self) -> CognitoAuthenication:
46
+ def cognito(self) -> CognitoAuthentication:
47
47
  """
48
48
  Cognito Authentication
49
49
  Returns:
50
50
  CognitoAuthenication: object to handle cognito authentication
51
51
  """
52
52
  if self.__cognito is None:
53
- self.__cognito = CognitoAuthenication(
53
+ self.__cognito = CognitoAuthentication(
54
54
  client_id=self.__cognito_client_id,
55
55
  region=self.__region,
56
56
  aplos_domain=self.__domain,