sumo-wrapper-python 1.0.25__tar.gz → 1.0.26__tar.gz
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.
Potentially problematic release.
This version of sumo-wrapper-python might be problematic. Click here for more details.
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/PKG-INFO +1 -1
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/_auth_provider.py +14 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/_version.py +9 -4
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/login.py +0 -12
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/sumo_client.py +69 -2
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo_wrapper_python.egg-info/PKG-INFO +1 -1
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/tests/test_sumo_thin_client.py +16 -3
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/tests/testdata/surface.yml +1 -1
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/.github/workflows/build_docs.yaml +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/.github/workflows/linting.yml +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/.github/workflows/publish_release.yml +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/.github/workflows/pytest.yml +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/.gitignore +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/.pre-commit-config.yaml +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/.readthedocs.yaml +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/CONTRIBUTING.md +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/LICENSE +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/README.md +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/SECURITY.md +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/Makefile +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/_static/equinor-logo.png +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/_static/equinor-logo2.jpg +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/_static/equinor_logo.jpg +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/_static/equinor_logo_only.jpg +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/_templates/layout.html +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/api.rst +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/conf.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/index.rst +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/make.bat +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/sumo-wrapper-python.rst +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/pyproject.toml +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/setup.cfg +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/__init__.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/__init__.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/_blob_client.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/_decorators.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/_logging.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/_retry_strategy.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/config.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo_wrapper_python.egg-info/SOURCES.txt +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo_wrapper_python.egg-info/dependency_links.txt +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo_wrapper_python.egg-info/entry_points.txt +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo_wrapper_python.egg-info/requires.txt +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo_wrapper_python.egg-info/top_level.txt +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/tests/conftest.py +0 -0
- {sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/tests/testdata/case.yml +0 -0
{sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/_auth_provider.py
RENAMED
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
import errno
|
|
2
2
|
import json
|
|
3
3
|
import os
|
|
4
|
+
import platform
|
|
4
5
|
import stat
|
|
5
6
|
import sys
|
|
6
7
|
import time
|
|
7
8
|
from datetime import datetime, timedelta, timezone
|
|
9
|
+
from pathlib import Path
|
|
8
10
|
from urllib.parse import parse_qs
|
|
9
11
|
|
|
10
12
|
import jwt
|
|
@@ -441,6 +443,18 @@ def get_auth_provider(
|
|
|
441
443
|
pass
|
|
442
444
|
# ELSE
|
|
443
445
|
if interactive:
|
|
446
|
+
lockfile_path = Path.home() / ".config/chromium/SingletonLock"
|
|
447
|
+
|
|
448
|
+
if Path(lockfile_path).is_symlink() and not str(
|
|
449
|
+
Path(lockfile_path).resolve()
|
|
450
|
+
).__contains__(platform.node()):
|
|
451
|
+
# https://github.com/equinor/sumo-wrapper-python/issues/193
|
|
452
|
+
print(
|
|
453
|
+
"\n\n\033[1mDetected chromium lockfile for different node; using firefox to authenticate.\033[0m"
|
|
454
|
+
)
|
|
455
|
+
os.environ["BROWSER"] = "firefox"
|
|
456
|
+
pass
|
|
457
|
+
|
|
444
458
|
return AuthProviderInteractive(client_id, authority, resource_id)
|
|
445
459
|
# ELSE
|
|
446
460
|
if devicecode:
|
|
@@ -1,8 +1,13 @@
|
|
|
1
|
-
# file generated by
|
|
1
|
+
# file generated by setuptools-scm
|
|
2
2
|
# don't change, don't track in version control
|
|
3
|
+
|
|
4
|
+
__all__ = ["__version__", "__version_tuple__", "version", "version_tuple"]
|
|
5
|
+
|
|
3
6
|
TYPE_CHECKING = False
|
|
4
7
|
if TYPE_CHECKING:
|
|
5
|
-
from typing import Tuple
|
|
8
|
+
from typing import Tuple
|
|
9
|
+
from typing import Union
|
|
10
|
+
|
|
6
11
|
VERSION_TUPLE = Tuple[Union[int, str], ...]
|
|
7
12
|
else:
|
|
8
13
|
VERSION_TUPLE = object
|
|
@@ -12,5 +17,5 @@ __version__: str
|
|
|
12
17
|
__version_tuple__: VERSION_TUPLE
|
|
13
18
|
version_tuple: VERSION_TUPLE
|
|
14
19
|
|
|
15
|
-
__version__ = version = '1.0.
|
|
16
|
-
__version_tuple__ = version_tuple = (1, 0,
|
|
20
|
+
__version__ = version = '1.0.26'
|
|
21
|
+
__version_tuple__ = version_tuple = (1, 0, 26)
|
|
@@ -1,7 +1,5 @@
|
|
|
1
1
|
import logging
|
|
2
|
-
import platform
|
|
3
2
|
from argparse import ArgumentParser
|
|
4
|
-
from pathlib import Path
|
|
5
3
|
|
|
6
4
|
from sumo.wrapper import SumoClient
|
|
7
5
|
|
|
@@ -69,16 +67,6 @@ def main():
|
|
|
69
67
|
if mode != "silent":
|
|
70
68
|
print("Login to Sumo environment: " + env)
|
|
71
69
|
|
|
72
|
-
if mode == "interactive":
|
|
73
|
-
lockfile_path = Path.home() / ".config/chromium/SingletonLock"
|
|
74
|
-
|
|
75
|
-
if Path(lockfile_path).is_symlink() and not str(
|
|
76
|
-
Path(lockfile_path).resolve()
|
|
77
|
-
).__contains__(platform.node()):
|
|
78
|
-
# https://github.com/equinor/sumo-wrapper-python/issues/193
|
|
79
|
-
is_interactive = False
|
|
80
|
-
is_devicecode = True
|
|
81
|
-
|
|
82
70
|
sumo = SumoClient(
|
|
83
71
|
env,
|
|
84
72
|
interactive=is_interactive,
|
|
@@ -2,6 +2,7 @@ import asyncio
|
|
|
2
2
|
import contextlib
|
|
3
3
|
import logging
|
|
4
4
|
import re
|
|
5
|
+
import time
|
|
5
6
|
|
|
6
7
|
import httpx
|
|
7
8
|
import jwt
|
|
@@ -372,7 +373,7 @@ class SumoClient:
|
|
|
372
373
|
params: query parameters, as dictionary
|
|
373
374
|
|
|
374
375
|
Returns:
|
|
375
|
-
Sumo JSON
|
|
376
|
+
Sumo JSON response as a dictionary
|
|
376
377
|
|
|
377
378
|
Examples:
|
|
378
379
|
Deleting object::
|
|
@@ -401,6 +402,46 @@ class SumoClient:
|
|
|
401
402
|
|
|
402
403
|
return retryer(_delete)
|
|
403
404
|
|
|
405
|
+
def _get_retry_details(self, response_in):
|
|
406
|
+
assert response_in.status_code == 202, (
|
|
407
|
+
"Incorrect status code; expcted 202"
|
|
408
|
+
)
|
|
409
|
+
headers = response_in.headers
|
|
410
|
+
location = headers.get("location")
|
|
411
|
+
assert location is not None, "Missing header: Location"
|
|
412
|
+
assert location.startswith(self.base_url)
|
|
413
|
+
retry_after = headers.get("retry-after")
|
|
414
|
+
assert retry_after is not None, "Missing header: Retry-After"
|
|
415
|
+
location = location[len(self.base_url) :]
|
|
416
|
+
retry_after = int(retry_after)
|
|
417
|
+
return location, retry_after
|
|
418
|
+
|
|
419
|
+
def poll(
|
|
420
|
+
self, response_in: httpx.Response, timeout=None
|
|
421
|
+
) -> httpx.Response:
|
|
422
|
+
"""Poll a specific endpoint until a result is obtained.
|
|
423
|
+
|
|
424
|
+
Args:
|
|
425
|
+
response_in: httpx.Response from a previous request, with 'location' and 'retry-after' headers.
|
|
426
|
+
|
|
427
|
+
Returns:
|
|
428
|
+
A new httpx.response object.
|
|
429
|
+
"""
|
|
430
|
+
location, retry_after = self._get_retry_details(response_in)
|
|
431
|
+
expiry = time.time() + timeout if timeout is not None else None
|
|
432
|
+
while True:
|
|
433
|
+
time.sleep(retry_after)
|
|
434
|
+
response = self.get(location)
|
|
435
|
+
if response.status_code != 202:
|
|
436
|
+
return response
|
|
437
|
+
if expiry is not None and time.time() > expiry:
|
|
438
|
+
raise httpx.TimeoutException(
|
|
439
|
+
"No response within specified timeout."
|
|
440
|
+
)
|
|
441
|
+
location, retry_after = self._get_retry_details(response)
|
|
442
|
+
pass
|
|
443
|
+
return None # should never get here.
|
|
444
|
+
|
|
404
445
|
def getLogger(self, name):
|
|
405
446
|
"""Gets a logger object that sends log objects into the message_log
|
|
406
447
|
index for the Sumo instance.
|
|
@@ -642,7 +683,7 @@ class SumoClient:
|
|
|
642
683
|
params: query parameters, as dictionary
|
|
643
684
|
|
|
644
685
|
Returns:
|
|
645
|
-
Sumo JSON
|
|
686
|
+
Sumo JSON response as a dictionary
|
|
646
687
|
|
|
647
688
|
Examples:
|
|
648
689
|
Deleting object::
|
|
@@ -670,3 +711,29 @@ class SumoClient:
|
|
|
670
711
|
retryer = self._retry_strategy.make_retryer_async()
|
|
671
712
|
|
|
672
713
|
return await retryer(_delete)
|
|
714
|
+
|
|
715
|
+
async def poll_async(
|
|
716
|
+
self, response_in: httpx.Response, timeout=None
|
|
717
|
+
) -> httpx.Response:
|
|
718
|
+
"""Poll a specific endpoint until a result is obtained.
|
|
719
|
+
|
|
720
|
+
Args:
|
|
721
|
+
response_in: httpx.Response from a previous request, with 'location' and 'retry-after' headers.
|
|
722
|
+
|
|
723
|
+
Returns:
|
|
724
|
+
A new httpx.response object.
|
|
725
|
+
"""
|
|
726
|
+
location, retry_after = self._get_retry_details(response_in)
|
|
727
|
+
expiry = time.time() + timeout if timeout is not None else None
|
|
728
|
+
while True:
|
|
729
|
+
await asyncio.sleep(retry_after)
|
|
730
|
+
response = await self.get_async(location)
|
|
731
|
+
if response.status_code != 202:
|
|
732
|
+
return response
|
|
733
|
+
if expiry is not None and time.time() > expiry:
|
|
734
|
+
raise httpx.TimeoutException(
|
|
735
|
+
"No response within specified timeout."
|
|
736
|
+
)
|
|
737
|
+
location, retry_after = self._get_retry_details(response)
|
|
738
|
+
pass
|
|
739
|
+
return None # should never get here.
|
|
@@ -112,9 +112,13 @@ def test_upload_search_delete_ensemble_child(token):
|
|
|
112
112
|
|
|
113
113
|
fmu_surface_metadata["fmu"]["case"]["uuid"] = case_uuid
|
|
114
114
|
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
115
|
+
try:
|
|
116
|
+
response_surface = _upload_child_level_json(
|
|
117
|
+
conn=sumo_client, parent_id=case_id, json=fmu_surface_metadata
|
|
118
|
+
)
|
|
119
|
+
except Exception as ex:
|
|
120
|
+
print(ex.response.text)
|
|
121
|
+
raise ex
|
|
118
122
|
|
|
119
123
|
assert 200 <= response_surface.status_code <= 202
|
|
120
124
|
assert isinstance(response_surface.json(), dict)
|
|
@@ -237,3 +241,12 @@ def test_upload_duplicate_ensemble(token):
|
|
|
237
241
|
# Search for ensemble
|
|
238
242
|
with pytest.raises(Exception):
|
|
239
243
|
assert _download_object(conn, object_id=case_id2)
|
|
244
|
+
|
|
245
|
+
|
|
246
|
+
def test_poll(token):
|
|
247
|
+
conn = SumoClient(env="dev", token=token)
|
|
248
|
+
res = conn.get("/admin/index/orphans")
|
|
249
|
+
res2 = conn.poll(res)
|
|
250
|
+
assert res2.status_code == 200
|
|
251
|
+
indexorphans = res2.json()
|
|
252
|
+
assert isinstance(indexorphans, list)
|
|
@@ -75,7 +75,7 @@ fmu:
|
|
|
75
75
|
file:
|
|
76
76
|
relative_path: realization-33/iter-0/share/results/maps/volantis_gp_base--amplitude.gri # case-relative
|
|
77
77
|
absolute_path: /some/absolute/path//realization-33/iter-0/share/results/maps/volantis_gp_base--amplitude.gri
|
|
78
|
-
checksum_md5:
|
|
78
|
+
checksum_md5: 0123456789abcdef0123456789abcdef # checksum of the file, not the data.
|
|
79
79
|
|
|
80
80
|
data: # The data block describes the actual data (e.g. surface). Only present in data objects
|
|
81
81
|
|
|
File without changes
|
|
File without changes
|
{sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/.github/workflows/publish_release.yml
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/docs/_static/equinor_logo_only.jpg
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sumo_wrapper_python-1.0.25 → sumo_wrapper_python-1.0.26}/src/sumo/wrapper/_retry_strategy.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|