fufu-cloud-cli 0.9.8__tar.gz → 0.10.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.
- {fufu_cloud_cli-0.9.8/src/fufu_cloud_cli.egg-info → fufu_cloud_cli-0.10.1}/PKG-INFO +37 -9
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/README.md +36 -8
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/pyproject.toml +1 -1
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/__init__.py +1 -1
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/api_backend.py +7 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/aws_errors.py +1 -1
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/capabilities.json +35 -19
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/cli.py +9 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/control.py +2 -1
- fufu_cloud_cli-0.10.1/src/fufu_cloud_cli/infrastructure.py +283 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/pulumi_bridge.py +5 -3
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/terraform_bridge/common.py +5 -1
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/terraform_bridge/google.py +3 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/terraform_bridge/runner.py +42 -9
- fufu_cloud_cli-0.10.1/src/fufu_cloud_cli/terraform_bridge/storage.py +173 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1/src/fufu_cloud_cli.egg-info}/PKG-INFO +37 -9
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli.egg-info/SOURCES.txt +2 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/LICENSE +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/MANIFEST.in +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/setup.cfg +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/__main__.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/aws_lambda.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/aws_output.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/bigquery.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/capacity.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/cloud_data.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/cloudflare.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/docker_backend.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/errors.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/gcloud_environment.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/gcloud_output.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/gcp_infra.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/gcp_sdk.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/gcs.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/http_runtime.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/iac_state.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/lambda_adapter.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/limits.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/manifest.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/object_transfer.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/observability.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/public_access.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/pubsub.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/pulumi-endpoints.json +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/remote_compute.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/runtime/functions/Dockerfile +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/runtime/ingress/Dockerfile +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/runtime/ingress/proxy.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/runtime_sdk.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/secrets.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/serverless.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/terraform_bridge/__init__.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/terraform_bridge/aws.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/terraform_bridge/aws_data.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/terraform_bridge/google_pubsub.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/terraform_bridge/remote_state.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/vendor/AWS-CLI-LICENSE.txt +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/vendor/__init__.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli/vendor/aws_text.py +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli.egg-info/dependency_links.txt +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli.egg-info/entry_points.txt +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli.egg-info/requires.txt +0 -0
- {fufu_cloud_cli-0.9.8 → fufu_cloud_cli-0.10.1}/src/fufu_cloud_cli.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: fufu-cloud-cli
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.10.1
|
|
4
4
|
Summary: FUFU Cloud CLI for tenant-scoped mock cloud development and deployment
|
|
5
5
|
License-Expression: LicenseRef-Proprietary
|
|
6
6
|
Requires-Python: >=3.10
|
|
@@ -27,10 +27,37 @@ Dynamic: license-file
|
|
|
27
27
|
`gcloud-fufu`、`az-fufu`、`wrangler-fufu`、`bq-fufu`。這是 AWS、Google Cloud、Azure 與 Cloudflare 的**明確子集**,
|
|
28
28
|
只供 FUFU mock 環境使用;不會把部署轉送到正式雲端。
|
|
29
29
|
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
30
|
+
0.10.1 新增官方 Terraform/OpenTofu/Pulumi 的 S3/GCS bucket 生命週期與
|
|
31
|
+
S3 bucket tags。需配套 FUFU API;不支援 bucket versioning、retention、
|
|
32
|
+
KMS、bucket IAM、GCS bucket labels 或 force destroy。
|
|
33
|
+
|
|
34
|
+
0.10.0 新增 Compute Engine/EC2 VM 與 GKE/EKS 介面的實際運算命令。
|
|
35
|
+
需要啟用相應 infrastructure backend 的 FUFU 服務端;VM 使用 KVM/KubeVirt,
|
|
36
|
+
叢集使用獨立 Kubernetes API 與共用節點,均不是官方雲端資源。
|
|
37
|
+
支援 VM 建立、SSH 指令、停止/啟動與刪除,以及叢集建立、查詢、
|
|
38
|
+
get-credentials/update-kubeconfig、waiter 與刪除。
|
|
39
|
+
取得憑證後可使用標準 kubectl 部署 Deployment、Service、Job 及受管 GPU 容器。
|
|
40
|
+
工作站需另安裝 kubectl;配套 Cloud Shell 已提供。
|
|
41
|
+
|
|
42
|
+
VM 尚無公開 IP、複寫儲存、live migration 或自助 GPU passthrough;
|
|
43
|
+
叢集尚無 workload PVC、公開 LoadBalancer、互動式 exec/attach/port-forward。
|
|
44
|
+
這批新 VM/cluster API 尚未支援官方 Terraform/OpenTofu/Pulumi provider。
|
|
45
|
+
原有 firewall、global LB、Redis 等 typed configuration 仍明示 `MOCK ONLY`,
|
|
46
|
+
不代表已建立相應網路或 Redis 資料面。
|
|
47
|
+
|
|
48
|
+
```bash
|
|
49
|
+
gcloud-fufu compute instances create demo-vm --image-family=debian-12
|
|
50
|
+
gcloud-fufu compute ssh demo-vm --command='uname -s; nproc'
|
|
51
|
+
gcloud-fufu container clusters create demo-gke
|
|
52
|
+
gcloud-fufu container clusters get-credentials demo-gke
|
|
53
|
+
kubectl get pods -A
|
|
54
|
+
aws-fufu eks create-cluster --name demo-eks
|
|
55
|
+
aws-fufu eks wait cluster-active --name demo-eks
|
|
56
|
+
aws-fufu eks update-kubeconfig --name demo-eks
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
這些操作需要 FUFU credential;不使用官方雲端金鑰。資源以租戶隔離,配額不足
|
|
60
|
+
會明確回覆 RESOURCE_EXHAUSTED。測試後請刪除所建 VM/cluster 以釋放資源。
|
|
34
61
|
|
|
35
62
|
0.9.8 提供 Cloud Run/Functions 的原生形式日誌查詢、CloudWatch Logs
|
|
36
63
|
tail/follow,以及 `fufu observability` 的日誌、請求指標與追蹤查詢。
|
|
@@ -73,9 +100,10 @@ insertAll/SELECT 與持久化日誌。`fufu_cloud_cli.gcp_sdk` 提供官方 Py
|
|
|
73
100
|
BigQuery、Cloud Tasks、Logging SDK 的明確 REST factory;可用 `[gcp]` extra
|
|
74
101
|
安裝已驗收相依。需要對應的新後端,並非透明 ADC 或所有 Google SDK 替換。
|
|
75
102
|
|
|
76
|
-
`fufu infrastructure`
|
|
77
|
-
|
|
78
|
-
|
|
103
|
+
`fufu infrastructure` 另保留 typed configuration mock 目錄,包含 Cloud SQL、
|
|
104
|
+
App Engine、DNS、VPC、Artifact Registry、Cloud Build、Gemini、VM Manager、
|
|
105
|
+
Eventarc 等。這個目錄只保存配置,不啟動 SQL/registry/網路/推論;
|
|
106
|
+
實際 VM/Kubernetes 請使用上述 compute/ec2/container/eks 指令。
|
|
79
107
|
UI 顯示僅設定,CLI stderr 保留 MOCK ONLY,不因輸出投影而隱藏。
|
|
80
108
|
新服務尚未接入 Terraform/OpenTofu/Pulumi;單機背景投遞不是雲端 HA。
|
|
81
109
|
|
|
@@ -107,7 +135,7 @@ Python 預設識別而遇到 Cloudflare HTTP 403/1010。識別標頭不取代
|
|
|
107
135
|
## Cloudflare 前端部署與 R2
|
|
108
136
|
|
|
109
137
|
```bash
|
|
110
|
-
pip install 'fufu-cloud-cli==0.
|
|
138
|
+
pip install 'fufu-cloud-cli==0.10.1'
|
|
111
139
|
export FUFU_CLOUDFLARE_CREDENTIAL_FILE=/run/secrets/fufu-cloudflare.json
|
|
112
140
|
wrangler-fufu capabilities
|
|
113
141
|
wrangler-fufu pages project create frontend --production-branch main
|
|
@@ -4,10 +4,37 @@
|
|
|
4
4
|
`gcloud-fufu`、`az-fufu`、`wrangler-fufu`、`bq-fufu`。這是 AWS、Google Cloud、Azure 與 Cloudflare 的**明確子集**,
|
|
5
5
|
只供 FUFU mock 環境使用;不會把部署轉送到正式雲端。
|
|
6
6
|
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
7
|
+
0.10.1 新增官方 Terraform/OpenTofu/Pulumi 的 S3/GCS bucket 生命週期與
|
|
8
|
+
S3 bucket tags。需配套 FUFU API;不支援 bucket versioning、retention、
|
|
9
|
+
KMS、bucket IAM、GCS bucket labels 或 force destroy。
|
|
10
|
+
|
|
11
|
+
0.10.0 新增 Compute Engine/EC2 VM 與 GKE/EKS 介面的實際運算命令。
|
|
12
|
+
需要啟用相應 infrastructure backend 的 FUFU 服務端;VM 使用 KVM/KubeVirt,
|
|
13
|
+
叢集使用獨立 Kubernetes API 與共用節點,均不是官方雲端資源。
|
|
14
|
+
支援 VM 建立、SSH 指令、停止/啟動與刪除,以及叢集建立、查詢、
|
|
15
|
+
get-credentials/update-kubeconfig、waiter 與刪除。
|
|
16
|
+
取得憑證後可使用標準 kubectl 部署 Deployment、Service、Job 及受管 GPU 容器。
|
|
17
|
+
工作站需另安裝 kubectl;配套 Cloud Shell 已提供。
|
|
18
|
+
|
|
19
|
+
VM 尚無公開 IP、複寫儲存、live migration 或自助 GPU passthrough;
|
|
20
|
+
叢集尚無 workload PVC、公開 LoadBalancer、互動式 exec/attach/port-forward。
|
|
21
|
+
這批新 VM/cluster API 尚未支援官方 Terraform/OpenTofu/Pulumi provider。
|
|
22
|
+
原有 firewall、global LB、Redis 等 typed configuration 仍明示 `MOCK ONLY`,
|
|
23
|
+
不代表已建立相應網路或 Redis 資料面。
|
|
24
|
+
|
|
25
|
+
```bash
|
|
26
|
+
gcloud-fufu compute instances create demo-vm --image-family=debian-12
|
|
27
|
+
gcloud-fufu compute ssh demo-vm --command='uname -s; nproc'
|
|
28
|
+
gcloud-fufu container clusters create demo-gke
|
|
29
|
+
gcloud-fufu container clusters get-credentials demo-gke
|
|
30
|
+
kubectl get pods -A
|
|
31
|
+
aws-fufu eks create-cluster --name demo-eks
|
|
32
|
+
aws-fufu eks wait cluster-active --name demo-eks
|
|
33
|
+
aws-fufu eks update-kubeconfig --name demo-eks
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
這些操作需要 FUFU credential;不使用官方雲端金鑰。資源以租戶隔離,配額不足
|
|
37
|
+
會明確回覆 RESOURCE_EXHAUSTED。測試後請刪除所建 VM/cluster 以釋放資源。
|
|
11
38
|
|
|
12
39
|
0.9.8 提供 Cloud Run/Functions 的原生形式日誌查詢、CloudWatch Logs
|
|
13
40
|
tail/follow,以及 `fufu observability` 的日誌、請求指標與追蹤查詢。
|
|
@@ -50,9 +77,10 @@ insertAll/SELECT 與持久化日誌。`fufu_cloud_cli.gcp_sdk` 提供官方 Py
|
|
|
50
77
|
BigQuery、Cloud Tasks、Logging SDK 的明確 REST factory;可用 `[gcp]` extra
|
|
51
78
|
安裝已驗收相依。需要對應的新後端,並非透明 ADC 或所有 Google SDK 替換。
|
|
52
79
|
|
|
53
|
-
`fufu infrastructure`
|
|
54
|
-
|
|
55
|
-
|
|
80
|
+
`fufu infrastructure` 另保留 typed configuration mock 目錄,包含 Cloud SQL、
|
|
81
|
+
App Engine、DNS、VPC、Artifact Registry、Cloud Build、Gemini、VM Manager、
|
|
82
|
+
Eventarc 等。這個目錄只保存配置,不啟動 SQL/registry/網路/推論;
|
|
83
|
+
實際 VM/Kubernetes 請使用上述 compute/ec2/container/eks 指令。
|
|
56
84
|
UI 顯示僅設定,CLI stderr 保留 MOCK ONLY,不因輸出投影而隱藏。
|
|
57
85
|
新服務尚未接入 Terraform/OpenTofu/Pulumi;單機背景投遞不是雲端 HA。
|
|
58
86
|
|
|
@@ -84,7 +112,7 @@ Python 預設識別而遇到 Cloudflare HTTP 403/1010。識別標頭不取代
|
|
|
84
112
|
## Cloudflare 前端部署與 R2
|
|
85
113
|
|
|
86
114
|
```bash
|
|
87
|
-
pip install 'fufu-cloud-cli==0.
|
|
115
|
+
pip install 'fufu-cloud-cli==0.10.1'
|
|
88
116
|
export FUFU_CLOUDFLARE_CREDENTIAL_FILE=/run/secrets/fufu-cloudflare.json
|
|
89
117
|
wrangler-fufu capabilities
|
|
90
118
|
wrangler-fufu pages project create frontend --production-branch main
|
|
@@ -184,6 +184,13 @@ class ApiClient:
|
|
|
184
184
|
return json.loads(raw)
|
|
185
185
|
except HTTPError as exc:
|
|
186
186
|
status = exc.code
|
|
187
|
+
if '/infrastructure/' in path and status == 429:
|
|
188
|
+
try:
|
|
189
|
+
value = json.loads(exc.read(4096))
|
|
190
|
+
if isinstance(value, dict) and value.get('code') == 'RESOURCE_EXHAUSTED':
|
|
191
|
+
raise FufuError('RESOURCE_EXHAUSTED', 'FUFU 租戶資源配額或主機容量已滿;請刪除不需要的資源,或調整平台資源配額後再重試。') from None
|
|
192
|
+
except (ValueError, OSError): pass
|
|
193
|
+
finally: exc.close()
|
|
187
194
|
if self.provider == 'aws' and '/compute/' in path and status in {400, 412}:
|
|
188
195
|
try:
|
|
189
196
|
value = json.loads(exc.read(4096))
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"""Only documented provider error codes may cross the public transport boundary."""
|
|
2
2
|
AWS_ERRORS = frozenset('''ConditionalCheckFailedException ResourceNotFoundException ResourceInUseException ResourceAlreadyExistsException ValidationException
|
|
3
|
-
NoSuchKey NoSuchBucket NotFound NotModified ParameterNotFound ParameterAlreadyExists ParameterVersionNotFound QueueDoesNotExist
|
|
3
|
+
NoSuchKey NoSuchBucket NoSuchTagSet BucketAlreadyExists BucketAlreadyOwnedByYou BucketNotEmpty NotFound NotModified ParameterNotFound ParameterAlreadyExists ParameterVersionNotFound QueueDoesNotExist
|
|
4
4
|
PreconditionFailed InvalidRange InvalidParameterException InvalidParameterValue InvalidAttributeName InvalidAttributeValue QueueNameExists
|
|
5
5
|
PurgeQueueInProgress ReceiptHandleIsInvalid BatchEntryIdsNotDistinct EmptyBatchRequest BatchRequestTooLong InvalidBatchEntryId
|
|
6
6
|
TooManyEntriesInBatchRequest InvalidMessageContents AWS.SimpleQueueService.NonExistentQueue TooManyRequestsException InvalidRequestContentException'''.split())
|
|
@@ -27,11 +27,11 @@
|
|
|
27
27
|
"backend": "api",
|
|
28
28
|
"compatibility": "official-provider-subset",
|
|
29
29
|
"providers": { "hashicorp/aws": "6.63.0", "hashicorp/google": "8.1.0" },
|
|
30
|
-
"resources": ["aws_iam_role", "aws_iam_role_policy", "aws_lambda_function", "aws_lambda_function_url", "aws_lambda_permission", "google_service_account", "google_cloud_run_v2_service", "google_cloud_run_v2_service_iam_member", "aws_sqs_queue", "aws_ssm_parameter", "google_pubsub_topic", "google_pubsub_subscription"],
|
|
30
|
+
"resources": ["aws_iam_role", "aws_iam_role_policy", "aws_lambda_function", "aws_lambda_function_url", "aws_lambda_permission", "google_service_account", "google_cloud_run_v2_service", "google_cloud_run_v2_service_iam_member", "aws_sqs_queue", "aws_ssm_parameter", "google_pubsub_topic", "google_pubsub_subscription", "aws_s3_bucket", "google_storage_bucket"],
|
|
31
31
|
"operations": ["init", "plan", "saved-plan-apply", "refresh", "update", "import", "destroy"],
|
|
32
|
-
"engines": { "terraform": "1.16.
|
|
32
|
+
"engines": { "terraform": "1.16.2", "opentofu": "1.12.6" },
|
|
33
33
|
"state": ["isolated-local", "tenant-remote-http", "context-binding"],
|
|
34
|
-
"limitations": ["Linux-amd64-verified", "terraform-extra-required", "root-default-providers-only", "OpenTofu-data-resources-verified-compute-not-retested", "no-full-cloud-IAM-or-runtime-equivalence", "no-
|
|
34
|
+
"limitations": ["Linux-amd64-verified", "terraform-extra-required", "root-default-providers-only", "OpenTofu-data-resources-verified-compute-not-retested", "no-full-cloud-IAM-or-runtime-equivalence", "no-VM-cluster-Functions-Gen1-Gen2-IaC", "storage-bucket-lifecycle-and-S3-tags-only", "no-force-destroy-retention-versioning-bucket-IAM-KMS", "PubSub-requires-patched-emulator", "unsupported-APIs-and-fields-fail-explicitly"]
|
|
35
35
|
},
|
|
36
36
|
"iac-remote-state": {
|
|
37
37
|
"status": "implemented", "backend": "api", "mode": "simplified",
|
|
@@ -41,7 +41,7 @@
|
|
|
41
41
|
"pulumi-data": {
|
|
42
42
|
"status": "implemented", "backend": "api", "compatibility": "official-provider-subset",
|
|
43
43
|
"providers": { "pulumi": "3.261.0", "aws": "7.45.0", "gcp": "9.36.1" },
|
|
44
|
-
"resources": ["aws:sqs/queue:Queue", "aws:ssm/parameter:Parameter", "gcp:pubsub/topic:Topic", "gcp:pubsub/subscription:Subscription"],
|
|
44
|
+
"resources": ["aws:sqs/queue:Queue", "aws:ssm/parameter:Parameter", "gcp:pubsub/topic:Topic", "gcp:pubsub/subscription:Subscription", "aws:s3/bucket:Bucket", "gcp:storage/bucket:Bucket"],
|
|
45
45
|
"operations": ["preview", "up", "refresh", "update", "import", "destroy"],
|
|
46
46
|
"limitations": ["Node.js-runtime", "default-providers", "separate-local-DIY-state", "external-passphrase-required", "secret-fields-encrypted-not-whole-state", "no-remote-backend", "no-compute-resource-acceptance", "trusted-programs-only"]
|
|
47
47
|
},
|
|
@@ -197,7 +197,8 @@
|
|
|
197
197
|
"metadata-describe-update-merge-delete",
|
|
198
198
|
"paginated-object-list",
|
|
199
199
|
"binary-cat",
|
|
200
|
-
"UTF8-preview"
|
|
200
|
+
"UTF8-preview",
|
|
201
|
+
"Terraform-OpenTofu-Pulumi-bucket-lifecycle"
|
|
201
202
|
],
|
|
202
203
|
"limitations": [
|
|
203
204
|
"object-5TiB-policy-subject-to-host-disk-capacity",
|
|
@@ -209,7 +210,8 @@
|
|
|
209
210
|
"single-writer-per-volume",
|
|
210
211
|
"no-signed-URLs",
|
|
211
212
|
"no-versioning-retention-ACL-KMS",
|
|
212
|
-
"no-
|
|
213
|
+
"no-bucket-labels-IAM-PATCH-force-destroy",
|
|
214
|
+
"bucket-current-tenant-location-STANDARD-only"
|
|
213
215
|
]
|
|
214
216
|
},
|
|
215
217
|
"azure-catalog-api": {
|
|
@@ -270,7 +272,11 @@
|
|
|
270
272
|
"rb",
|
|
271
273
|
"ls",
|
|
272
274
|
"cp-upload-download",
|
|
273
|
-
"rm"
|
|
275
|
+
"rm",
|
|
276
|
+
"get-bucket-tagging",
|
|
277
|
+
"put-bucket-tagging",
|
|
278
|
+
"delete-bucket-tagging",
|
|
279
|
+
"Terraform-OpenTofu-Pulumi-bucket-lifecycle"
|
|
274
280
|
],
|
|
275
281
|
"limitations": [
|
|
276
282
|
"object-10000-parts-of-up-to-5GiB-subject-to-host-disk-capacity",
|
|
@@ -534,21 +540,23 @@
|
|
|
534
540
|
},
|
|
535
541
|
"gcp-compute-engine": {
|
|
536
542
|
"name": "Compute Engine",
|
|
537
|
-
"status": "
|
|
543
|
+
"status": "implemented",
|
|
538
544
|
"backend": "api",
|
|
539
|
-
"mode": "
|
|
545
|
+
"mode": "simplified",
|
|
540
546
|
"operations": [
|
|
541
|
-
"
|
|
547
|
+
"create-list-describe-delete", "stop-start", "guest-ssh-command"
|
|
542
548
|
],
|
|
543
|
-
"
|
|
549
|
+
"limitations": ["requires-FUFU-infrastructure-backend", "Debian-12-only", "private-network", "single-node-disk", "no-self-service-GPU-passthrough", "no-official-IaC-provider"],
|
|
550
|
+
"reason": "實際 KVM/KubeVirt VM、持久磁碟與 SSH 指令;原生風格指令子集,無官方雲端資源。"
|
|
544
551
|
},
|
|
545
552
|
"gcp-gke": {
|
|
546
553
|
"name": "GKE",
|
|
547
|
-
"status": "
|
|
554
|
+
"status": "implemented",
|
|
548
555
|
"backend": "api",
|
|
549
|
-
"mode": "
|
|
550
|
-
"operations": ["
|
|
551
|
-
"
|
|
556
|
+
"mode": "simplified",
|
|
557
|
+
"operations": ["create-list-describe-delete", "get-credentials", "kubectl-workloads", "GPU-container-jobs"],
|
|
558
|
+
"limitations": ["requires-FUFU-infrastructure-backend", "shared-workers", "single-control-plane-replica", "no-workload-PVC", "no-public-LoadBalancer", "no-interactive-exec-or-portforward", "no-official-IaC-provider"],
|
|
559
|
+
"reason": "獨立 vCluster Kubernetes API 與控制面資料;共用受管節點,支援標準 kubectl 工作負載子集。"
|
|
552
560
|
},
|
|
553
561
|
"gcp-vpc": {
|
|
554
562
|
"name": "VPC / Firewall",
|
|
@@ -637,8 +645,12 @@
|
|
|
637
645
|
},
|
|
638
646
|
"aws-ec2": {
|
|
639
647
|
"name": "EC2",
|
|
640
|
-
"status": "
|
|
641
|
-
"
|
|
648
|
+
"status": "implemented",
|
|
649
|
+
"backend": "api",
|
|
650
|
+
"mode": "simplified",
|
|
651
|
+
"operations": ["run-describe-terminate-instances", "stop-start", "instance-waiters"],
|
|
652
|
+
"limitations": ["requires-FUFU-infrastructure-backend", "Debian-12-only", "private-network", "single-node-disk", "no-self-service-GPU-passthrough", "no-official-IaC-provider"],
|
|
653
|
+
"reason": "實際 KVM/KubeVirt VM;支援生命週期與 scoped instance ID,無官方 EC2 網路或完整 API。"
|
|
642
654
|
},
|
|
643
655
|
"aws-ecs": {
|
|
644
656
|
"name": "ECS / Fargate",
|
|
@@ -647,8 +659,12 @@
|
|
|
647
659
|
},
|
|
648
660
|
"aws-eks": {
|
|
649
661
|
"name": "EKS",
|
|
650
|
-
"status": "
|
|
651
|
-
"
|
|
662
|
+
"status": "implemented",
|
|
663
|
+
"backend": "api",
|
|
664
|
+
"mode": "simplified",
|
|
665
|
+
"operations": ["create-list-describe-delete", "update-kubeconfig", "cluster-waiters", "kubectl-workloads", "GPU-container-jobs"],
|
|
666
|
+
"limitations": ["requires-FUFU-infrastructure-backend", "shared-workers", "single-control-plane-replica", "no-workload-PVC", "no-public-LoadBalancer", "no-interactive-exec-or-portforward", "no-official-IaC-provider"],
|
|
667
|
+
"reason": "獨立 vCluster Kubernetes API 與控制面資料;FUFU 短效認證,不是 AWS 原生 IAM 或託管控制面。"
|
|
652
668
|
},
|
|
653
669
|
"aws-app-runner": {
|
|
654
670
|
"name": "App Runner",
|
|
@@ -518,6 +518,9 @@ def entry(provider, argv=None):
|
|
|
518
518
|
if provider == 'fufu' and argv[:1] == ['infrastructure']:
|
|
519
519
|
from .gcp_infra import configuration_command
|
|
520
520
|
emit(configuration_command(argv[1:], Parser)); return
|
|
521
|
+
if provider == 'fufu' and argv[:1] == ['kubernetes-token']:
|
|
522
|
+
from .infrastructure import token_command
|
|
523
|
+
emit(token_command(argv[1:], Parser)); return
|
|
521
524
|
# Native global selectors are checked against the authenticated tenant scope.
|
|
522
525
|
if provider in {'aws-fufu', 'gcloud-fufu'}:
|
|
523
526
|
rest = []; i = 0; explicit_region = False
|
|
@@ -580,6 +583,12 @@ def entry(provider, argv=None):
|
|
|
580
583
|
if output_format and argv[:2] == ['functions', 'call']:
|
|
581
584
|
require(output_format == 'json', 'UNSUPPORTED_FORMAT', 'Functions call 目前只支援 JSON 回應。')
|
|
582
585
|
from . import public_access
|
|
586
|
+
if provider == 'gcloud-fufu' and argv[:2] in [['compute', 'instances'], ['compute', 'ssh'], ['container', 'clusters']]:
|
|
587
|
+
from .infrastructure import gcp_command
|
|
588
|
+
emit(gcp_command(argv, Parser)); return
|
|
589
|
+
if provider == 'aws-fufu' and argv[:1] in [['ec2'], ['eks']]:
|
|
590
|
+
from .infrastructure import aws_command as infrastructure_aws_command
|
|
591
|
+
emit(infrastructure_aws_command(argv, Parser)); return
|
|
583
592
|
if provider == 'gcloud-fufu' and argv and argv[0] in {'scheduler', 'tasks', 'logging', 'compute', 'sql', 'artifacts', 'dns', 'eventarc', 'container', 'redis'}:
|
|
584
593
|
from .gcp_infra import command
|
|
585
594
|
emit(command(argv, Parser)); return
|
|
@@ -28,6 +28,7 @@ AWS_OPERATIONS = {
|
|
|
28
28
|
},
|
|
29
29
|
's3api': {
|
|
30
30
|
'CreateBucket': 'Bucket CreateBucketConfiguration', 'DeleteBucket': 'Bucket', 'ListBuckets': '', 'HeadBucket': 'Bucket', 'GetBucketLocation': 'Bucket',
|
|
31
|
+
'GetBucketTagging': 'Bucket', 'PutBucketTagging': 'Bucket Tagging', 'DeleteBucketTagging': 'Bucket',
|
|
31
32
|
'ListObjectsV2': 'Bucket Prefix MaxKeys ContinuationToken Delimiter StartAfter EncodingType', 'PutObject': 'Bucket Key Body ContentType Metadata',
|
|
32
33
|
'GetObject': 'Bucket Key ChecksumMode Range IfMatch IfNoneMatch', 'HeadObject': 'Bucket Key ChecksumMode IfMatch IfNoneMatch', 'DeleteObject': 'Bucket Key',
|
|
33
34
|
},
|
|
@@ -53,7 +54,7 @@ AWS_OPERATIONS = {
|
|
|
53
54
|
'PutRetentionPolicy': 'logGroupName retentionInDays', 'DeleteRetentionPolicy': 'logGroupName',
|
|
54
55
|
},
|
|
55
56
|
}
|
|
56
|
-
JSON_FIELDS = set('AssumeRolePolicyDocument PolicyDocument AttributeDefinitions KeySchema ProvisionedThroughput GlobalSecondaryIndexes LocalSecondaryIndexes StreamSpecification Item Key ExpressionAttributeNames ExpressionAttributeValues ExclusiveStartKey RequestItems CreateBucketConfiguration Metadata Attributes MessageAttributes Tags tags ParameterFilters Entries logEvents'.split())
|
|
57
|
+
JSON_FIELDS = set('AssumeRolePolicyDocument PolicyDocument AttributeDefinitions KeySchema ProvisionedThroughput GlobalSecondaryIndexes LocalSecondaryIndexes StreamSpecification Item Key ExpressionAttributeNames ExpressionAttributeValues ExclusiveStartKey RequestItems CreateBucketConfiguration Metadata Attributes MessageAttributes Tags tags Tagging ParameterFilters Entries logEvents'.split())
|
|
57
58
|
LIST_FIELDS = set('ActionNames ResourceArns Names AttributeNames MessageAttributeNames MessageSystemAttributeNames TagKeys logStreamNames'.split())
|
|
58
59
|
BOOL_FIELDS = set('ConsistentRead ScanIndexForward WithDecryption Overwrite Enabled Recursive descending startFromHead'.split())
|
|
59
60
|
INT_FIELDS = set('Limit MaxKeys MaxResults MaxNumberOfMessages VisibilityTimeout WaitTimeSeconds DelaySeconds BatchSize limit startTime endTime retentionInDays'.split())
|