posthog_cli/sourcemaps/
upload.rs

1use std::path::PathBuf;
2
3use anyhow::{Context, Ok, Result};
4use tracing::{info, warn};
5
6use crate::api::symbol_sets::{upload, SymbolSetUpload};
7use crate::invocation_context::context;
8
9use crate::sourcemaps::source_pair::read_pairs;
10use crate::utils::files::delete_files;
11
12#[derive(clap::Args, Clone)]
13pub struct UploadArgs {
14    /// The directory containing the bundled chunks
15    #[arg(short, long)]
16    pub directory: PathBuf,
17
18    /// If your bundler adds a public path prefix to sourcemap URLs,
19    /// we need to ignore it while searching for them
20    /// For use alongside e.g. esbuilds "publicPath" config setting.
21    #[arg(short, long)]
22    pub public_path_prefix: Option<String>,
23
24    /// One or more directory glob patterns to ignore
25    #[arg(short, long)]
26    pub ignore: Vec<String>,
27
28    /// Whether to delete the source map files after uploading them
29    #[arg(long, default_value = "false")]
30    pub delete_after: bool,
31
32    /// Whether to skip SSL verification when uploading chunks - only use when using self-signed certificates for
33    /// self-deployed instances
34    #[arg(long, default_value = "false")]
35    pub skip_ssl_verification: bool,
36
37    /// The maximum number of chunks to upload in a single batch
38    #[arg(long, default_value = "50")]
39    pub batch_size: usize,
40
41    /// DEPRECATED: Does nothing. Set project during `inject` instead
42    #[arg(long)]
43    pub project: Option<String>,
44
45    /// DEPRECATED: Does nothing. Set version during `inject` instead
46    #[arg(long)]
47    pub version: Option<String>,
48}
49
50pub fn upload_cmd(args: UploadArgs) -> Result<()> {
51    let UploadArgs {
52        directory,
53        public_path_prefix,
54        ignore,
55        delete_after,
56        skip_ssl_verification: _,
57        batch_size,
58        project: p,
59        version: v,
60    } = args;
61
62    if p.is_some() || v.is_some() {
63        warn!("`--project` and `--version` are deprecated and do nothing. Set project and version during `inject` instead.");
64    }
65
66    context().capture_command_invoked("sourcemap_upload");
67
68    let pairs = read_pairs(&directory, &ignore, &public_path_prefix)?;
69    let sourcemap_paths = pairs
70        .iter()
71        .map(|pair| pair.sourcemap.inner.path.clone())
72        .collect::<Vec<_>>();
73    info!("Found {} chunks to upload", pairs.len());
74
75    let uploads = pairs
76        .into_iter()
77        .map(TryInto::try_into)
78        .collect::<Result<Vec<SymbolSetUpload>>>()
79        .context("While preparing files for upload")?;
80
81    upload(&uploads, batch_size)?;
82
83    if delete_after {
84        delete_files(sourcemap_paths).context("While deleting sourcemaps")?;
85    }
86
87    Ok(())
88}