1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
use camel_cli::commands;
use clap::{Parser, Subcommand};
#[derive(Parser)]
#[command(
name = "camel",
version,
about = "Command-line interface for Apache Camel in Rust"
)]
struct Cli {
#[command(subcommand)]
command: Commands,
}
#[derive(Subcommand)]
enum Commands {
/// Start a Camel context from YAML route files.
///
/// Trust model: `camel run` executes route scripts, WASM modules, and beans
/// resolved from the current working directory. Only run from a trusted directory.
Run {
/// Glob pattern for route YAML files (overrides Camel.toml routes config)
#[arg(long, value_name = "GLOB")]
routes: Option<String>,
/// Path to Camel.toml config file
#[arg(long, value_name = "FILE", default_value = "Camel.toml")]
config: String,
/// Enable file-watcher hot-reload (overrides Camel.toml watch setting)
#[arg(long, overrides_with = "no_watch")]
watch: bool,
/// Disable file-watcher hot-reload (overrides Camel.toml watch setting)
#[arg(long, overrides_with = "watch")]
no_watch: bool,
/// Enable OpenTelemetry export (traces, metrics, logs)
#[arg(long)]
otel: bool,
/// OTLP endpoint URL (implies --otel)
#[arg(long, value_name = "URL")]
otel_endpoint: Option<String>,
/// OTel service name (implies --otel)
#[arg(long, value_name = "NAME")]
service_name: Option<String>,
/// Override health server port (starts standalone health server)
#[arg(long, value_name = "PORT")]
health_port: Option<u16>,
},
/// Inspect a runtime journal file.
Journal {
#[command(subcommand)]
action: JournalAction,
},
/// Scaffold a new Camel project
New(commands::new::NewArgs),
/// Manage WASM plugins (processors and beans)
Plugin {
#[command(subcommand)]
action: commands::plugin::PluginAction,
},
/// Generate OpenAPI document from REST route files
Openapi {
#[command(subcommand)]
action: commands::openapi::OpenapiAction,
},
/// Lint a route file against the production component catalog.
Lint(commands::lint::LintArgs),
/// Start Language Server Protocol server over stdio.
Lsp,
}
#[derive(Subcommand)]
enum JournalAction {
/// Inspect events in a redb journal file.
Inspect(commands::journal::JournalInspectArgs),
}
#[tokio::main]
async fn main() {
// Install rustls crypto provider before any TLS operations.
// The dep graph enables both ring and aws-lc-rs, so explicit selection
// is required to avoid a runtime panic.
let _ = rustls::crypto::ring::default_provider().install_default();
let cli = Cli::parse();
match cli.command {
Commands::Run {
routes,
config,
watch,
no_watch,
otel,
otel_endpoint,
service_name,
health_port,
} => {
// Resolve CLI watch override: --watch → Some(true), --no-watch → Some(false), neither → None
let cli_watch = if watch {
Some(true)
} else if no_watch {
Some(false)
} else {
None
};
if let Err(e) = commands::run::run(
routes,
config,
cli_watch,
otel,
otel_endpoint,
service_name,
health_port,
)
.await
{
commands::errors::report_cli_failure_and_exit("run", &e);
}
}
Commands::Journal { action } => match action {
JournalAction::Inspect(args) => {
commands::journal::run_inspect(args).await;
}
},
Commands::New(args) => {
commands::new::run_new(args);
}
Commands::Plugin { action } => {
commands::plugin::run_plugin(action);
}
Commands::Openapi { action } => {
commands::openapi::run(action);
}
Commands::Lint(args) => {
commands::lint::run(args).await;
}
Commands::Lsp => {
let code = commands::lsp::run().await;
std::process::exit(code);
}
}
}