chipfoundry-cli 2.4.0__tar.gz → 2.4.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.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: chipfoundry-cli
3
- Version: 2.4.0
3
+ Version: 2.4.1
4
4
  Summary: CLI tool to automate ChipFoundry project submission to SFTP server
5
5
  Home-page: https://chipfoundry.io
6
6
  License: Apache-2.0
@@ -1,2 +1,2 @@
1
1
  """ChipFoundry CLI package: Automate project submission to SFTP."""
2
- __version__ = "2.3.2"
2
+ __version__ = "2.4.1"
@@ -402,8 +402,13 @@ def init(project_root, shuttle, description):
402
402
  local_proj = local_data.get('project', {}) if isinstance(local_data, dict) else {}
403
403
 
404
404
  config = load_user_config()
405
+ api_key = config.get('api_key')
405
406
  username = config.get("sftp_username")
406
- if not username:
407
+ # Try to refresh sftp_username from the platform, but don't block init on it.
408
+ # SFTP accounts are only auto-provisioned once a project deposit is paid/waived/
409
+ # sponsored and the user has an SSH key on their profile; init must work before
410
+ # that so users can configure locally and use `cf precheck` / `cf push --remote`.
411
+ if not username and api_key:
407
412
  try:
408
413
  me = _api_get("/auth/cli/whoami")
409
414
  username = me.get("sftp_username")
@@ -412,11 +417,10 @@ def init(project_root, shuttle, description):
412
417
  save_user_config(config)
413
418
  except SystemExit:
414
419
  pass
415
- if not username:
416
- console.print("[bold red]No SFTP account linked to your platform account. Please run 'cf login' first.[/bold red]")
417
- raise click.Abort()
418
-
419
- api_key = config.get('api_key')
420
+ # Fall back to email (or 'unknown') purely as a label in .cf/project.json.
421
+ # This field is metadata only: SFTP routing uses the live session identity,
422
+ # and the backend stores cli_project_json as an opaque blob.
423
+ user_label = username or config.get("user_email") or "unknown"
420
424
  platform_id = local_proj.get('platform_project_id')
421
425
  platform_proj: Optional[dict] = None
422
426
  if platform_id and api_key:
@@ -469,7 +473,7 @@ def init(project_root, shuttle, description):
469
473
  proj = data.setdefault('project', {})
470
474
  proj['name'] = name
471
475
  proj['type'] = project_type
472
- proj['user'] = username
476
+ proj['user'] = user_label
473
477
  proj.setdefault('version', local_proj.get('version') or "1")
474
478
  proj.setdefault('user_project_wrapper_hash', local_proj.get('user_project_wrapper_hash', ""))
475
479
  proj.setdefault('submission_state', local_proj.get('submission_state', "Draft"))
@@ -1619,7 +1623,11 @@ def push(project_root, sftp_host, sftp_username, sftp_key, project_id, project_n
1619
1623
  sftp_username = me.get("sftp_username")
1620
1624
  if not sftp_username:
1621
1625
  console.print("[bold red]No SFTP account linked to your platform account.[/bold red]")
1622
- console.print("Contact support or provide --sftp-username.")
1626
+ console.print(
1627
+ "An SFTP account is provisioned once a project deposit is paid/waived/sponsored "
1628
+ "and an SSH public key is on your profile."
1629
+ )
1630
+ console.print("Override with --sftp-username if you already know yours, or contact support.")
1623
1631
  raise click.Abort()
1624
1632
  config["sftp_username"] = sftp_username
1625
1633
  save_user_config(config)
@@ -1805,7 +1813,11 @@ def pull(project_name, output_dir, sftp_host, sftp_username, sftp_key):
1805
1813
  sftp_username = me.get("sftp_username")
1806
1814
  if not sftp_username:
1807
1815
  console.print("[bold red]No SFTP account linked to your platform account.[/bold red]")
1808
- console.print("Contact support or provide --sftp-username.")
1816
+ console.print(
1817
+ "An SFTP account is provisioned once a project deposit is paid/waived/sponsored "
1818
+ "and an SSH public key is on your profile."
1819
+ )
1820
+ console.print("Override with --sftp-username if you already know yours, or contact support.")
1809
1821
  raise click.Abort()
1810
1822
  config["sftp_username"] = sftp_username
1811
1823
  save_user_config(config)
@@ -2089,24 +2101,34 @@ def status(sftp_host, sftp_username, sftp_key, json_output, show_all):
2089
2101
  platform_id = _load_project_platform_id(os.getcwd())
2090
2102
  if not platform_id:
2091
2103
  console.print("[dim]Tip: Run [bold]cf link[/bold] to connect this project to the platform.[/dim]\n")
2104
+ # SFTP listing is a best-effort extra on top of the platform status above.
2105
+ # Skip it quietly when the user has no SFTP account yet (auto-provisioned
2106
+ # after a project deposit is paid/waived/sponsored + an SSH key is on file).
2092
2107
  if not sftp_username:
2093
- me = _api_get("/auth/cli/whoami")
2094
- sftp_username = me.get("sftp_username")
2108
+ if config.get("api_key"):
2109
+ try:
2110
+ me = _api_get("/auth/cli/whoami")
2111
+ sftp_username = me.get("sftp_username")
2112
+ except SystemExit:
2113
+ sftp_username = None
2095
2114
  if not sftp_username:
2096
- console.print("[red]No SFTP account linked to your platform account.[/red]")
2097
- console.print("Contact support or provide --sftp-username.")
2098
- raise click.Abort()
2115
+ console.print(
2116
+ "[dim]SFTP listing skipped no SFTP account linked yet. "
2117
+ "An account is provisioned once a project deposit is paid/waived/sponsored "
2118
+ "and an SSH public key is on your profile.[/dim]"
2119
+ )
2120
+ return
2099
2121
  config["sftp_username"] = sftp_username
2100
2122
  save_user_config(config)
2101
2123
  if not sftp_key:
2102
2124
  sftp_key = config.get("sftp_key")
2103
-
2125
+
2104
2126
  # Always resolve key_path to absolute path if set
2105
2127
  if sftp_key:
2106
2128
  key_path = os.path.abspath(os.path.expanduser(sftp_key))
2107
2129
  else:
2108
2130
  key_path = DEFAULT_SSH_KEY
2109
-
2131
+
2110
2132
  if not os.path.exists(key_path):
2111
2133
  console.print(f"[red]SFTP key file not found: {key_path}[/red]")
2112
2134
  console.print("[yellow]Please run 'cf keygen' to generate a key or 'cf config' to set a custom key path.[/yellow]")
@@ -2232,7 +2254,11 @@ def tapeouts(sftp_host, sftp_username, sftp_key, limit, days):
2232
2254
  sftp_username = me.get("sftp_username")
2233
2255
  if not sftp_username:
2234
2256
  console.print("[red]No SFTP account linked to your platform account.[/red]")
2235
- console.print("Contact support or provide --sftp-username.")
2257
+ console.print(
2258
+ "An SFTP account is provisioned once a project deposit is paid/waived/sponsored "
2259
+ "and an SSH public key is on your profile."
2260
+ )
2261
+ console.print("Override with --sftp-username if you already know yours, or contact support.")
2236
2262
  raise click.Abort()
2237
2263
  config["sftp_username"] = sftp_username
2238
2264
  save_user_config(config)
@@ -2422,7 +2448,11 @@ def confirm(project_root, sftp_host, sftp_username, sftp_key, project_name):
2422
2448
  sftp_username = me.get("sftp_username")
2423
2449
  if not sftp_username:
2424
2450
  console.print("[bold red]No SFTP account linked to your platform account.[/bold red]")
2425
- console.print("Contact support or provide --sftp-username.")
2451
+ console.print(
2452
+ "An SFTP account is provisioned once a project deposit is paid/waived/sponsored "
2453
+ "and an SSH public key is on your profile."
2454
+ )
2455
+ console.print("Override with --sftp-username if you already know yours, or contact support.")
2426
2456
  raise click.Abort()
2427
2457
  config["sftp_username"] = sftp_username
2428
2458
  save_user_config(config)
@@ -1,6 +1,6 @@
1
1
  [tool.poetry]
2
2
  name = "chipfoundry-cli"
3
- version = "2.4.0"
3
+ version = "2.4.1"
4
4
  description = "CLI tool to automate ChipFoundry project submission to SFTP server"
5
5
  authors = ["ChipFoundry <marwan.abbas@chipfoundry.io>"]
6
6
  readme = "README.md"
File without changes