argus-alm 0.12.10__tar.gz → 0.13.1__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.
Files changed (95) hide show
  1. {argus_alm-0.12.10 → argus_alm-0.13.1}/PKG-INFO +2 -4
  2. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/base.py +1 -1
  3. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/driver_matrix_tests/cli.py +2 -2
  4. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/driver_matrix_tests/client.py +1 -1
  5. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/generic/cli.py +22 -2
  6. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/generic/client.py +22 -0
  7. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/generic_result.py +3 -3
  8. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/sct/client.py +5 -4
  9. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/sirenada/client.py +1 -1
  10. {argus_alm-0.12.10 → argus_alm-0.13.1}/pyproject.toml +14 -4
  11. argus_alm-0.12.10/argus/backend/.gitkeep +0 -0
  12. argus_alm-0.12.10/argus/backend/cli.py +0 -41
  13. argus_alm-0.12.10/argus/backend/controller/__init__.py +0 -0
  14. argus_alm-0.12.10/argus/backend/controller/admin.py +0 -20
  15. argus_alm-0.12.10/argus/backend/controller/admin_api.py +0 -354
  16. argus_alm-0.12.10/argus/backend/controller/api.py +0 -529
  17. argus_alm-0.12.10/argus/backend/controller/auth.py +0 -67
  18. argus_alm-0.12.10/argus/backend/controller/client_api.py +0 -108
  19. argus_alm-0.12.10/argus/backend/controller/main.py +0 -274
  20. argus_alm-0.12.10/argus/backend/controller/notification_api.py +0 -72
  21. argus_alm-0.12.10/argus/backend/controller/notifications.py +0 -13
  22. argus_alm-0.12.10/argus/backend/controller/team.py +0 -126
  23. argus_alm-0.12.10/argus/backend/controller/team_ui.py +0 -18
  24. argus_alm-0.12.10/argus/backend/controller/testrun_api.py +0 -482
  25. argus_alm-0.12.10/argus/backend/controller/view_api.py +0 -162
  26. argus_alm-0.12.10/argus/backend/db.py +0 -100
  27. argus_alm-0.12.10/argus/backend/error_handlers.py +0 -21
  28. argus_alm-0.12.10/argus/backend/events/event_processors.py +0 -34
  29. argus_alm-0.12.10/argus/backend/models/__init__.py +0 -0
  30. argus_alm-0.12.10/argus/backend/models/result.py +0 -138
  31. argus_alm-0.12.10/argus/backend/models/web.py +0 -389
  32. argus_alm-0.12.10/argus/backend/plugins/__init__.py +0 -0
  33. argus_alm-0.12.10/argus/backend/plugins/core.py +0 -225
  34. argus_alm-0.12.10/argus/backend/plugins/driver_matrix_tests/controller.py +0 -63
  35. argus_alm-0.12.10/argus/backend/plugins/driver_matrix_tests/model.py +0 -421
  36. argus_alm-0.12.10/argus/backend/plugins/driver_matrix_tests/plugin.py +0 -22
  37. argus_alm-0.12.10/argus/backend/plugins/driver_matrix_tests/raw_types.py +0 -62
  38. argus_alm-0.12.10/argus/backend/plugins/driver_matrix_tests/service.py +0 -60
  39. argus_alm-0.12.10/argus/backend/plugins/driver_matrix_tests/udt.py +0 -42
  40. argus_alm-0.12.10/argus/backend/plugins/generic/model.py +0 -79
  41. argus_alm-0.12.10/argus/backend/plugins/generic/plugin.py +0 -16
  42. argus_alm-0.12.10/argus/backend/plugins/generic/types.py +0 -13
  43. argus_alm-0.12.10/argus/backend/plugins/loader.py +0 -40
  44. argus_alm-0.12.10/argus/backend/plugins/sct/controller.py +0 -185
  45. argus_alm-0.12.10/argus/backend/plugins/sct/plugin.py +0 -38
  46. argus_alm-0.12.10/argus/backend/plugins/sct/resource_setup.py +0 -178
  47. argus_alm-0.12.10/argus/backend/plugins/sct/service.py +0 -491
  48. argus_alm-0.12.10/argus/backend/plugins/sct/testrun.py +0 -272
  49. argus_alm-0.12.10/argus/backend/plugins/sct/udt.py +0 -101
  50. argus_alm-0.12.10/argus/backend/plugins/sirenada/model.py +0 -113
  51. argus_alm-0.12.10/argus/backend/plugins/sirenada/plugin.py +0 -17
  52. argus_alm-0.12.10/argus/backend/service/admin.py +0 -27
  53. argus_alm-0.12.10/argus/backend/service/argus_service.py +0 -688
  54. argus_alm-0.12.10/argus/backend/service/build_system_monitor.py +0 -188
  55. argus_alm-0.12.10/argus/backend/service/client_service.py +0 -122
  56. argus_alm-0.12.10/argus/backend/service/event_service.py +0 -18
  57. argus_alm-0.12.10/argus/backend/service/jenkins_service.py +0 -240
  58. argus_alm-0.12.10/argus/backend/service/notification_manager.py +0 -150
  59. argus_alm-0.12.10/argus/backend/service/release_manager.py +0 -230
  60. argus_alm-0.12.10/argus/backend/service/results_service.py +0 -317
  61. argus_alm-0.12.10/argus/backend/service/stats.py +0 -540
  62. argus_alm-0.12.10/argus/backend/service/team_manager_service.py +0 -83
  63. argus_alm-0.12.10/argus/backend/service/testrun.py +0 -559
  64. argus_alm-0.12.10/argus/backend/service/user.py +0 -307
  65. argus_alm-0.12.10/argus/backend/service/views.py +0 -258
  66. argus_alm-0.12.10/argus/backend/template_filters.py +0 -27
  67. argus_alm-0.12.10/argus/backend/tests/__init__.py +0 -0
  68. argus_alm-0.12.10/argus/backend/tests/argus_web.test.yaml +0 -39
  69. argus_alm-0.12.10/argus/backend/tests/conftest.py +0 -44
  70. argus_alm-0.12.10/argus/backend/tests/results_service/__init__.py +0 -0
  71. argus_alm-0.12.10/argus/backend/tests/results_service/test_best_results.py +0 -70
  72. argus_alm-0.12.10/argus/backend/util/common.py +0 -65
  73. argus_alm-0.12.10/argus/backend/util/config.py +0 -38
  74. argus_alm-0.12.10/argus/backend/util/encoders.py +0 -41
  75. argus_alm-0.12.10/argus/backend/util/logsetup.py +0 -81
  76. argus_alm-0.12.10/argus/backend/util/module_loaders.py +0 -30
  77. argus_alm-0.12.10/argus/backend/util/send_email.py +0 -91
  78. argus_alm-0.12.10/argus/client/generic_result_old.py +0 -143
  79. argus_alm-0.12.10/argus/db/.gitkeep +0 -0
  80. argus_alm-0.12.10/argus/db/argus_json.py +0 -14
  81. argus_alm-0.12.10/argus/db/cloud_types.py +0 -125
  82. argus_alm-0.12.10/argus/db/config.py +0 -135
  83. argus_alm-0.12.10/argus/db/db_types.py +0 -139
  84. argus_alm-0.12.10/argus/db/interface.py +0 -370
  85. argus_alm-0.12.10/argus/db/testrun.py +0 -740
  86. argus_alm-0.12.10/argus/db/utils.py +0 -15
  87. {argus_alm-0.12.10 → argus_alm-0.13.1}/LICENSE +0 -0
  88. {argus_alm-0.12.10 → argus_alm-0.13.1}/README.md +0 -0
  89. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/__init__.py +0 -0
  90. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/__init__.py +0 -0
  91. {argus_alm-0.12.10 → argus_alm-0.13.1}/argus/client/sct/types.py +0 -0
  92. {argus_alm-0.12.10/argus/backend → argus_alm-0.13.1/argus/common}/__init__.py +0 -0
  93. {argus_alm-0.12.10/argus/backend/util → argus_alm-0.13.1/argus/common}/enums.py +0 -0
  94. /argus_alm-0.12.10/argus/backend/plugins/sct/types.py → /argus_alm-0.13.1/argus/common/sct_types.py +0 -0
  95. /argus_alm-0.12.10/argus/backend/plugins/sirenada/types.py → /argus_alm-0.13.1/argus/common/sirenada_types.py +0 -0
@@ -1,16 +1,14 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: argus-alm
3
- Version: 0.12.10
3
+ Version: 0.13.1
4
4
  Summary: Argus
5
5
  Home-page: https://github.com/scylladb/argus
6
6
  License: Apache-2.0
7
7
  Author: Alexey Kartashov
8
8
  Author-email: alexey.kartashov@scylladb.com
9
- Requires-Python: >=3.10,<4.0
9
+ Requires-Python: >=3.12,<4.0
10
10
  Classifier: License :: OSI Approved :: Apache Software License
11
11
  Classifier: Programming Language :: Python :: 3
12
- Classifier: Programming Language :: Python :: 3.10
13
- Classifier: Programming Language :: Python :: 3.11
14
12
  Classifier: Programming Language :: Python :: 3.12
15
13
  Requires-Dist: click (>=8.1.3,<9.0.0)
16
14
  Requires-Dist: requests (>=2.26.0,<3.0.0)
@@ -6,7 +6,7 @@ from uuid import UUID
6
6
 
7
7
  import requests
8
8
 
9
- from argus.backend.util.enums import TestStatus
9
+ from argus.common.enums import TestStatus
10
10
  from argus.client.generic_result import GenericResultTable
11
11
  from argus.client.sct.types import LogLink
12
12
 
@@ -3,7 +3,7 @@ import json
3
3
  from pathlib import Path
4
4
  import click
5
5
  import logging
6
- from argus.backend.util.enums import TestStatus
6
+ from argus.common.enums import TestStatus
7
7
 
8
8
  from argus.client.driver_matrix_tests.client import ArgusDriverMatrixClient
9
9
 
@@ -107,4 +107,4 @@ cli.add_command(finish_driver_matrix_run)
107
107
 
108
108
 
109
109
  if __name__ == "__main__":
110
- cli()
110
+ cli()
@@ -1,5 +1,5 @@
1
1
  from uuid import UUID
2
- from argus.backend.util.enums import TestStatus
2
+ from argus.common.enums import TestStatus
3
3
  from argus.client.base import ArgusClient
4
4
 
5
5
 
@@ -1,7 +1,9 @@
1
+ import json
2
+ from pathlib import Path
1
3
  import click
2
4
  import logging
3
- from argus.backend.util.enums import TestStatus
4
5
 
6
+ from argus.client.base import TestStatus
5
7
  from argus.client.generic.client import ArgusGenericClient
6
8
 
7
9
  LOGGER = logging.getLogger(__name__)
@@ -39,9 +41,27 @@ def finish_run(api_key: str, base_url: str, id: str, status: str, scylla_version
39
41
  client.finalize_generic_run(run_id=id, status=status, scylla_version=scylla_version)
40
42
 
41
43
 
44
+ @click.command("trigger-jobs")
45
+ @click.option("--api-key", help="Argus API key for authorization", required=True)
46
+ @click.option("--base-url", default="https://argus.scylladb.com", help="Base URL for argus instance")
47
+ @click.option("--version", help="Scylla version to filter plans by", default=None, required=False)
48
+ @click.option("--plan-id", help="Specific plan id for filtering", default=None, required=False)
49
+ @click.option("--release", help="Release name to filter plans by", default=None, required=False)
50
+ @click.option("--job-info-file", required=True, help="JSON file with trigger information (see detailed docs)")
51
+ def trigger_jobs(api_key: str, base_url: str, job_info_file: str, version: str, plan_id: str, release: str):
52
+ client = ArgusGenericClient(auth_token=api_key, base_url=base_url)
53
+ path = Path(job_info_file)
54
+ if not path.exists():
55
+ LOGGER.error("File not found: %s", job_info_file)
56
+ exit(128)
57
+ payload = json.load(path.open("rt", encoding="utf-8"))
58
+ client.trigger_jobs({ "release": release, "version": version, "plan_id": plan_id, **payload })
59
+
60
+
42
61
  cli.add_command(submit_run)
43
62
  cli.add_command(finish_run)
63
+ cli.add_command(trigger_jobs)
44
64
 
45
65
 
46
66
  if __name__ == "__main__":
47
- cli()
67
+ cli()
@@ -7,6 +7,10 @@ LOGGER = logging.getLogger(__name__)
7
7
  class ArgusGenericClient(ArgusClient):
8
8
  test_type = "generic"
9
9
  schema_version: None = "v1"
10
+
11
+ class Routes(ArgusClient.Routes):
12
+ TRIGGER_JOBS = "/planning/plan/trigger"
13
+
10
14
  def __init__(self, auth_token: str, base_url: str, api_version="v1") -> None:
11
15
  super().__init__(auth_token, base_url, api_version)
12
16
 
@@ -22,6 +26,24 @@ class ArgusGenericClient(ArgusClient):
22
26
  response = self.submit_run(run_type=self.test_type, run_body=request_body)
23
27
  self.check_response(response)
24
28
 
29
+ def trigger_jobs(self, common_params: dict[str, str], params: list[dict[str, str]], version: str = None, release: str = None, plan_id: str = None):
30
+ request_body = {
31
+ "common_params": common_params,
32
+ "params": params,
33
+ "version": version,
34
+ "release": release,
35
+ "plan_id": plan_id,
36
+ }
37
+ response = self.post(
38
+ endpoint=self.Routes.TRIGGER_JOBS,
39
+ location_params={},
40
+ body={
41
+ **self.generic_body,
42
+ **request_body,
43
+ }
44
+ )
45
+ self.check_response(response)
46
+ return response.json()
25
47
 
26
48
  def finalize_generic_run(self, run_id: str, status: str, scylla_version: str | None = None):
27
49
  response = self.finalize_run(run_type=self.test_type, run_id=run_id, body={
@@ -62,6 +62,7 @@ class ResultTableMeta(type):
62
62
  cls_instance.description = meta.description
63
63
  cls_instance.columns = meta.Columns
64
64
  cls_instance.column_types = {column.name: column.type for column in cls_instance.columns}
65
+ cls_instance.sut_package_name = getattr(meta, 'sut_package_name', '')
65
66
  cls_instance.rows = []
66
67
  validation_rules = getattr(meta, 'ValidationRules', {})
67
68
  for col_name, rule in validation_rules.items():
@@ -98,7 +99,6 @@ class GenericResultTable(metaclass=ResultTableMeta):
98
99
  Base class for all Generic Result Tables in Argus. Use it as a base class for your result table.
99
100
  """
100
101
  sut_timestamp: int = 0 # automatic timestamp based on SUT version. Works only with SCT and refers to Scylla version.
101
- sut_details: str = ""
102
102
  results: list[Cell] = field(default_factory=list)
103
103
 
104
104
  def as_dict(self) -> dict:
@@ -112,12 +112,12 @@ class GenericResultTable(metaclass=ResultTableMeta):
112
112
  "description": self.description,
113
113
  "columns_meta": [column.as_dict() for column in self.columns],
114
114
  "rows_meta": rows,
115
- "validation_rules": {k: v.as_dict() for k, v in self.validation_rules.items()}
115
+ "validation_rules": {k: v.as_dict() for k, v in self.validation_rules.items()},
116
+ "sut_package_name": self.sut_package_name,
116
117
  }
117
118
  return {
118
119
  "meta": meta_info,
119
120
  "sut_timestamp": self.sut_timestamp,
120
- "sut_details": self.sut_details,
121
121
  "results": [result.as_dict() for result in self.results]
122
122
  }
123
123
 
@@ -2,8 +2,8 @@ import base64
2
2
  from typing import Any
3
3
  from uuid import UUID
4
4
  from dataclasses import asdict
5
- from argus.backend.plugins.sct.types import GeminiResultsRequest, PerformanceResultsRequest
6
- from argus.backend.util.enums import ResourceState, TestStatus
5
+ from argus.common.sct_types import GeminiResultsRequest, PerformanceResultsRequest
6
+ from argus.common.enums import ResourceState, TestStatus
7
7
  from argus.client.base import ArgusClient
8
8
  from argus.client.sct.types import EventsInfo, LogLink, Package
9
9
 
@@ -56,7 +56,7 @@ class ArgusSCTClient(ArgusClient):
56
56
  response = super().set_status(run_type=self.test_type, run_id=self.run_id, new_status=new_status)
57
57
  self.check_response(response)
58
58
 
59
- def set_sct_runner(self, public_ip: str, private_ip: str, region: str, backend: str) -> None:
59
+ def set_sct_runner(self, public_ip: str, private_ip: str, region: str, backend: str, name: str = None) -> None:
60
60
  """
61
61
  Sets runner information for an SCT run.
62
62
  """
@@ -69,6 +69,7 @@ class ArgusSCTClient(ArgusClient):
69
69
  "private_ip": private_ip,
70
70
  "region": region,
71
71
  "backend": backend,
72
+ "name": name,
72
73
  }
73
74
  )
74
75
  self.check_response(response)
@@ -298,4 +299,4 @@ class ArgusSCTClient(ArgusClient):
298
299
  "file_name": file_name,
299
300
  "content": str(base64.encodebytes(bytes(raw_content, encoding="utf-8")), encoding="utf-8")
300
301
  }
301
- )
302
+ )
@@ -5,7 +5,7 @@ from pathlib import Path
5
5
  from typing import TypedDict
6
6
  from xml.etree import ElementTree
7
7
 
8
- from argus.backend.plugins.sirenada.types import RawSirenadaRequest, RawSirenadaTestCase
8
+ from argus.common.sirenada_types import RawSirenadaRequest, RawSirenadaTestCase
9
9
 
10
10
  from argus.client.base import ArgusClient
11
11
 
@@ -1,12 +1,17 @@
1
1
  [tool.poetry]
2
2
  name = "argus-alm"
3
- version = "0.12.10"
3
+ version = "0.13.1"
4
4
  description = "Argus"
5
5
  authors = ["Alexey Kartashov <alexey.kartashov@scylladb.com>", "Łukasz Sójka <lukasz.sojka@scylladb.com>"]
6
6
  license = "Apache-2.0"
7
7
  repository = "https://github.com/scylladb/argus"
8
8
  readme = "README.md"
9
- packages = [{include = "argus"}]
9
+ packages = [
10
+ { include = "argus/client" },
11
+ { include = "argus/common" },
12
+ { include = "argus/__init__.py" },
13
+ ]
14
+ exclude = ["argus/client/tests"]
10
15
 
11
16
  [tool.poetry.group.web-backend]
12
17
  optional = true
@@ -16,7 +21,7 @@ optional = true
16
21
 
17
22
  [tool.poetry.dependencies]
18
23
  requests = "^2.26.0"
19
- python = "^3.10"
24
+ python = "^3.12"
20
25
  click = "^8.1.3"
21
26
 
22
27
  [tool.poetry.scripts]
@@ -39,8 +44,9 @@ python-slugify = "^6.1.1"
39
44
  supervisor = "^4.2.4"
40
45
 
41
46
  [tool.poetry.dev-dependencies]
47
+ black = "^24.10.0"
42
48
  coverage = "5.5"
43
- docker = "4.4.4"
49
+ docker = "7.1.0"
44
50
  pytest = "6.2.5"
45
51
  ipython = "^8.1"
46
52
  pylint = "^2.12.0"
@@ -49,3 +55,7 @@ pre-commit = "^1.14.0"
49
55
  [build-system]
50
56
  requires = ["poetry-core>=1.0.0"]
51
57
  build-backend = "poetry.core.masonry.api"
58
+
59
+ [tool.black]
60
+ line-length = 110
61
+ target-version = ["py312"]
File without changes
@@ -1,41 +0,0 @@
1
- import logging
2
- import click
3
- from flask import Blueprint
4
- from flask.cli import with_appcontext
5
- from cassandra.cqlengine.management import sync_table, sync_type
6
- from argus.backend.db import ScyllaCluster
7
- from argus.backend.plugins.loader import all_plugin_models, all_plugin_types
8
- from argus.backend.service.build_system_monitor import JenkinsMonitor
9
-
10
- cli_bp = Blueprint("cli", __name__)
11
- LOGGER = logging.getLogger(__name__)
12
-
13
-
14
- @cli_bp.cli.add_command
15
- @click.command('sync-models')
16
- @with_appcontext
17
- def sync_models_command():
18
- sync_models()
19
-
20
- def sync_models():
21
- cluster = ScyllaCluster.get()
22
- cluster.sync_core_tables()
23
- LOGGER.info("Synchronizing plugin types...")
24
- for user_type in all_plugin_types():
25
- LOGGER.info("Synchronizing plugin type %s...", user_type.__name__)
26
- sync_type(ks_name=cluster.config["SCYLLA_KEYSPACE_NAME"], type_model=user_type)
27
- LOGGER.info("Synchronizing plugin models...")
28
- for model in all_plugin_models(True):
29
- LOGGER.info("Synchronizing plugin model %s...", model.__name__)
30
- sync_table(model=model, keyspaces=[cluster.config["SCYLLA_KEYSPACE_NAME"]])
31
-
32
- LOGGER.info("Plugins ready.")
33
- click.echo("All models synchronized.")
34
-
35
- @cli_bp.cli.add_command
36
- @click.command('scan-jenkins')
37
- @with_appcontext
38
- def scan_jenkins_command():
39
- monitor = JenkinsMonitor()
40
- monitor.collect()
41
- click.echo("Done.")
File without changes
@@ -1,20 +0,0 @@
1
- import logging
2
- from flask import (
3
- Blueprint,
4
- render_template,
5
- )
6
- from argus.backend.controller.admin_api import bp as admin_api_bp
7
- from argus.backend.service.user import login_required, check_roles
8
- from argus.backend.models.web import UserRoles
9
-
10
- bp = Blueprint('admin', __name__, url_prefix='/admin')
11
- bp.register_blueprint(admin_api_bp)
12
- LOGGER = logging.getLogger(__name__)
13
-
14
-
15
- @bp.route("/")
16
- @bp.route("/<string:path>")
17
- @check_roles(UserRoles.Admin)
18
- @login_required
19
- def index(path: str = "index"):
20
- return render_template("admin/index.html.j2", current_route=path)
@@ -1,354 +0,0 @@
1
- import logging
2
- from uuid import UUID
3
- from flask import (
4
- Blueprint,
5
- request,
6
- Request,
7
- )
8
- from argus.backend.error_handlers import handle_api_exception
9
- from argus.backend.service.release_manager import ReleaseEditPayload, ReleaseManagerService
10
- from argus.backend.service.user import UserService, api_login_required, check_roles
11
- from argus.backend.models.web import User, UserRoles
12
-
13
- bp = Blueprint('admin_api', __name__, url_prefix='/api/v1')
14
- LOGGER = logging.getLogger(__name__)
15
- bp.register_error_handler(Exception, handle_api_exception)
16
-
17
-
18
- def get_payload(client_request: Request):
19
- if not client_request.is_json:
20
- raise Exception(
21
- "Content-Type mismatch, expected application/json, got:", client_request.content_type)
22
- request_payload = client_request.get_json()
23
-
24
- return request_payload
25
-
26
-
27
- @bp.route("/", methods=["GET"])
28
- @check_roles(UserRoles.Admin)
29
- @api_login_required
30
- def index():
31
- return {
32
- "version": "v1"
33
- }
34
-
35
-
36
- @bp.route("/release/create", methods=["POST"])
37
- @check_roles(UserRoles.Admin)
38
- @api_login_required
39
- def create_release():
40
- payload = get_payload(request)
41
- release = ReleaseManagerService().create_release(**payload)
42
-
43
- return {
44
- "status": "ok",
45
- "response": {
46
- "new_release": release
47
- }
48
- }
49
-
50
-
51
- @bp.route("/release/set_perpetual", methods=["POST"])
52
- @check_roles(UserRoles.Admin)
53
- @api_login_required
54
- def set_release_perpetual():
55
- payload = get_payload(request)
56
- result = ReleaseManagerService().set_release_perpetuality(**payload)
57
- return {
58
- "status": "ok",
59
- "response": {
60
- "updated": result
61
- }
62
- }
63
-
64
-
65
- @bp.route("/release/set_state", methods=["POST"])
66
- @check_roles(UserRoles.Admin)
67
- @api_login_required
68
- def set_release_state():
69
- payload = get_payload(request)
70
- result = ReleaseManagerService().set_release_state(**payload)
71
-
72
- return {
73
- "status": "ok",
74
- "response": {
75
- "updated": result
76
- }
77
- }
78
-
79
-
80
- @bp.route("/release/set_dormant", methods=["POST"])
81
- @check_roles(UserRoles.Admin)
82
- @api_login_required
83
- def set_release_dormancy():
84
- payload = get_payload(request)
85
- result = ReleaseManagerService().set_release_dormancy(**payload)
86
-
87
- return {
88
- "status": "ok",
89
- "response": {
90
- "updated": result
91
- }
92
- }
93
-
94
-
95
- @bp.route("/release/edit", methods=["POST"])
96
- @check_roles(UserRoles.Admin)
97
- @api_login_required
98
- def edit_release():
99
- payload: ReleaseEditPayload = get_payload(request)
100
- result = ReleaseManagerService().edit_release(payload)
101
-
102
- return {
103
- "status": "ok",
104
- "response": {
105
- "updated": result
106
- }
107
- }
108
-
109
-
110
- @bp.route("/release/delete", methods=["POST"])
111
- @check_roles(UserRoles.Admin)
112
- @api_login_required
113
- def delete_release():
114
- payload = get_payload(request)
115
- result = ReleaseManagerService().delete_release(release_id=payload["releaseId"])
116
-
117
- return {
118
- "status": "ok",
119
- "response": {
120
- "deleted": result
121
- }
122
- }
123
-
124
-
125
- @bp.route("/group/create", methods=["POST"])
126
- @check_roles(UserRoles.Admin)
127
- @api_login_required
128
- def create_group():
129
- payload = get_payload(request)
130
- group = ReleaseManagerService().create_group(**payload)
131
-
132
- return {
133
- "status": "ok",
134
- "response": {
135
- "new_group": group
136
- }
137
- }
138
-
139
-
140
- @bp.route("/group/update", methods=["POST"])
141
- @check_roles(UserRoles.Admin)
142
- @api_login_required
143
- def update_group():
144
- payload = get_payload(request)
145
- result = ReleaseManagerService().update_group(**payload)
146
- return {
147
- "status": "ok",
148
- "response": {
149
- "updated": result
150
- }
151
- }
152
-
153
-
154
- @bp.route("/group/delete", methods=["POST"])
155
- @check_roles(UserRoles.Admin)
156
- @api_login_required
157
- def delete_group():
158
- payload = get_payload(request)
159
- result = ReleaseManagerService().delete_group(**payload)
160
-
161
- return {
162
- "status": "ok",
163
- "response": {
164
- "deleted": result
165
- }
166
- }
167
-
168
-
169
- @bp.route("/test/create", methods=["POST"])
170
- @check_roles(UserRoles.Admin)
171
- @api_login_required
172
- def create_test():
173
- payload = get_payload(request)
174
- test = ReleaseManagerService().create_test(**payload)
175
- return {
176
- "status": "ok",
177
- "response": {
178
- "new_test": test
179
- }
180
- }
181
-
182
-
183
- @bp.route("/test/update", methods=["POST"])
184
- @check_roles(UserRoles.Admin)
185
- @api_login_required
186
- def update_test():
187
- payload = get_payload(request)
188
- result = ReleaseManagerService().update_test(**payload)
189
- return {
190
- "status": "ok",
191
- "response": {
192
- "updated": result
193
- }
194
- }
195
-
196
-
197
- @bp.route("/test/batch_move", methods=["POST"])
198
- @check_roles(UserRoles.Admin)
199
- @api_login_required
200
- def batch_move_tests():
201
- payload = get_payload(request)
202
- result = ReleaseManagerService().batch_move_tests(**payload)
203
- return {
204
- "status": "ok",
205
- "response": {
206
- "moved": result
207
- }
208
- }
209
-
210
-
211
- @bp.route("/test/delete", methods=["POST"])
212
- @check_roles(UserRoles.Admin)
213
- @api_login_required
214
- def delete_test():
215
- payload = get_payload(request)
216
- result = ReleaseManagerService().delete_test(**payload)
217
-
218
- return {
219
- "status": "ok",
220
- "response": {
221
- "deleted": result
222
- }
223
- }
224
-
225
-
226
- @bp.route("/releases/get", methods=["GET"])
227
- @check_roles(UserRoles.Admin)
228
- @api_login_required
229
- def get_releases():
230
- releases = ReleaseManagerService().get_releases()
231
- return {
232
- "status": "ok",
233
- "response": releases
234
- }
235
-
236
-
237
- @bp.route("/groups/get", methods=["GET"])
238
- @check_roles(UserRoles.Admin)
239
- @api_login_required
240
- def get_groups_for_release():
241
- release_id = request.args.get("releaseId")
242
- if not release_id:
243
- raise Exception("ReleaseId not provided in the request")
244
- groups = ReleaseManagerService().get_groups(release_id=UUID(release_id))
245
-
246
- return {
247
- "status": "ok",
248
- "response": groups
249
- }
250
-
251
-
252
- @bp.route("/tests/get", methods=["GET"])
253
- @check_roles(UserRoles.Admin)
254
- @api_login_required
255
- def get_tests_for_group():
256
- group_id = request.args.get("groupId")
257
- if not group_id:
258
- raise Exception("GroupId not provided in the request")
259
- tests = ReleaseManagerService().get_tests(group_id=UUID(group_id))
260
- return {
261
- "status": "ok",
262
- "response": tests
263
- }
264
-
265
-
266
- @bp.route("/release/test/state/toggle", methods=["POST"])
267
- @check_roles(UserRoles.Admin)
268
- @api_login_required
269
- def quick_toggle_test_enabled():
270
-
271
- payload = get_payload(request)
272
- res = ReleaseManagerService().toggle_test_enabled(test_id=payload["entityId"], new_state=payload["state"])
273
- return {
274
- "status": "ok",
275
- "response": res
276
- }
277
-
278
-
279
- @bp.route("/release/group/state/toggle", methods=["POST"])
280
- @check_roles(UserRoles.Admin)
281
- @api_login_required
282
- def quick_toggle_group_enabled():
283
-
284
- payload = get_payload(request)
285
- res = ReleaseManagerService().toggle_group_enabled(group_id=payload["entityId"], new_state=payload["state"])
286
- return {
287
- "status": "ok",
288
- "response": res
289
- }
290
-
291
-
292
- @bp.route("/users", methods=["GET"])
293
- @check_roles(UserRoles.Admin)
294
- @api_login_required
295
- def user_info():
296
- result = UserService().get_users_privileged()
297
-
298
- return {
299
- "status": "ok",
300
- "response": result
301
- }
302
-
303
-
304
- @bp.route("/user/<string:user_id>/email/set", methods=["POST"])
305
- @check_roles(UserRoles.Admin)
306
- @api_login_required
307
- def user_change_email(user_id: str):
308
- payload = get_payload(request)
309
-
310
- user = User.get(id=user_id)
311
- result = UserService().update_email(user=user, new_email=payload["newEmail"])
312
-
313
- return {
314
- "status": "ok",
315
- "response": result
316
- }
317
-
318
-
319
- @bp.route("/user/<string:user_id>/delete", methods=["POST"])
320
- @check_roles(UserRoles.Admin)
321
- @api_login_required
322
- def user_delete(user_id: str):
323
- result = UserService().delete_user(user_id=user_id)
324
-
325
- return {
326
- "status": "ok",
327
- "response": result
328
- }
329
-
330
-
331
- @bp.route("/user/<string:user_id>/password/set", methods=["POST"])
332
- @check_roles(UserRoles.Admin)
333
- @api_login_required
334
- def user_change_password(user_id: str):
335
- payload = get_payload(request)
336
-
337
- user = User.get(id=user_id)
338
- result = UserService().update_password(user=user, old_password="", new_password=payload["newPassword"], force=True)
339
-
340
- return {
341
- "status": "ok",
342
- "response": result
343
- }
344
-
345
- @bp.route("/user/<string:user_id>/admin/toggle", methods=["POST"])
346
- @check_roles(UserRoles.Admin)
347
- @api_login_required
348
- def user_toggle_admin(user_id: str):
349
- result = UserService().toggle_admin(user_id=user_id)
350
-
351
- return {
352
- "status": "ok",
353
- "response": result
354
- }