tinybird 0.0.1.dev291__py3-none-any.whl → 1.0.5__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.
- tinybird/ch_utils/constants.py +5 -0
- tinybird/connectors.py +1 -7
- tinybird/context.py +3 -3
- tinybird/datafile/common.py +10 -8
- tinybird/datafile/parse_pipe.py +2 -2
- tinybird/feedback_manager.py +3 -0
- tinybird/prompts.py +1 -0
- tinybird/service_datasources.py +223 -0
- tinybird/sql_template.py +26 -11
- tinybird/sql_template_fmt.py +14 -4
- tinybird/tb/__cli__.py +2 -2
- tinybird/tb/cli.py +1 -0
- tinybird/tb/client.py +104 -26
- tinybird/tb/config.py +24 -0
- tinybird/tb/modules/agent/agent.py +103 -67
- tinybird/tb/modules/agent/banner.py +15 -15
- tinybird/tb/modules/agent/explore_agent.py +5 -0
- tinybird/tb/modules/agent/mock_agent.py +5 -1
- tinybird/tb/modules/agent/models.py +6 -2
- tinybird/tb/modules/agent/prompts.py +49 -2
- tinybird/tb/modules/agent/tools/deploy.py +1 -1
- tinybird/tb/modules/agent/tools/execute_query.py +15 -18
- tinybird/tb/modules/agent/tools/request_endpoint.py +1 -1
- tinybird/tb/modules/agent/tools/run_command.py +9 -0
- tinybird/tb/modules/agent/utils.py +38 -48
- tinybird/tb/modules/branch.py +150 -0
- tinybird/tb/modules/build.py +58 -13
- tinybird/tb/modules/build_common.py +209 -25
- tinybird/tb/modules/cli.py +129 -16
- tinybird/tb/modules/common.py +172 -146
- tinybird/tb/modules/connection.py +125 -194
- tinybird/tb/modules/connection_kafka.py +382 -0
- tinybird/tb/modules/copy.py +3 -1
- tinybird/tb/modules/create.py +83 -150
- tinybird/tb/modules/datafile/build.py +27 -38
- tinybird/tb/modules/datafile/build_datasource.py +21 -25
- tinybird/tb/modules/datafile/diff.py +1 -1
- tinybird/tb/modules/datafile/format_pipe.py +46 -7
- tinybird/tb/modules/datafile/playground.py +59 -68
- tinybird/tb/modules/datafile/pull.py +2 -3
- tinybird/tb/modules/datasource.py +477 -308
- tinybird/tb/modules/deployment.py +2 -0
- tinybird/tb/modules/deployment_common.py +84 -44
- tinybird/tb/modules/deprecations.py +4 -4
- tinybird/tb/modules/dev_server.py +33 -12
- tinybird/tb/modules/exceptions.py +14 -0
- tinybird/tb/modules/feedback_manager.py +1 -1
- tinybird/tb/modules/info.py +69 -12
- tinybird/tb/modules/infra.py +4 -5
- tinybird/tb/modules/job_common.py +15 -0
- tinybird/tb/modules/local.py +143 -23
- tinybird/tb/modules/local_common.py +347 -19
- tinybird/tb/modules/local_logs.py +209 -0
- tinybird/tb/modules/login.py +21 -2
- tinybird/tb/modules/login_common.py +254 -12
- tinybird/tb/modules/mock.py +5 -54
- tinybird/tb/modules/mock_common.py +0 -54
- tinybird/tb/modules/open.py +10 -5
- tinybird/tb/modules/project.py +14 -5
- tinybird/tb/modules/shell.py +15 -7
- tinybird/tb/modules/sink.py +3 -1
- tinybird/tb/modules/telemetry.py +11 -3
- tinybird/tb/modules/test.py +13 -9
- tinybird/tb/modules/test_common.py +13 -87
- tinybird/tb/modules/tinyunit/tinyunit.py +0 -14
- tinybird/tb/modules/tinyunit/tinyunit_lib.py +0 -6
- tinybird/tb/modules/watch.py +5 -3
- tinybird/tb_cli_modules/common.py +2 -2
- tinybird/tb_cli_modules/telemetry.py +1 -1
- tinybird/tornado_template.py +6 -7
- {tinybird-0.0.1.dev291.dist-info → tinybird-1.0.5.dist-info}/METADATA +32 -6
- tinybird-1.0.5.dist-info/RECORD +132 -0
- {tinybird-0.0.1.dev291.dist-info → tinybird-1.0.5.dist-info}/WHEEL +1 -1
- tinybird-0.0.1.dev291.dist-info/RECORD +0 -128
- {tinybird-0.0.1.dev291.dist-info → tinybird-1.0.5.dist-info}/entry_points.txt +0 -0
- {tinybird-0.0.1.dev291.dist-info → tinybird-1.0.5.dist-info}/top_level.txt +0 -0
tinybird/tb/modules/common.py
CHANGED
|
@@ -30,7 +30,6 @@ import requests
|
|
|
30
30
|
from click import Context
|
|
31
31
|
from click._termui_impl import ProgressBar
|
|
32
32
|
from humanfriendly.tables import format_pretty_table
|
|
33
|
-
from packaging.version import Version
|
|
34
33
|
from thefuzz import process
|
|
35
34
|
|
|
36
35
|
from tinybird.tb.client import (
|
|
@@ -61,7 +60,6 @@ from tinybird.tb.modules.exceptions import (
|
|
|
61
60
|
CLIAuthException,
|
|
62
61
|
CLIConnectionException,
|
|
63
62
|
CLIException,
|
|
64
|
-
CLIReleaseException,
|
|
65
63
|
CLIWorkspaceException,
|
|
66
64
|
)
|
|
67
65
|
from tinybird.tb.modules.feedback_manager import FeedbackManager, warning_message
|
|
@@ -378,9 +376,33 @@ def getenv_bool(key: str, default: bool) -> bool:
|
|
|
378
376
|
return v.lower() == "true" or v == "1"
|
|
379
377
|
|
|
380
378
|
|
|
381
|
-
def _get_tb_client(token: str, host: str, staging: bool = False) -> TinyB:
|
|
379
|
+
def _get_tb_client(token: str, host: str, staging: bool = False, branch: Optional[str] = None) -> TinyB:
|
|
382
380
|
disable_ssl: bool = getenv_bool("TB_DISABLE_SSL_CHECKS", False)
|
|
383
|
-
|
|
381
|
+
cloud_client = TinyB(
|
|
382
|
+
token,
|
|
383
|
+
host,
|
|
384
|
+
version=VERSION,
|
|
385
|
+
disable_ssl_checks=disable_ssl,
|
|
386
|
+
send_telemetry=True,
|
|
387
|
+
staging=staging,
|
|
388
|
+
)
|
|
389
|
+
|
|
390
|
+
if not branch:
|
|
391
|
+
return cloud_client
|
|
392
|
+
|
|
393
|
+
workspaces = cloud_client.user_workspaces_and_branches(version="v1")
|
|
394
|
+
workspace = next((w for w in workspaces.get("workspaces", []) if w.get("name") == branch), None)
|
|
395
|
+
if not workspace:
|
|
396
|
+
raise CLIException(FeedbackManager.error_exception(error=f"Branch {branch} not found"))
|
|
397
|
+
|
|
398
|
+
return TinyB(
|
|
399
|
+
workspace.get("token", ""),
|
|
400
|
+
host,
|
|
401
|
+
version=VERSION,
|
|
402
|
+
disable_ssl_checks=disable_ssl,
|
|
403
|
+
send_telemetry=True,
|
|
404
|
+
staging=staging,
|
|
405
|
+
)
|
|
384
406
|
|
|
385
407
|
|
|
386
408
|
def create_tb_client(ctx: Context) -> TinyB:
|
|
@@ -414,7 +436,16 @@ def analyze_file(filename: str, client: TinyB, format: str):
|
|
|
414
436
|
meta, data = _analyze(filename, client, format)
|
|
415
437
|
schema = meta["analysis"]["schema"]
|
|
416
438
|
schema = schema.replace(", ", ",\n ")
|
|
417
|
-
content = f"""DESCRIPTION
|
|
439
|
+
content = f"""DESCRIPTION >
|
|
440
|
+
Generated from {filename}
|
|
441
|
+
|
|
442
|
+
SCHEMA >
|
|
443
|
+
{schema}
|
|
444
|
+
|
|
445
|
+
ENGINE "MergeTree"
|
|
446
|
+
# ENGINE_SORTING_KEY "user_id, timestamp"
|
|
447
|
+
# ENGINE_TTL "timestamp + toIntervalDay(60)"
|
|
448
|
+
# Learn more at https://www.tinybird.co/docs/forward/dev-reference/datafiles/datasource-files"""
|
|
418
449
|
return content
|
|
419
450
|
|
|
420
451
|
|
|
@@ -429,7 +460,16 @@ def _generate_datafile(
|
|
|
429
460
|
meta, data = _analyze(filename, client, format, connector=connector)
|
|
430
461
|
schema = meta["analysis"]["schema"]
|
|
431
462
|
schema = schema.replace(", ", ",\n ")
|
|
432
|
-
datafile = f"""DESCRIPTION
|
|
463
|
+
datafile = f"""DESCRIPTION >
|
|
464
|
+
Generated from {filename}
|
|
465
|
+
|
|
466
|
+
SCHEMA >
|
|
467
|
+
{schema}
|
|
468
|
+
|
|
469
|
+
ENGINE "MergeTree"
|
|
470
|
+
# ENGINE_SORTING_KEY "user_id, timestamp"
|
|
471
|
+
# ENGINE_TTL "timestamp + toIntervalDay(60)"
|
|
472
|
+
# Learn more at https://www.tinybird.co/docs/forward/dev-reference/datafiles/datasource-files"""
|
|
433
473
|
return generate_datafile(datafile, filename, data, force, _format=format, folder=folder)
|
|
434
474
|
|
|
435
475
|
|
|
@@ -908,7 +948,7 @@ def get_format_from_filename_or_url(filename_or_url: str) -> str:
|
|
|
908
948
|
'csv'
|
|
909
949
|
"""
|
|
910
950
|
filename_or_url = filename_or_url.lower()
|
|
911
|
-
if filename_or_url.endswith("json"
|
|
951
|
+
if filename_or_url.endswith(("json", "ndjson")):
|
|
912
952
|
return "ndjson"
|
|
913
953
|
if filename_or_url.endswith("parquet"):
|
|
914
954
|
return "parquet"
|
|
@@ -916,7 +956,7 @@ def get_format_from_filename_or_url(filename_or_url: str) -> str:
|
|
|
916
956
|
return "csv"
|
|
917
957
|
try:
|
|
918
958
|
parsed = urlparse(filename_or_url)
|
|
919
|
-
if parsed.path.endswith("json"
|
|
959
|
+
if parsed.path.endswith(("json", "ndjson")):
|
|
920
960
|
return "ndjson"
|
|
921
961
|
if parsed.path.endswith("parquet"):
|
|
922
962
|
return "parquet"
|
|
@@ -965,7 +1005,10 @@ def push_data(
|
|
|
965
1005
|
cb.prev_done = 0 # type: ignore[attr-defined]
|
|
966
1006
|
|
|
967
1007
|
if not silent:
|
|
968
|
-
|
|
1008
|
+
if mode == "replace":
|
|
1009
|
+
click.echo(FeedbackManager.highlight(message=f"\n» Replacing data in {datasource_name}..."))
|
|
1010
|
+
else:
|
|
1011
|
+
click.echo(FeedbackManager.highlight(message=f"\n» Appending data to {datasource_name}..."))
|
|
969
1012
|
|
|
970
1013
|
if isinstance(url, list):
|
|
971
1014
|
urls = url
|
|
@@ -1165,10 +1208,26 @@ def _get_setting_value(connection, setting, sensitive_settings):
|
|
|
1165
1208
|
return connection.get(setting, "")
|
|
1166
1209
|
|
|
1167
1210
|
|
|
1168
|
-
def
|
|
1211
|
+
def get_current_workspace_branches(config: CLIConfig) -> List[Dict[str, Any]]:
|
|
1212
|
+
current_main_workspace: Optional[Dict[str, Any]] = get_current_main_workspace(config)
|
|
1213
|
+
if not current_main_workspace:
|
|
1214
|
+
raise CLIException(FeedbackManager.error_unable_to_identify_main_workspace())
|
|
1215
|
+
|
|
1216
|
+
client = config.get_client()
|
|
1217
|
+
user_branches: List[Dict[str, Any]] = (client.user_workspace_branches("v1")).get("workspaces", [])
|
|
1218
|
+
all_branches: List[Dict[str, Any]] = (client.branches()).get("environments", [])
|
|
1219
|
+
branches = user_branches + [branch for branch in all_branches if branch not in user_branches]
|
|
1220
|
+
|
|
1221
|
+
return [branch for branch in branches if branch.get("main") == current_main_workspace["id"]]
|
|
1222
|
+
|
|
1223
|
+
|
|
1224
|
+
def switch_workspace(config: CLIConfig, workspace_name_or_id: str, only_environments: bool = False) -> None:
|
|
1169
1225
|
try:
|
|
1170
|
-
|
|
1171
|
-
|
|
1226
|
+
if only_environments:
|
|
1227
|
+
workspaces = get_current_workspace_branches(config)
|
|
1228
|
+
else:
|
|
1229
|
+
response = config.get_client().user_workspaces(version="v1")
|
|
1230
|
+
workspaces = response["workspaces"]
|
|
1172
1231
|
|
|
1173
1232
|
workspace = next(
|
|
1174
1233
|
(
|
|
@@ -1563,130 +1622,6 @@ def _get_current_main_workspace_common(
|
|
|
1563
1622
|
return current
|
|
1564
1623
|
|
|
1565
1624
|
|
|
1566
|
-
def is_post_semver(new_version: Version, current_version: Version) -> bool:
|
|
1567
|
-
"""
|
|
1568
|
-
Check if only the post part of the semantic version has changed.
|
|
1569
|
-
|
|
1570
|
-
Args:
|
|
1571
|
-
new_version (Version): The new version to check.
|
|
1572
|
-
current_version (Version): The current version to compare with.
|
|
1573
|
-
|
|
1574
|
-
Returns:
|
|
1575
|
-
bool: True if only the post part of the version has changed, False otherwise.
|
|
1576
|
-
|
|
1577
|
-
Examples:
|
|
1578
|
-
>>> is_post_semver(Version("0.0.0-2"), Version("0.0.0-1"))
|
|
1579
|
-
True
|
|
1580
|
-
>>> is_post_semver(Version("0.0.0-1"), Version("0.0.0-1"))
|
|
1581
|
-
False
|
|
1582
|
-
>>> is_post_semver(Version("0.0.1-1"), Version("0.0.0-1"))
|
|
1583
|
-
False
|
|
1584
|
-
>>> is_post_semver(Version("0.1.0-1"), Version("0.0.0-1"))
|
|
1585
|
-
False
|
|
1586
|
-
>>> is_post_semver(Version("1.0.0-1"), Version("0.0.0-1"))
|
|
1587
|
-
False
|
|
1588
|
-
>>> is_post_semver(Version("0.0.1-1"), Version("0.0.0"))
|
|
1589
|
-
False
|
|
1590
|
-
"""
|
|
1591
|
-
if (
|
|
1592
|
-
new_version.major == current_version.major
|
|
1593
|
-
and new_version.minor == current_version.minor
|
|
1594
|
-
and new_version.micro == current_version.micro
|
|
1595
|
-
):
|
|
1596
|
-
return new_version.post is not None and new_version.post != current_version.post
|
|
1597
|
-
|
|
1598
|
-
return False
|
|
1599
|
-
|
|
1600
|
-
|
|
1601
|
-
def is_major_semver(new_version: Version, current_version: Version) -> bool:
|
|
1602
|
-
"""
|
|
1603
|
-
Check if only the major part of the semantic version has changed.
|
|
1604
|
-
|
|
1605
|
-
Args:
|
|
1606
|
-
new_version (Version): The new version to check.
|
|
1607
|
-
current_version (Version): The current version to compare with.
|
|
1608
|
-
|
|
1609
|
-
Returns:
|
|
1610
|
-
bool: True if only the major part of the version has changed, False otherwise.
|
|
1611
|
-
|
|
1612
|
-
Examples:
|
|
1613
|
-
>>> is_major_semver(Version("1.0.0"), Version("0.0.0"))
|
|
1614
|
-
True
|
|
1615
|
-
>>> is_major_semver(Version("0.0.0"), Version("0.0.0"))
|
|
1616
|
-
False
|
|
1617
|
-
>>> is_major_semver(Version("1.0.1"), Version("1.0.0"))
|
|
1618
|
-
False
|
|
1619
|
-
>>> is_major_semver(Version("2.0.0-1"), Version("1.0.1-2"))
|
|
1620
|
-
True
|
|
1621
|
-
"""
|
|
1622
|
-
|
|
1623
|
-
return new_version.major != current_version.major
|
|
1624
|
-
|
|
1625
|
-
|
|
1626
|
-
def print_release_summary(config: CLIConfig, semver: Optional[str], info: bool = False, dry_run=False):
|
|
1627
|
-
if not semver:
|
|
1628
|
-
click.echo(FeedbackManager.info_release_no_rollback())
|
|
1629
|
-
return
|
|
1630
|
-
try:
|
|
1631
|
-
client = config.get_client()
|
|
1632
|
-
response = client.release_rm(config["id"], semver, confirmation=config["name"], dry_run=True)
|
|
1633
|
-
except Exception as e:
|
|
1634
|
-
raise CLIReleaseException(FeedbackManager.error_exception(error=str(e)))
|
|
1635
|
-
else:
|
|
1636
|
-
columns = ["name", "id", "notes"]
|
|
1637
|
-
if not response:
|
|
1638
|
-
click.echo(FeedbackManager.info_release_no_rollback())
|
|
1639
|
-
return
|
|
1640
|
-
|
|
1641
|
-
if len(response["datasources"]) or len(response["pipes"]):
|
|
1642
|
-
semver = response.get("semver", semver)
|
|
1643
|
-
if info:
|
|
1644
|
-
if dry_run:
|
|
1645
|
-
click.echo(FeedbackManager.info_release_rm_resources_dry_run(semver=semver))
|
|
1646
|
-
else:
|
|
1647
|
-
click.echo(FeedbackManager.info_release_rm_resources())
|
|
1648
|
-
else:
|
|
1649
|
-
click.echo(FeedbackManager.info_release_rollback(semver=semver))
|
|
1650
|
-
|
|
1651
|
-
if len(response["datasources"]):
|
|
1652
|
-
click.echo("\nDatasources:")
|
|
1653
|
-
rows = [
|
|
1654
|
-
[ds, response["datasources"][ds], response["notes"].get(response["datasources"][ds], "")]
|
|
1655
|
-
for ds in response["datasources"]
|
|
1656
|
-
]
|
|
1657
|
-
echo_safe_humanfriendly_tables_format_smart_table(rows, column_names=columns)
|
|
1658
|
-
|
|
1659
|
-
if len(response["pipes"]):
|
|
1660
|
-
click.echo("\nPipes:")
|
|
1661
|
-
rows = [
|
|
1662
|
-
[pipe, response["pipes"][pipe], response["notes"].get(response["pipes"][pipe], "")]
|
|
1663
|
-
for pipe in response["pipes"]
|
|
1664
|
-
]
|
|
1665
|
-
echo_safe_humanfriendly_tables_format_smart_table(rows, column_names=columns)
|
|
1666
|
-
|
|
1667
|
-
|
|
1668
|
-
def get_oldest_rollback(config: CLIConfig, client: TinyB) -> Optional[str]:
|
|
1669
|
-
oldest_rollback_response = client.release_oldest_rollback(config["id"])
|
|
1670
|
-
return oldest_rollback_response.get("semver") if oldest_rollback_response else None
|
|
1671
|
-
|
|
1672
|
-
|
|
1673
|
-
def remove_release(
|
|
1674
|
-
dry_run: bool, config: CLIConfig, semver: Optional[str], client: TinyB, force: bool, show_print=True
|
|
1675
|
-
):
|
|
1676
|
-
if semver == OLDEST_ROLLBACK:
|
|
1677
|
-
semver = get_oldest_rollback(config, client)
|
|
1678
|
-
if show_print:
|
|
1679
|
-
print_release_summary(config, semver, info=True, dry_run=True)
|
|
1680
|
-
if not dry_run:
|
|
1681
|
-
if semver:
|
|
1682
|
-
response = client.release_rm(
|
|
1683
|
-
config["id"], semver, confirmation=config["name"], dry_run=dry_run, force=force
|
|
1684
|
-
)
|
|
1685
|
-
click.echo(FeedbackManager.success_release_delete(semver=response.get("semver")))
|
|
1686
|
-
else:
|
|
1687
|
-
click.echo(FeedbackManager.info_no_release_deleted())
|
|
1688
|
-
|
|
1689
|
-
|
|
1690
1625
|
def run_aws_iamrole_connection_flow(
|
|
1691
1626
|
client: TinyB,
|
|
1692
1627
|
service: str,
|
|
@@ -2197,18 +2132,17 @@ def ask_for_organization(
|
|
|
2197
2132
|
user_token = get_user_token(config, user_token)
|
|
2198
2133
|
organization = create_organization_and_add_workspaces(config, organization_name, user_token)
|
|
2199
2134
|
organization_id = organization.get("id")
|
|
2135
|
+
elif len(organizations) == 1:
|
|
2136
|
+
organization_name = organizations[0]["name"]
|
|
2137
|
+
organization_id = organizations[0]["id"]
|
|
2200
2138
|
else:
|
|
2201
|
-
|
|
2202
|
-
|
|
2203
|
-
|
|
2139
|
+
sorted_organizations = sort_organizations_by_user(organizations, user_email=user_email)
|
|
2140
|
+
current_organization = ask_for_organization_interactively(sorted_organizations)
|
|
2141
|
+
if current_organization:
|
|
2142
|
+
organization_id = current_organization.get("id")
|
|
2143
|
+
organization_name = current_organization.get("name")
|
|
2204
2144
|
else:
|
|
2205
|
-
|
|
2206
|
-
current_organization = ask_for_organization_interactively(sorted_organizations)
|
|
2207
|
-
if current_organization:
|
|
2208
|
-
organization_id = current_organization.get("id")
|
|
2209
|
-
organization_name = current_organization.get("name")
|
|
2210
|
-
else:
|
|
2211
|
-
return None, None
|
|
2145
|
+
return None, None
|
|
2212
2146
|
return organization_id, organization_name
|
|
2213
2147
|
|
|
2214
2148
|
|
|
@@ -2262,3 +2196,95 @@ def update_cli() -> None:
|
|
|
2262
2196
|
click.echo(FeedbackManager.success(message="✓ Tinybird CLI updated"))
|
|
2263
2197
|
else:
|
|
2264
2198
|
click.echo(FeedbackManager.info(message="✓ Tinybird CLI is already up-to-date"))
|
|
2199
|
+
|
|
2200
|
+
|
|
2201
|
+
def create_workspace_branch(
|
|
2202
|
+
branch_name: Optional[str],
|
|
2203
|
+
last_partition: bool,
|
|
2204
|
+
all: bool,
|
|
2205
|
+
ignore_datasources: Optional[List[str]],
|
|
2206
|
+
wait: Optional[bool],
|
|
2207
|
+
) -> None:
|
|
2208
|
+
"""
|
|
2209
|
+
Creates a workspace branch
|
|
2210
|
+
"""
|
|
2211
|
+
config = CLIConfig.get_project_config()
|
|
2212
|
+
_ = try_update_config_with_remote(config)
|
|
2213
|
+
|
|
2214
|
+
try:
|
|
2215
|
+
workspace = get_current_workspace(config)
|
|
2216
|
+
if not workspace:
|
|
2217
|
+
raise CLIWorkspaceException(FeedbackManager.error_workspace())
|
|
2218
|
+
|
|
2219
|
+
if not branch_name:
|
|
2220
|
+
click.echo(FeedbackManager.info_workspace_branch_create_greeting())
|
|
2221
|
+
default_name = f"{workspace['name']}_{uuid.uuid4().hex[0:4]}"
|
|
2222
|
+
branch_name = click.prompt("\Branch name", default=default_name, err=True, type=str)
|
|
2223
|
+
assert isinstance(branch_name, str)
|
|
2224
|
+
|
|
2225
|
+
response = config.get_client().create_workspace_branch(
|
|
2226
|
+
branch_name,
|
|
2227
|
+
last_partition,
|
|
2228
|
+
all,
|
|
2229
|
+
ignore_datasources,
|
|
2230
|
+
)
|
|
2231
|
+
assert isinstance(response, dict)
|
|
2232
|
+
|
|
2233
|
+
is_job: bool = "job" in response
|
|
2234
|
+
is_summary: bool = "partitions" in response
|
|
2235
|
+
|
|
2236
|
+
if not is_job and not is_summary:
|
|
2237
|
+
raise CLIException(str(response))
|
|
2238
|
+
|
|
2239
|
+
if all and not is_job:
|
|
2240
|
+
raise CLIException(str(response))
|
|
2241
|
+
|
|
2242
|
+
click.echo(
|
|
2243
|
+
FeedbackManager.success_workspace_branch_created(workspace_name=workspace["name"], branch_name=branch_name)
|
|
2244
|
+
)
|
|
2245
|
+
|
|
2246
|
+
job_id: Optional[str] = None
|
|
2247
|
+
|
|
2248
|
+
if is_job:
|
|
2249
|
+
job_id = response["job"]["job_id"]
|
|
2250
|
+
job_url = response["job"]["job_url"]
|
|
2251
|
+
click.echo(FeedbackManager.info_data_branch_job_url(url=job_url))
|
|
2252
|
+
|
|
2253
|
+
if wait and is_job:
|
|
2254
|
+
assert isinstance(job_id, str)
|
|
2255
|
+
|
|
2256
|
+
# Await the job to finish and get the result dict
|
|
2257
|
+
job_response = wait_job(config.get_client(), job_id, job_url, "Environment creation")
|
|
2258
|
+
if job_response is None:
|
|
2259
|
+
raise CLIException(f"Empty job API response (job_id: {job_id}, job_url: {job_url})")
|
|
2260
|
+
else:
|
|
2261
|
+
response = job_response.get("result", {})
|
|
2262
|
+
is_summary = "partitions" in response
|
|
2263
|
+
|
|
2264
|
+
except Exception as e:
|
|
2265
|
+
raise CLIException(FeedbackManager.error_exception(error=str(e)))
|
|
2266
|
+
|
|
2267
|
+
|
|
2268
|
+
async def print_current_branch(config: CLIConfig) -> None:
|
|
2269
|
+
_ = try_update_config_with_remote(config, only_if_needed=True)
|
|
2270
|
+
|
|
2271
|
+
response = config.get_client().user_workspaces_and_branches("v1")
|
|
2272
|
+
|
|
2273
|
+
columns = ["name", "id", "workspace"]
|
|
2274
|
+
table = []
|
|
2275
|
+
|
|
2276
|
+
for workspace in response["workspaces"]:
|
|
2277
|
+
if config["id"] == workspace["id"]:
|
|
2278
|
+
click.echo(FeedbackManager.info_current_branch())
|
|
2279
|
+
if workspace.get("is_branch"):
|
|
2280
|
+
name = workspace["name"]
|
|
2281
|
+
main_workspace = get_current_main_workspace(config)
|
|
2282
|
+
assert isinstance(main_workspace, dict)
|
|
2283
|
+
main_name = main_workspace["name"]
|
|
2284
|
+
else:
|
|
2285
|
+
name = MAIN_BRANCH
|
|
2286
|
+
main_name = workspace["name"]
|
|
2287
|
+
table.append([name, workspace["id"], main_name])
|
|
2288
|
+
break
|
|
2289
|
+
|
|
2290
|
+
echo_safe_humanfriendly_tables_format_smart_table(table, column_names=columns)
|