From 822cc1bb5bc06d6e53c2d432ef89855350475c9d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 11:20:53 +0900 Subject: [PATCH 01/10] feat(cli): pair --embed with --no-embed so the config file can be cancelled `embed` was OR-merged with the config, so `embed = true` in .risundlerc.toml was irreversible from the CLI (#24). Treat the pair as an Option resolved last-wins, preferring an explicit CLI flag over the config over the builtin default. Co-Authored-By: Claude Fable 5 --- src/cli.rs | 38 +++++++++++++++++++++++++++++++++++++- src/commands/bundle.rs | 29 ++++++++++++++++++++++++----- 2 files changed, 61 insertions(+), 6 deletions(-) diff --git a/src/cli.rs b/src/cli.rs index d00e250..c69eb1e 100644 --- a/src/cli.rs +++ b/src/cli.rs @@ -13,6 +13,10 @@ use std::path::PathBuf; version, after_help = "For library management, see `risundle library --help`." )] +#[expect( + clippy::struct_excessive_bools, + reason = "CLI フラグの列挙であり、bool の数は引数の数を映しているだけで状態機械の複雑さではない" +)] pub struct BundleArgs { /// Path to the compiler to use #[arg(short, long)] @@ -23,9 +27,13 @@ pub struct BundleArgs { pub keep: Vec, /// Embed the original source as a comment at the top - #[arg(short, long)] + #[arg(short, long, overrides_with = "no_embed")] pub embed: bool, + /// Do not embed the original source (cancels the config file) + #[arg(long)] + pub no_embed: bool, + /// Skip hash verification of library updates #[arg(short = 'n', long = "no-check")] pub no_check: bool, @@ -42,6 +50,20 @@ pub struct BundleArgs { pub options: Vec, } +impl BundleArgs { + /// `--embed` / `--no-embed` は後勝ちのペア。どちらも指定されなければ `None` を返し、 + /// 設定ファイル (なければ組み込み既定) に委ねる。 + pub fn embed_override(&self) -> Option { + if self.embed { + Some(true) + } else if self.no_embed { + Some(false) + } else { + None + } + } +} + // エントリポイントで argv の先頭を `risundle library` に差し替えて渡すため、 // help・usage 上のコマンド名が `risundle library` として表示される。 @@ -114,4 +136,18 @@ mod tests { fn hyphen_arguments_before_double_dash_are_rejected() { assert!(BundleArgs::try_parse_from(["risundle", "main.cpp", "-O2"]).is_err()); } + + #[test] + fn embed_pair_resolves_to_the_last_flag() { + let parse = |argv: &[&str]| { + let argv = [&["risundle", "main.cpp"], argv].concat(); + BundleArgs::try_parse_from(argv).unwrap().embed_override() + }; + assert_eq!(parse(&[]), None); + assert_eq!(parse(&["-e"]), Some(true)); + assert_eq!(parse(&["--no-embed"]), Some(false)); + // 後勝ち: 同時指定はコマンドライン上で後にある方が有効。 + assert_eq!(parse(&["--embed", "--no-embed"]), Some(false)); + assert_eq!(parse(&["--no-embed", "--embed"]), Some(true)); + } } diff --git a/src/commands/bundle.rs b/src/commands/bundle.rs index dff1088..079e48c 100644 --- a/src/commands/bundle.rs +++ b/src/commands/bundle.rs @@ -35,14 +35,15 @@ pub fn run(args: BundleArgs) -> Result<()> { // 設定へ吸収されない CLI 固有の値だけ、この場に残す。残りのフィールドは Settings::resolve へ // 所有権ごと渡し、設定とのマージで clone せずに済ませる。 + let embed = args.embed_override(); let BundleArgs { compiler, keep, - embed, no_check, no_tree_shaking, file, options, + .. } = args; let settings = Settings::resolve(&file, compiler, options, keep, embed)?; @@ -145,7 +146,7 @@ impl Settings { compiler: Option, options: Vec, keep: Vec, - embed: bool, + embed: Option, ) -> Result { let config = config::resolve(file)?; Ok(Self { @@ -160,7 +161,7 @@ impl Settings { } else { keep.into_iter().collect() }, - embed: embed || config.embed, + embed: embed.unwrap_or(config.embed), }) } } @@ -432,7 +433,7 @@ mod tests { Some(PathBuf::from("my-g++")), vec!["-O2".to_owned()], vec!["ac-library".to_owned()], - true, + Some(true), ) .unwrap(); assert_eq!(cli.compiler, PathBuf::from("my-g++")); @@ -441,7 +442,7 @@ mod tests { assert!(cli.embed); // CLI 省略時は設定 (.risundlerc.toml が無いここでは組み込みデフォルト) が生きる。 - let defaults = Settings::resolve(&file, None, vec![], vec![], false).unwrap(); + let defaults = Settings::resolve(&file, None, vec![], vec![], None).unwrap(); let expected = Config::default(); assert_eq!(defaults.compiler, expected.compiler); assert_eq!(defaults.options, expected.options); @@ -451,4 +452,22 @@ mod tests { ); assert!(!defaults.embed); } + + #[test] + fn no_embed_cancels_the_config_file() { + // 設定ファイルの embed = true を、CLI の明示 (--no-embed = Some(false)) が打ち消せる。 + let temp = TempDir::new().unwrap(); + std::fs::write( + temp.path().join(".risundlerc.toml"), + "[bundle]\nembed = true\n", + ) + .unwrap(); + let file = temp.path().join("main.cpp"); + std::fs::write(&file, "int main() {}").unwrap(); + + let from_config = Settings::resolve(&file, None, vec![], vec![], None).unwrap(); + assert!(from_config.embed); + let cancelled = Settings::resolve(&file, None, vec![], vec![], Some(false)).unwrap(); + assert!(!cancelled.embed); + } } From 16ea7952da1020cfcac6e155dcc1e30f27a440a5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 11:22:40 +0900 Subject: [PATCH 02/10] feat(cli)!: make --keep additive and pair it with --no-keep MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit A single -k used to replace the default keep = ["std"] wholesale, so forgetting -k std silently expanded the entire standard library (#24). The effective set is now (config keep ∪ --keep) − --no-keep; --no-keep wins over --keep regardless of order, erring toward the self-contained (expanded) output. --no-keep std restores the ability to empty the set from the CLI, which previously required the accidental -k '' trick. Co-Authored-By: Claude Fable 5 --- src/cli.rs | 8 ++++-- src/commands/bundle.rs | 59 ++++++++++++++++++++++++++++++++---------- 2 files changed, 51 insertions(+), 16 deletions(-) diff --git a/src/cli.rs b/src/cli.rs index c69eb1e..4d75f48 100644 --- a/src/cli.rs +++ b/src/cli.rs @@ -22,10 +22,14 @@ pub struct BundleArgs { #[arg(short, long)] pub compiler: Option, - /// Library ID to keep out of tree-shaking (can be repeated) - #[arg(short, long = "keep")] + /// Library ID to add to the keep set, leaving it out of tree-shaking (can be repeated) + #[arg(short, long = "keep", value_name = "ID")] pub keep: Vec, + /// Library ID to remove from the keep set (can be repeated; beats --keep) + #[arg(long = "no-keep", value_name = "ID")] + pub no_keep: Vec, + /// Embed the original source as a comment at the top #[arg(short, long, overrides_with = "no_embed")] pub embed: bool, diff --git a/src/commands/bundle.rs b/src/commands/bundle.rs index 079e48c..20a0b71 100644 --- a/src/commands/bundle.rs +++ b/src/commands/bundle.rs @@ -39,6 +39,7 @@ pub fn run(args: BundleArgs) -> Result<()> { let BundleArgs { compiler, keep, + no_keep, no_check, no_tree_shaking, file, @@ -46,7 +47,7 @@ pub fn run(args: BundleArgs) -> Result<()> { .. } = args; - let settings = Settings::resolve(&file, compiler, options, keep, embed)?; + let settings = Settings::resolve(&file, compiler, options, keep, no_keep, embed)?; let inventory = Inventory::load(&store, &settings.keep)?; warn_std_compiler(&settings.compiler, &inventory); if !no_check && !no_tree_shaking { @@ -129,8 +130,9 @@ fn warn_std_compiler(compiler: &Path, inventory: &Inventory) { } } -/// `.risundlerc.toml` の設定に CLI オプションを重ねた実効設定。CLI で明示された項目が設定 (なければ -/// 組み込みデフォルト) を上書きする。 +/// `.risundlerc.toml` の設定に CLI オプションを重ねた実効設定。重ね方は項目の型ごとに決まる: +/// スカラー (`compiler`) と bool (`embed`) は CLI 明示が設定を上書きし、集合 (`keep`) は +/// 設定へ加算した上で `--no-keep` を除く (#24)。 struct Settings { compiler: PathBuf, options: Vec, @@ -139,16 +141,21 @@ struct Settings { } impl Settings { - /// CLI で明示された値 (`compiler`・`options`・`keep`・`embed`) を消費して設定と重ね合わせる。 - /// `file` は設定ファイルの探索起点として借用するだけで、呼び出し側が引き続き所有する。 + /// CLI で明示された値を消費して設定と重ね合わせる。`file` は設定ファイルの探索起点として + /// 借用するだけで、呼び出し側が引き続き所有する。 fn resolve( file: &Path, compiler: Option, options: Vec, keep: Vec, + no_keep: Vec, embed: Option, ) -> Result { let config = config::resolve(file)?; + // 実効 keep = (config の keep ∪ --keep) − --no-keep。同じ ID が両方にあれば順序に依らず + // --no-keep が勝つ (誤 keep はジャッジで解決できない #include を残す硬い失敗、誤展開は + // ファイルが膨らむだけの柔らかい失敗なので、衝突は展開側へ倒す)。 + let no_keep: BTreeSet = no_keep.into_iter().collect(); Ok(Self { compiler: compiler.unwrap_or(config.compiler), options: if options.is_empty() { @@ -156,11 +163,12 @@ impl Settings { } else { options }, - keep: if keep.is_empty() { - config.keep.into_iter().collect() - } else { - keep.into_iter().collect() - }, + keep: config + .keep + .into_iter() + .chain(keep) + .filter(|id| !no_keep.contains(id)) + .collect(), embed: embed.unwrap_or(config.embed), }) } @@ -427,22 +435,24 @@ mod tests { let file = temp.path().join("main.cpp"); std::fs::write(&file, "int main() {}").unwrap(); - // CLI で明示された値が勝つ。 + // CLI で明示された値が勝つ (keep は上書きではなく設定への加算)。 let cli = Settings::resolve( &file, Some(PathBuf::from("my-g++")), vec!["-O2".to_owned()], vec!["ac-library".to_owned()], + vec![], Some(true), ) .unwrap(); assert_eq!(cli.compiler, PathBuf::from("my-g++")); assert_eq!(cli.options, vec!["-O2".to_owned()]); assert!(cli.keep.contains("ac-library")); + assert!(cli.keep.contains("std"), "-k は既定の std を消さない"); assert!(cli.embed); // CLI 省略時は設定 (.risundlerc.toml が無いここでは組み込みデフォルト) が生きる。 - let defaults = Settings::resolve(&file, None, vec![], vec![], None).unwrap(); + let defaults = Settings::resolve(&file, None, vec![], vec![], vec![], None).unwrap(); let expected = Config::default(); assert_eq!(defaults.compiler, expected.compiler); assert_eq!(defaults.options, expected.options); @@ -465,9 +475,30 @@ mod tests { let file = temp.path().join("main.cpp"); std::fs::write(&file, "int main() {}").unwrap(); - let from_config = Settings::resolve(&file, None, vec![], vec![], None).unwrap(); + let from_config = Settings::resolve(&file, None, vec![], vec![], vec![], None).unwrap(); assert!(from_config.embed); - let cancelled = Settings::resolve(&file, None, vec![], vec![], Some(false)).unwrap(); + let cancelled = + Settings::resolve(&file, None, vec![], vec![], vec![], Some(false)).unwrap(); assert!(!cancelled.embed); } + + #[test] + fn no_keep_subtracts_from_the_keep_set() { + let temp = TempDir::new().unwrap(); + let file = temp.path().join("main.cpp"); + std::fs::write(&file, "int main() {}").unwrap(); + let resolve = |keep: &[&str], no_keep: &[&str]| { + let owned = |ids: &[&str]| ids.iter().map(|&id| (*id).to_owned()).collect(); + Settings::resolve(&file, None, vec![], owned(keep), owned(no_keep), None) + .unwrap() + .keep + }; + + // --no-keep std で、CLI から keep を空にできる (可逆性の回復)。 + assert!(resolve(&[], &["std"]).is_empty()); + // 同じ ID が両方にあれば、順序に依らず --no-keep が勝つ。 + assert!(!resolve(&["std"], &["std"]).contains("std")); + // 他の ID には影響しない。 + assert!(resolve(&["ac-library"], &["std"]).contains("ac-library")); + } } From 5526b01812f0e8a89e5fee1a5688a45927be5874 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 11:25:03 +0900 Subject: [PATCH 03/10] feat(bundle): warn when std is missing from the effective keep set Forgetting "std" in the config's keep (or --no-keep'ing it by accident elsewhere) silently emits a huge bundle that only surfaces at submission size limits. Warn on absence, but stay quiet when the CLI passed --no-keep std explicitly: absence is guarded, explicit intent is respected (#24). Co-Authored-By: Claude Fable 5 --- src/commands/bundle.rs | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/src/commands/bundle.rs b/src/commands/bundle.rs index 20a0b71..8845841 100644 --- a/src/commands/bundle.rs +++ b/src/commands/bundle.rs @@ -47,7 +47,9 @@ pub fn run(args: BundleArgs) -> Result<()> { .. } = args; + let std_removed_explicitly = no_keep.iter().any(|id| id == STD_ID); let settings = Settings::resolve(&file, compiler, options, keep, no_keep, embed)?; + warn_std_not_kept(&settings.keep, std_removed_explicitly); let inventory = Inventory::load(&store, &settings.keep)?; warn_std_compiler(&settings.compiler, &inventory); if !no_check && !no_tree_shaking { @@ -106,6 +108,18 @@ fn display_origin(origin: &str, inventory: &Inventory, target_dir: Option<&Path> ) } +/// 実効 keep から std が外れていれば警告する。std の展開はほぼ常に事故で、巨大な出力が黙って +/// 生成され提出時のサイズ制限まで顕在化しないため、書き忘れ (設定ファイルの `keep` に std を +/// 挙げ損ねた等) は防護する。一方 CLI の `--no-keep std` は明示された意思なので警告しない。 +fn warn_std_not_kept(keep: &BTreeSet, removed_explicitly: bool) { + if keep.contains(STD_ID) || removed_explicitly { + return; + } + eprintln!( + "warning: the standard library (`{STD_ID}`) is not in the keep set and will be fully expanded; add \"{STD_ID}\" to `keep` in .risundlerc.toml, or pass `--no-keep {STD_ID}` to make the expansion explicit" + ); +} + /// std がバンドル対象のコンパイラ向けに登録されているかを確認し、外れていれば警告する。 /// /// std 未登録、または現在のコンパイラが std の認識集合に無い場合に `add-std` を促す。コンパイラは @@ -482,6 +496,18 @@ mod tests { assert!(!cancelled.embed); } + #[test] + fn warn_std_not_kept_covers_absence_and_explicit_removal() { + // 警告は標準エラーへの出力のみで戻り値を持たないため、各経路が落ちずに通ることを確かめる。 + let kept: BTreeSet = ["std".to_owned()].into(); + // std が keep にある → 警告なし。 + warn_std_not_kept(&kept, false); + // std が無い (書き忘れの可能性) → 警告。 + warn_std_not_kept(&BTreeSet::new(), false); + // --no-keep std の明示 → 意図を尊重して警告なし。 + warn_std_not_kept(&BTreeSet::new(), true); + } + #[test] fn no_keep_subtracts_from_the_keep_set() { let temp = TempDir::new().unwrap(); From ca6720e3a76bff2c3a7d0254c5496b9f27fd7e3a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 11:28:05 +0900 Subject: [PATCH 04/10] feat(bundle)!: append CLI compiler options to the config instead of replacing Passing any option after -- used to discard the whole configured list, so `-- -O0` also dropped -std=gnu++17 (#24). Append the CLI options and delegate override semantics to the compiler's own last-wins rules (-std=... beats an earlier one, -U kills -D); risundle does not interpret flags itself. Co-Authored-By: Claude Fable 5 --- src/commands/bundle.rs | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/src/commands/bundle.rs b/src/commands/bundle.rs index 8845841..fdb7da4 100644 --- a/src/commands/bundle.rs +++ b/src/commands/bundle.rs @@ -146,7 +146,7 @@ fn warn_std_compiler(compiler: &Path, inventory: &Inventory) { /// `.risundlerc.toml` の設定に CLI オプションを重ねた実効設定。重ね方は項目の型ごとに決まる: /// スカラー (`compiler`) と bool (`embed`) は CLI 明示が設定を上書きし、集合 (`keep`) は -/// 設定へ加算した上で `--no-keep` を除く (#24)。 +/// 設定へ加算した上で `--no-keep` を除き、順序付きリスト (`options`) は設定へ追記する (#24)。 struct Settings { compiler: PathBuf, options: Vec, @@ -172,11 +172,9 @@ impl Settings { let no_keep: BTreeSet = no_keep.into_iter().collect(); Ok(Self { compiler: compiler.unwrap_or(config.compiler), - options: if options.is_empty() { - config.options - } else { - options - }, + // 実効 options = config の options + CLI の options。上書きの意味論はコンパイラの + // 後勝ち (-std 等) や -U に委ね、risundle 側では重複や矛盾を解釈しない。 + options: config.options.into_iter().chain(options).collect(), keep: config .keep .into_iter() @@ -449,18 +447,21 @@ mod tests { let file = temp.path().join("main.cpp"); std::fs::write(&file, "int main() {}").unwrap(); - // CLI で明示された値が勝つ (keep は上書きではなく設定への加算)。 + // CLI で明示された値が勝つ (keep は設定への加算、options は設定への追記)。 let cli = Settings::resolve( &file, Some(PathBuf::from("my-g++")), - vec!["-O2".to_owned()], + vec!["-O0".to_owned()], vec!["ac-library".to_owned()], vec![], Some(true), ) .unwrap(); assert_eq!(cli.compiler, PathBuf::from("my-g++")); - assert_eq!(cli.options, vec!["-O2".to_owned()]); + let mut expected_options = Config::default().options; + expected_options.push("-O0".to_owned()); + // 追記なので -std=gnu++17 等の既定は生き残り、-O0 は既定の -O2 に後勝ちする。 + assert_eq!(cli.options, expected_options); assert!(cli.keep.contains("ac-library")); assert!(cli.keep.contains("std"), "-k は既定の std を消さない"); assert!(cli.embed); From 4dac959705719e3d36f0dc7003475f83a962a87f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 11:30:05 +0900 Subject: [PATCH 05/10] feat(cli): add --no-config to ignore .risundlerc.toml entirely Appending cannot cancel every kind of configured flag (a config -I, for example), so provide one cross-cutting escape hatch defined as: behave exactly as if no config file were found. This keeps the effective settings reachable from builtin defaults via the CLI alone, for any future config key (#24). Co-Authored-By: Claude Fable 5 --- src/cli.rs | 4 +++ src/commands/bundle.rs | 57 ++++++++++++++++++++++++++++++++++++------ 2 files changed, 53 insertions(+), 8 deletions(-) diff --git a/src/cli.rs b/src/cli.rs index 4d75f48..f14419a 100644 --- a/src/cli.rs +++ b/src/cli.rs @@ -46,6 +46,10 @@ pub struct BundleArgs { #[arg(long = "no-tree-shaking")] pub no_tree_shaking: bool, + /// Ignore any .risundlerc.toml, behaving as if none exists + #[arg(long = "no-config")] + pub no_config: bool, + /// C++ source file to bundle pub file: PathBuf, diff --git a/src/commands/bundle.rs b/src/commands/bundle.rs index fdb7da4..80cda46 100644 --- a/src/commands/bundle.rs +++ b/src/commands/bundle.rs @@ -42,13 +42,14 @@ pub fn run(args: BundleArgs) -> Result<()> { no_keep, no_check, no_tree_shaking, + no_config, file, options, .. } = args; let std_removed_explicitly = no_keep.iter().any(|id| id == STD_ID); - let settings = Settings::resolve(&file, compiler, options, keep, no_keep, embed)?; + let settings = Settings::resolve(&file, no_config, compiler, options, keep, no_keep, embed)?; warn_std_not_kept(&settings.keep, std_removed_explicitly); let inventory = Inventory::load(&store, &settings.keep)?; warn_std_compiler(&settings.compiler, &inventory); @@ -159,13 +160,20 @@ impl Settings { /// 借用するだけで、呼び出し側が引き続き所有する。 fn resolve( file: &Path, + no_config: bool, compiler: Option, options: Vec, keep: Vec, no_keep: Vec, embed: Option, ) -> Result { - let config = config::resolve(file)?; + // --no-config は「設定ファイルが 1 つも見つからない環境」と完全に同一の挙動と定義する。 + // これにより、CLI だけで組み込み既定から実効設定を組み立て直せることが常に保証される。 + let config = if no_config { + config::Config::default() + } else { + config::resolve(file)? + }; // 実効 keep = (config の keep ∪ --keep) − --no-keep。同じ ID が両方にあれば順序に依らず // --no-keep が勝つ (誤 keep はジャッジで解決できない #include を残す硬い失敗、誤展開は // ファイルが膨らむだけの柔らかい失敗なので、衝突は展開側へ倒す)。 @@ -450,6 +458,7 @@ mod tests { // CLI で明示された値が勝つ (keep は設定への加算、options は設定への追記)。 let cli = Settings::resolve( &file, + false, Some(PathBuf::from("my-g++")), vec!["-O0".to_owned()], vec!["ac-library".to_owned()], @@ -467,7 +476,7 @@ mod tests { assert!(cli.embed); // CLI 省略時は設定 (.risundlerc.toml が無いここでは組み込みデフォルト) が生きる。 - let defaults = Settings::resolve(&file, None, vec![], vec![], vec![], None).unwrap(); + let defaults = Settings::resolve(&file, false, None, vec![], vec![], vec![], None).unwrap(); let expected = Config::default(); assert_eq!(defaults.compiler, expected.compiler); assert_eq!(defaults.options, expected.options); @@ -490,13 +499,37 @@ mod tests { let file = temp.path().join("main.cpp"); std::fs::write(&file, "int main() {}").unwrap(); - let from_config = Settings::resolve(&file, None, vec![], vec![], vec![], None).unwrap(); + let from_config = + Settings::resolve(&file, false, None, vec![], vec![], vec![], None).unwrap(); assert!(from_config.embed); let cancelled = - Settings::resolve(&file, None, vec![], vec![], vec![], Some(false)).unwrap(); + Settings::resolve(&file, false, None, vec![], vec![], vec![], Some(false)).unwrap(); assert!(!cancelled.embed); } + #[test] + fn no_config_behaves_as_if_no_config_file_exists() { + // --no-config は「設定ファイルが 1 つも見つからない環境」と同一挙動、が仕様の定義。 + let temp = TempDir::new().unwrap(); + std::fs::write( + temp.path().join(".risundlerc.toml"), + "[compiler]\npath = \"clang++\"\noptions = [\"-I/secret\"]\n", + ) + .unwrap(); + let file = temp.path().join("main.cpp"); + std::fs::write(&file, "int main() {}").unwrap(); + + let isolated = Settings::resolve(&file, true, None, vec![], vec![], vec![], None).unwrap(); + let expected = Config::default(); + assert_eq!(isolated.compiler, expected.compiler); + assert_eq!(isolated.options, expected.options); + assert_eq!( + isolated.keep, + expected.keep.into_iter().collect::>() + ); + assert!(!isolated.embed); + } + #[test] fn warn_std_not_kept_covers_absence_and_explicit_removal() { // 警告は標準エラーへの出力のみで戻り値を持たないため、各経路が落ちずに通ることを確かめる。 @@ -516,9 +549,17 @@ mod tests { std::fs::write(&file, "int main() {}").unwrap(); let resolve = |keep: &[&str], no_keep: &[&str]| { let owned = |ids: &[&str]| ids.iter().map(|&id| (*id).to_owned()).collect(); - Settings::resolve(&file, None, vec![], owned(keep), owned(no_keep), None) - .unwrap() - .keep + Settings::resolve( + &file, + false, + None, + vec![], + owned(keep), + owned(no_keep), + None, + ) + .unwrap() + .keep }; // --no-keep std で、CLI から keep を空にできる (可逆性の回復)。 From 8fae0fa91cefd6c193554c7e40073f92671151e1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 11:36:12 +0900 Subject: [PATCH 06/10] style(cli): drop the "keep set" jargon from user-facing text Co-Authored-By: Claude Fable 5 --- src/cli.rs | 4 ++-- src/commands/bundle.rs | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/cli.rs b/src/cli.rs index f14419a..6dd08f8 100644 --- a/src/cli.rs +++ b/src/cli.rs @@ -22,11 +22,11 @@ pub struct BundleArgs { #[arg(short, long)] pub compiler: Option, - /// Library ID to add to the keep set, leaving it out of tree-shaking (can be repeated) + /// Also keep a library unexpanded, out of tree-shaking (can be repeated) #[arg(short, long = "keep", value_name = "ID")] pub keep: Vec, - /// Library ID to remove from the keep set (can be repeated; beats --keep) + /// Stop keeping a library (can be repeated; beats --keep) #[arg(long = "no-keep", value_name = "ID")] pub no_keep: Vec, diff --git a/src/commands/bundle.rs b/src/commands/bundle.rs index 80cda46..0bb1fbc 100644 --- a/src/commands/bundle.rs +++ b/src/commands/bundle.rs @@ -117,7 +117,7 @@ fn warn_std_not_kept(keep: &BTreeSet, removed_explicitly: bool) { return; } eprintln!( - "warning: the standard library (`{STD_ID}`) is not in the keep set and will be fully expanded; add \"{STD_ID}\" to `keep` in .risundlerc.toml, or pass `--no-keep {STD_ID}` to make the expansion explicit" + "warning: the standard library (`{STD_ID}`) is not kept and will be fully expanded; add \"{STD_ID}\" to `keep` in .risundlerc.toml, or pass `--no-keep {STD_ID}` to make the expansion explicit" ); } From 046ce65d9cbebf3cb8a6a903d1639d64cbe05e57 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 11:36:12 +0900 Subject: [PATCH 07/10] docs: describe the per-type config layering and the new --no-* options Document the #24 semantics across README, cheatsheet, and spec (en/ja): --keep is now additive with --no-keep as its inverse, CLI compiler options append to the configured ones, --no-embed cancels a configured embed, and --no-config behaves exactly as if no config file were found. The spec also records the std-missing warning and its suppression, and the cheatsheet FAQ about -k dropping std is reworked into the config keep footgun it has become. Co-Authored-By: Claude Fable 5 --- README.ja.md | 13 ++++++++----- README.md | 13 ++++++++----- docs/cheatsheet.ja.md | 22 ++++++++++++++++------ docs/cheatsheet.md | 22 ++++++++++++++++------ docs/spec.ja.md | 13 ++++++++++++- docs/spec.md | 13 ++++++++++++- 6 files changed, 72 insertions(+), 24 deletions(-) diff --git a/README.ja.md b/README.ja.md index 2f87f9a..b144de0 100644 --- a/README.ja.md +++ b/README.ja.md @@ -59,17 +59,20 @@ risundle [OPTIONS] [-- ...] | オプション | 説明 | | --- | --- | | `-c`, `--compiler ` | 使用するコンパイラ (既定: `g++`) | -| `-k`, `--keep ` | tree-shaking の対象外にするライブラリ ID (繰り返し可。既定: `std`) | +| `-k`, `--keep ` | 展開せず `#include` のまま残すライブラリを追加指定する (繰り返し可。既定: `std`) | +| `--no-keep ` | 維持指定 (keep) からライブラリを外す (繰り返し可。`--keep` より優先) | | `--no-tree-shaking` | tree-shaking を無効化し、keep 指定以外をすべて展開する (フォールバック用) | | `-e`, `--embed` | 元のソースを先頭にコメントとして埋め込む | +| `--no-embed` | 元のソースを埋め込まない (設定ファイルの指定を打ち消す) | | `-n`, `--no-check` | ライブラリ更新のハッシュ検証をスキップする | -| `-- ...` | `--` 以降をコンパイラへそのまま渡す | +| `--no-config` | `.risundlerc.toml` を無視する (設定ファイルが無い時と同じ挙動) | +| `-- ...` | `--` 以降をコンパイラへそのまま渡す (設定の options への追記) | `--keep` はライブラリを展開せず `#include` のまま残しますが、`--no-tree-shaking` は keep 指定を除く全ライブラリを展開した上で tree-shaking を行いません。両者は別物で、併用もできます。なお `--no-tree-shaking` は識別子情報を使わないため、ライブラリ更新のハッシュ検証も行いません。 ```bash -# clang++ を使い、AC Library も展開せず #include のまま残す -risundle -c clang++ -k std -k ac-library main.cpp > submission.cpp +# clang++ を使い、AC Library も展開せず #include のまま残す (std は既定で維持される) +risundle -c clang++ -k ac-library main.cpp > submission.cpp # コンパイラに追加オプションを渡す risundle main.cpp -- -std=gnu++20 -O2 @@ -94,7 +97,7 @@ risundle library ## 設定ファイル -解答ファイルのあるディレクトリから親方向に探索し、最も近い `.risundlerc.toml` を 1 つ採用します (複数ファイルのマージはしません)。CLI オプションが設定ファイルより優先されます。 +解答ファイルのあるディレクトリから親方向に探索し、最も近い `.risundlerc.toml` を 1 つ採用します (複数ファイルのマージはしません)。CLI で明示したオプションが設定ファイルより優先されます: スカラーと bool は上書き、維持指定 (keep) は `--keep` で追加・`--no-keep` で除外、`--` のコンパイラオプションは設定への追記です。`--no-config` を指定すると設定ファイルを無視できます。 ```toml [compiler] diff --git a/README.md b/README.md index 28d0488..73fca7d 100644 --- a/README.md +++ b/README.md @@ -59,17 +59,20 @@ Bundles `` and writes the result to standard output. | Option | Description | | --- | --- | | `-c`, `--compiler ` | Compiler to use (default: `g++`) | -| `-k`, `--keep ` | Library ID to exclude from tree-shaking (repeatable; default: `std`) | +| `-k`, `--keep ` | Also keep a library unexpanded, out of tree-shaking (repeatable; default: `std`) | +| `--no-keep ` | Stop keeping a library (repeatable; beats `--keep`) | | `--no-tree-shaking` | Disable tree-shaking and expand everything except kept libraries (useful as a fallback) | | `-e`, `--embed` | Embed the original source as a comment at the top | +| `--no-embed` | Do not embed the original source (cancels the config file) | | `-n`, `--no-check` | Skip the hash verification of library updates | -| `-- ...` | Pass everything after `--` straight to the compiler | +| `--no-config` | Ignore any `.risundlerc.toml`, behaving as if none exists | +| `-- ...` | Pass everything after `--` straight to the compiler, appended to the configured options | `--keep` leaves a library unexpanded as an `#include`, whereas `--no-tree-shaking` expands every library except the kept ones but performs no tree-shaking. The two are different and can be combined. Note that `--no-tree-shaking` also skips the hash verification of library updates, since it uses no identifier information. ```bash -# Use clang++ and leave AC Library unexpanded, keeping it as #include -risundle -c clang++ -k std -k ac-library main.cpp > submission.cpp +# Use clang++ and leave AC Library unexpanded too (std stays kept by default) +risundle -c clang++ -k ac-library main.cpp > submission.cpp # Pass extra options to the compiler risundle main.cpp -- -std=gnu++20 -O2 @@ -94,7 +97,7 @@ risundle library ## Configuration file -risundle searches from the directory of the solution file toward its parents and adopts the single nearest `.risundlerc.toml` (it does not merge multiple files). CLI options take precedence over the configuration file. +risundle searches from the directory of the solution file toward its parents and adopts the single nearest `.risundlerc.toml` (it does not merge multiple files). Explicit CLI options take precedence over the configuration file: scalars and booleans are overridden, `--keep` and `--no-keep` add and remove kept libraries, and options after `--` are appended to the configured ones. `--no-config` ignores the file entirely. ```toml [compiler] diff --git a/docs/cheatsheet.ja.md b/docs/cheatsheet.ja.md index 42f9717..6ce07e7 100644 --- a/docs/cheatsheet.ja.md +++ b/docs/cheatsheet.ja.md @@ -76,10 +76,18 @@ oj t && risundle main.cpp > submission.cpp && oj s submission.cpp 例: AC Library がジャッジ側にあるので埋め込みたくない。 ```bash -risundle -k std -k ac-library main.cpp > submission.cpp +risundle -k ac-library main.cpp > submission.cpp ``` -`-k` に渡すのは登録時の ID です。`-k` を 1 つでも指定すると既定の `keep = ["std"]` は上書きされるため、`-k std` も一緒に指定してください (忘れると標準ライブラリまで展開されます)。このとき解答側の include は `#include "..."` ではなく `#include ` のような山括弧で書いてください (`"..."` だと keep が効かないことがあります)。 +`-k` に渡すのは登録時の ID です。`-k` は「追加」なので、既定で維持される std はそのまま残ります。このとき解答側の include は `#include "..."` ではなく `#include ` のような山括弧で書いてください (`"..."` だと keep が効かないことがあります)。 + +### keep しているライブラリを今回だけ展開したい + +```bash +risundle --no-keep ac-library main.cpp > submission.cpp +``` + +設定ファイルや `-k` で維持指定していても、`--no-keep` が優先されて展開されます。 ### ジャッジと同じコンパイラ・同じフラグで処理したい @@ -120,7 +128,7 @@ bundle() { risundle -e main.cpp > submission.cpp ``` -コードを公開するジャッジで、tree-shaking 前の読みやすいコードを見せたいときに。 +コードを公開するジャッジで、tree-shaking 前の読みやすいコードを見せたいときに。設定ファイルで `embed = true` を常用している場合は、`--no-embed` で今回だけ打ち消せます。 ## ライブラリを触ったらやること @@ -170,7 +178,9 @@ options = ["-std=gnu++20", "-O2", "-DONLINE_JUDGE", "-DATCODER"] keep = ["std", "ac-library"] ``` -CLI オプションを併用した場合はそちらが優先されます。 +CLI オプションを併用した場合はそちらが優先されます (`-k` は設定への追加、`--` のコンパイラオプションは設定への追記になります)。設定ファイルを無視したいときは `--no-config` を付けてください。 + +なお `keep` を自分で書くときは `"std"` も一緒に並べてください。書き忘れると標準ライブラリまで展開されます (その場合は risundle が警告を出します)。 ## うまくいかないとき @@ -197,9 +207,9 @@ risundle --no-tree-shaking main.cpp > submission.cpp 解答側の include を `#include "atcoder/dsu"` のような `"..."` 形式で書いていませんか。`#include ` の山括弧形式に変えてください。 -### `-k` を付けたら標準ライブラリまで展開されるようになった +### 標準ライブラリまで展開されてしまう -`-k` の指定は既定の `keep = ["std"]` を上書きします。`-k std` を並べて指定してください。 +維持指定 (keep) に std が入っていません。典型は設定ファイルの `keep` に `"std"` を書き忘れているケースです (`keep` を自分で書くと既定値は使われません)。`.risundlerc.toml` の `keep` に `"std"` を足してください。この状態では risundle も警告を出します。 ### エラーメッセージの行番号が元のファイルと合わない diff --git a/docs/cheatsheet.md b/docs/cheatsheet.md index 8c9d0f0..8d99c49 100644 --- a/docs/cheatsheet.md +++ b/docs/cheatsheet.md @@ -77,10 +77,18 @@ oj t && risundle main.cpp > submission.cpp && oj s submission.cpp Example: the judge provides AC Library, so you don't want it embedded. ```bash -risundle -k std -k ac-library main.cpp > submission.cpp +risundle -k ac-library main.cpp > submission.cpp ``` -`-k` takes the ID you used at registration. Specifying `-k` even once overrides the default `keep = ["std"]`, so pass `-k std` alongside it (forget it and the standard library gets expanded too). Also write the includes in your solution with angle brackets like `#include `, not `#include "..."` (with `"..."` the keep may not take effect). +`-k` takes the ID you used at registration. `-k` is additive, so std stays kept by default. Also write the includes in your solution with angle brackets like `#include `, not `#include "..."` (with `"..."` the keep may not take effect). + +### Expand a kept library just this once + +```bash +risundle --no-keep ac-library main.cpp > submission.cpp +``` + +`--no-keep` beats both the config file and `-k`, so the library gets expanded. ### Process with the same compiler and flags as the judge @@ -121,7 +129,7 @@ From then on, `bundle main.cpp` is all you need. When the fallback fires, check risundle -e main.cpp > submission.cpp ``` -For judges that publish submissions, when you want readers to see the readable pre-tree-shaking code. +For judges that publish submissions, when you want readers to see the readable pre-tree-shaking code. If your config file sets `embed = true`, cancel it for one run with `--no-embed`. ## After touching a library @@ -171,7 +179,9 @@ options = ["-std=gnu++20", "-O2", "-DONLINE_JUDGE", "-DATCODER"] keep = ["std", "ac-library"] ``` -CLI options take precedence when both are given. +CLI options take precedence when both are given (`-k` adds to the configured keeps, and options after `--` are appended to the configured ones). Add `--no-config` to ignore the file entirely. + +When you write `keep` yourself, list `"std"` alongside the rest. Forget it and the standard library gets expanded too (risundle prints a warning when that happens). ## When things go wrong @@ -198,9 +208,9 @@ If this fixes it, tree-shaking dropped a needed definition (a report in the [iss Are you writing the include as `#include "atcoder/dsu"`? Switch to the angle-bracket form `#include `. -### Adding `-k` made the standard library get expanded too +### The standard library got expanded too -Specifying `-k` overrides the default `keep = ["std"]`. Pass `-k std` alongside it. +std is missing from the effective keeps. The typical cause is a config file whose `keep` forgets to list `"std"` (writing `keep` yourself replaces the default). Add `"std"` to `keep` in `.risundlerc.toml`. risundle also prints a warning in this situation. ### Error line numbers don't match the original file diff --git a/docs/spec.ja.md b/docs/spec.ja.md index bf7e9e7..c6334f3 100644 --- a/docs/spec.ja.md +++ b/docs/spec.ja.md @@ -36,7 +36,18 @@ README より踏み込んだ、各コマンドの挙動・エラー条件・出 ### 設定の解決 -`` のあるディレクトリから親方向に `.risundlerc.toml` を探し、最も近い 1 つだけを既定値に使う (複数あってもマージしない)。CLI オプションは設定ファイルより優先される。どちらにも無い項目は組み込みの既定値 (`compiler = g++`、`options = ["-std=gnu++17", "-O2", "-DONLINE_JUDGE", "-DATCODER"]`、`keep = ["std"]`、`embed = false`) で補う。 +`` のあるディレクトリから親方向に `.risundlerc.toml` を探し、最も近い 1 つだけを既定値に使う (複数あってもマージしない)。設定ファイルで省略された項目は組み込みの既定値 (`compiler = g++`、`options = ["-std=gnu++17", "-O2", "-DONLINE_JUDGE", "-DATCODER"]`、`keep = ["std"]`、`embed = false`) で補う。設定ファイル内の各項目は宣言的な全量指定であり、既定値へのマージはしない (`keep = ["ac-library"]` と書けば既定の `std` は含まれない)。 + +CLI オプションの重ね方は、項目の型ごとに決まる。 + +- `compiler` (スカラー) — CLI の `--compiler` が設定を上書きする。 +- `embed` (bool) — `--embed` / `--no-embed` は後勝ちのペアで、CLI で明示された場合のみ設定を上書きする。 +- `keep` (集合) — 実効 keep = (設定の keep ∪ `--keep`) − `--no-keep`。同じ ID が両方に指定された場合は、順序に依らず `--no-keep` が勝つ。 +- `options` (順序付きリスト) — 実効 options = 設定の options + `--` 以降の CLI オプション。同種フラグの上書きはコンパイラの後勝ち (`-std` 等) や `-U` に委ね、risundle 側では解釈しない。 + +`--no-config` を指定すると `.risundlerc.toml` を一切読まず、設定ファイルが 1 つも見つからない環境と完全に同一の挙動になる。これにより、CLI だけで組み込み既定から実効設定を組み立て直せることが常に保証される。 + +実効 keep に `std` が含まれない場合は警告を出す (std の全展開はほぼ常に事故で、巨大な出力が提出時まで顕在化しないため)。ただし CLI で `--no-keep std` と明示された場合は、意図とみなして警告しない。 ### ライブラリの変更検知 diff --git a/docs/spec.md b/docs/spec.md index 0f3d86a..12ea8ba 100644 --- a/docs/spec.md +++ b/docs/spec.md @@ -36,7 +36,18 @@ See the README for the full list of options. The following are the behavioral de ### Resolving configuration -Searches from the directory of `` toward its parents for `.risundlerc.toml` and uses only the single nearest one as defaults (no merging even if multiple exist). CLI options take precedence over the configuration file. Items present in neither are filled in with the built-in defaults (`compiler = g++`, `options = ["-std=gnu++17", "-O2", "-DONLINE_JUDGE", "-DATCODER"]`, `keep = ["std"]`, `embed = false`). +Searches from the directory of `` toward its parents for `.risundlerc.toml` and uses only the single nearest one as defaults (no merging even if multiple exist). Items omitted in the configuration file are filled in with the built-in defaults (`compiler = g++`, `options = ["-std=gnu++17", "-O2", "-DONLINE_JUDGE", "-DATCODER"]`, `keep = ["std"]`, `embed = false`). Each item in the configuration file is a declarative, complete value and is not merged with the defaults (writing `keep = ["ac-library"]` does not include the default `std`). + +How CLI options are layered on top depends on the type of the item. + +- `compiler` (scalar) — the CLI `--compiler` overrides the configuration. +- `embed` (bool) — `--embed` / `--no-embed` are a last-wins pair, overriding the configuration only when given explicitly. +- `keep` (set) — effective keep = (configured keep ∪ `--keep`) − `--no-keep`. When the same ID appears in both, `--no-keep` wins regardless of order. +- `options` (ordered list) — effective options = configured options + the CLI options after `--`. Overriding between flags of the same kind is delegated to the compiler's own last-wins rules (`-std` etc.) and `-U`; risundle does not interpret them. + +With `--no-config`, no `.risundlerc.toml` is read at all and the behavior is exactly identical to an environment where no configuration file is found. This guarantees that the effective settings can always be rebuilt from the built-in defaults through the CLI alone. + +When `std` is not in the effective keep, a warning is printed (expanding `std` is almost always an accident whose huge output only surfaces at submission time). The warning is suppressed when `--no-keep std` was passed explicitly on the CLI, which is taken as intent. ### Library change detection From ac7d58104bcb970186000e738afe4ce04a13f4d3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 12:01:33 +0900 Subject: [PATCH 08/10] docs(cheatsheet): say --embed attaches the source exactly as written "pre-tree-shaking code" could be read as the preprocessed-but-unshaken output; the attachment is the untouched text of the input file. Co-Authored-By: Claude Fable 5 --- docs/cheatsheet.ja.md | 2 +- docs/cheatsheet.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/cheatsheet.ja.md b/docs/cheatsheet.ja.md index 6ce07e7..1ad2fac 100644 --- a/docs/cheatsheet.ja.md +++ b/docs/cheatsheet.ja.md @@ -128,7 +128,7 @@ bundle() { risundle -e main.cpp > submission.cpp ``` -コードを公開するジャッジで、tree-shaking 前の読みやすいコードを見せたいときに。設定ファイルで `embed = true` を常用している場合は、`--no-embed` で今回だけ打ち消せます。 +コードを公開するジャッジで、自分が書いたままの元ソースを見せたいときに。設定ファイルで `embed = true` を常用している場合は、`--no-embed` で今回だけ打ち消せます。 ## ライブラリを触ったらやること diff --git a/docs/cheatsheet.md b/docs/cheatsheet.md index 8d99c49..8ef539e 100644 --- a/docs/cheatsheet.md +++ b/docs/cheatsheet.md @@ -129,7 +129,7 @@ From then on, `bundle main.cpp` is all you need. When the fallback fires, check risundle -e main.cpp > submission.cpp ``` -For judges that publish submissions, when you want readers to see the readable pre-tree-shaking code. If your config file sets `embed = true`, cancel it for one run with `--no-embed`. +For judges that publish submissions, when you want readers to see the source exactly as you wrote it. If your config file sets `embed = true`, cancel it for one run with `--no-embed`. ## After touching a library From 2a4680f9bae2f32994382065ba45500ed01e310b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 14:13:08 +0900 Subject: [PATCH 09/10] style(cli): declare overrides_with on both sides of the embed pair One-sided overrides_with already resolves last-wins in both directions (verified in review), so this is intent documentation, not a bug fix. Co-Authored-By: Claude Fable 5 --- src/cli.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/cli.rs b/src/cli.rs index 6dd08f8..45cdffc 100644 --- a/src/cli.rs +++ b/src/cli.rs @@ -34,8 +34,8 @@ pub struct BundleArgs { #[arg(short, long, overrides_with = "no_embed")] pub embed: bool, - /// Do not embed the original source (cancels the config file) - #[arg(long)] + /// Do not embed the original source (cancels a configured embed) + #[arg(long, overrides_with = "embed")] pub no_embed: bool, /// Skip hash verification of library updates From 9bced9e7f5744cc9930ae602ed30bd9ce3a01551 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=82=8A=E3=81=99=E3=82=8A=E3=81=99/TwoSquirrels?= <47352965+TwoSquirrels@users.noreply.github.com> Date: Sat, 11 Jul 2026 14:13:08 +0900 Subject: [PATCH 10/10] docs: say --no-embed cancels only a configured embed "cancels the config file" read as if the whole file were ignored, which is --no-config's job. Co-Authored-By: Claude Fable 5 --- README.ja.md | 2 +- README.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README.ja.md b/README.ja.md index b144de0..f9c4245 100644 --- a/README.ja.md +++ b/README.ja.md @@ -63,7 +63,7 @@ risundle [OPTIONS] [-- ...] | `--no-keep ` | 維持指定 (keep) からライブラリを外す (繰り返し可。`--keep` より優先) | | `--no-tree-shaking` | tree-shaking を無効化し、keep 指定以外をすべて展開する (フォールバック用) | | `-e`, `--embed` | 元のソースを先頭にコメントとして埋め込む | -| `--no-embed` | 元のソースを埋め込まない (設定ファイルの指定を打ち消す) | +| `--no-embed` | 元のソースを埋め込まない (設定の `embed = true` を打ち消す) | | `-n`, `--no-check` | ライブラリ更新のハッシュ検証をスキップする | | `--no-config` | `.risundlerc.toml` を無視する (設定ファイルが無い時と同じ挙動) | | `-- ...` | `--` 以降をコンパイラへそのまま渡す (設定の options への追記) | diff --git a/README.md b/README.md index 73fca7d..f0752ed 100644 --- a/README.md +++ b/README.md @@ -63,7 +63,7 @@ Bundles `` and writes the result to standard output. | `--no-keep ` | Stop keeping a library (repeatable; beats `--keep`) | | `--no-tree-shaking` | Disable tree-shaking and expand everything except kept libraries (useful as a fallback) | | `-e`, `--embed` | Embed the original source as a comment at the top | -| `--no-embed` | Do not embed the original source (cancels the config file) | +| `--no-embed` | Do not embed the original source (cancels a configured `embed = true`) | | `-n`, `--no-check` | Skip the hash verification of library updates | | `--no-config` | Ignore any `.risundlerc.toml`, behaving as if none exists | | `-- ...` | Pass everything after `--` straight to the compiler, appended to the configured options |