use std::ffi::OsString; use crate::check_in::{CheckInConfig, CronConfig, HeartbeatConfig}; use crate::error::ErrorConfig; use crate::log::{LogConfig, LogOrigin}; use ::log::warn; use clap::Parser; /// A wrapper to track the execution of arbitrary processes with AppSignal. /// /// This wrapper allows an arbitrary process to be executed, sending its /// standard output and standard error as logs to AppSignal, as well as /// tracking its lifetime using heartbeat or cron check-ins. /// /// The wrapper is transparent: it passes through standard input to the /// executed process, it passes through the executed process's standard /// output and standard error to its own standard output and standard error, /// and it exits with the executed process's exit code. #[derive(Debug, Parser)] #[command(version)] pub struct Cli { /// The AppSignal *app-level* push API key. Required. /// /// This is the app-level push API key for the AppSignal application /// that logs, errors and check-ins will be sent to. This is *not* the /// organization-level API key. /// /// You can find these keys in the AppSignal dashboard: /// https://appsignal.com/redirect-to/organization?to=admin/api_keys /// /// Required unless a log source API key is provided using the /// `--log-source` option, and no check-ins or errors are being sent. #[arg( long, env = "APPSIGNAL_APP_PUSH_API_KEY", value_name = "APP_PUSH_API_KEY", required_unless_present = "log_source" )] api_key: Option, /// The name to use to send check-ins, logs and errors to AppSignal. /// Required. /// /// This value is used as the identifier for cron or heartbeat /// check-ins, if either the `--cron` or `--heartbeat` option is set, as /// the group for logs, and as the action for errors. /// /// This name should represent a *kind* of process, not be unique to /// the specific invocation of the process. See the `--digest` option for /// a unique identifier for this invocation. /// /// The `--cron`, `--heartbeat`, `--log` and `--error` options can be /// used to override this value for each use case. #[arg(index = 1, value_name = "NAME", required = true)] name: String, /// The command to execute. Required. /// /// #[arg(index = 2, allow_hyphen_values = true, last = true, required = true)] pub command: Vec, /// Send heartbeat check-ins. /// /// If this option is set, a heartbeat check-in will be sent two times /// per minute. /// /// Optionally, the identifier for the check-in can be provided. If /// omitted, the name given as the first argument will be used. #[arg( long, value_name = "IDENTIFIER", requires = "api_key", conflicts_with = "cron" )] heartbeat: Option