新增Tripo三类生成冒烟CLI

增加仅通过环境变量配置的 Tripo generation example

顺序提交 text、image、multiview 三类任务并执行单次状态查询

保持无命令行参数且不调用 SDK 轮询接口
This commit is contained in:
2026-09-18 18:42:58 +08:00
parent 5be4a51ac1
commit 25314d9a4a
3 changed files with 149 additions and 0 deletions
+1
View File
@@ -4161,6 +4161,7 @@ version = "0.1.0"
dependencies = [
"serde_json",
"shared-contracts",
"tokio",
"tripo3d-sdk",
"url",
]
@@ -9,3 +9,6 @@ shared-contracts = { workspace = true }
serde_json = { workspace = true }
tripo3d-sdk = { workspace = true }
url = { workspace = true }
[dev-dependencies]
tokio = { workspace = true, features = ["macros", "rt-multi-thread"] }
@@ -0,0 +1,145 @@
//! Submit one request through each supported 3D generation endpoint.
//!
//! Configuration is intentionally environment-only:
//!
//! ```text
//! TRIPO_API_KEY=... TRIPO_BASE_URL=https://openapi.tripo3d.com/v3 \
//! cargo run --locked -p platform-tripo --example tripo_generation_smoke \
//! --manifest-path server-rs/Cargo.toml
//! ```
//!
//! The example performs one-shot task queries after submission. It does not
//! expose or call the SDK's polling helpers.
use std::{env, time::Duration};
use platform_tripo::TripoProviderClient;
use shared_contracts::model3d::{
common::{Model3dModelVersion, Model3dTextureQuality},
image_to_model::Model3dImageToModelRequest,
multiview_to_model::{Model3dMultiviewInputs, Model3dMultiviewToModelRequest},
text_to_model::Model3dTextToModelRequest,
};
const SAMPLE_IMAGE_URL: &str =
"https://raw.githubusercontent.com/VAST-AI-Research/tripo-python-sdk/master/example.png";
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
let api_key = required_env("TRIPO_API_KEY")?;
let base_url = required_env("TRIPO_BASE_URL")?;
let client = TripoProviderClient::new(platform_tripo::TripoSettings::new(
api_key,
base_url,
Duration::from_secs(60),
2,
"genarrative-tripo-smoke/1".to_string(),
))?;
let text = client
.submit(&Model3dTextToModelRequest {
prompt: "a low-poly wooden treasure chest".to_string(),
model: Some(Model3dModelVersion::H31),
negative_prompt: None,
image_seed: None,
model_seed: None,
texture_seed: None,
texture: Some(true),
pbr: Some(true),
texture_quality: Some(Model3dTextureQuality::Standard),
texture_version: None,
delight: None,
geometry_quality: None,
face_limit: None,
auto_size: None,
quad: None,
smart_low_poly: None,
generate_parts: None,
compress: None,
export_uv: None,
export_orientation: None,
})
.await?;
println!("text_to_model task_id={}", text.task_id);
let image = client
.submit_image_to_model(&Model3dImageToModelRequest {
input: SAMPLE_IMAGE_URL.to_string(),
model: Some(Model3dModelVersion::H31),
enable_image_autofix: None,
model_seed: None,
texture_seed: None,
texture: Some(true),
pbr: Some(true),
texture_quality: Some(Model3dTextureQuality::Standard),
texture_version: None,
delight: None,
texture_alignment: None,
geometry_quality: None,
face_limit: None,
auto_size: None,
orientation: None,
quad: None,
smart_low_poly: None,
generate_parts: None,
compress: None,
export_uv: None,
export_orientation: None,
})
.await?;
println!("image_to_model task_id={}", image.task_id);
let multiview = client
.submit_multiview_to_model(&Model3dMultiviewToModelRequest {
inputs: Model3dMultiviewInputs::Views {
front: SAMPLE_IMAGE_URL.to_string(),
left: Some(SAMPLE_IMAGE_URL.to_string()),
back: None,
right: None,
},
model: Some(Model3dModelVersion::H31),
model_seed: None,
texture_seed: None,
texture: Some(true),
pbr: Some(true),
texture_quality: Some(Model3dTextureQuality::Standard),
texture_version: None,
delight: None,
geometry_quality: None,
texture_alignment: None,
face_limit: None,
auto_size: None,
orientation: None,
quad: None,
smart_low_poly: None,
generate_parts: None,
compress: None,
export_uv: None,
export_orientation: None,
})
.await?;
println!("multiview_to_model task_id={}", multiview.task_id);
for (name, handle) in [
("text_to_model", text),
("image_to_model", image),
("multiview_to_model", multiview),
] {
let snapshot = client.get_task(&handle).await?;
println!(
"{name} status={:?} progress={:?}",
snapshot.status, snapshot.progress
);
}
Ok(())
}
fn required_env(name: &str) -> Result<String, String> {
let value =
env::var(name).map_err(|_| format!("missing required environment variable {name}"))?;
if value.trim().is_empty() {
return Err(format!("environment variable {name} must not be blank"));
}
Ok(value)
}