tauri-apps/tauri · error
failed to extract merge module filename
Error message
failed to extract merge module filename
What it means
get_merge_modules iterates *.msm files in the merge-modules directory and derives each module's filename via Path::file_name(). If a matched path has no final component (ends in '..', root, or empty), file_name() returns None and the code panics with .expect("failed to extract merge module filename").
Solutions
- Point mergeModules at actual .msm files, not directories; remove trailing slashes and '..' components from the configured paths.
- Check the merge-modules directory for odd entries (dot directories, symlinks to roots) and clean them.
- Replace the expect with file_name().with_context(...)? or a filter_map that skips nameless paths.
Example fix
// before
let filename = path.file_name().expect("failed to extract merge module filename")
.to_os_string().into_string().expect("failed to convert merge module filename to string");
// after
let filename = path.file_name()
.with_context(|| format!("merge module path has no filename: {}", path.display()))?
.to_string_lossy().into_owned(); Defensive patterns
Strategy: validation
Validate before calling
// pre-scan merge module dir
for entry in glob("**/*.msm")? {
let p = entry?;
if p.file_name().is_none() {
return Err(anyhow!("bad merge module path: {}", p.display()));
}
} Type guard
fn has_filename(p: &std::path::Path) -> bool { p.file_name().is_some() } Try / catch
// wrap the bundler in a subprocess; on this panic, report that a mergeModules // path is malformed (trailing slash, '..', or a directory).
Prevention
- Configure mergeModules as concrete .msm files, not directories
- Avoid trailing separators and '..' in configured paths
- Sanitize downloaded merge modules (rename to ASCII, place in a clean dir)
When it happens
Trigger: Calling bundle_project with bundle.windows.wix.mergeModules entries (or the resources/resources dir containing merge modules) where a glob-expanded path lacks a file name — e.g. a glob like "dir/*" matched nothing useful or the configured path ends in a separator or '..'.
Common situations: A merge module configured as a directory instead of an .msm file, a path with a trailing slash in tauri.conf.json, or a custom glob returning '.'/'..' entries.
Related errors
- app version build number cannot be greater than 65535
- app version major number cannot be greater than 255
- app version minor number cannot be greater than 255
- app version patch number cannot be greater than 65535
- app wix version should be in the format…
AI-assisted analysis of tauri-apps/tauri@460ec35447 (2026-09-18).
Data as JSON: /api/errors/fa6d08fa77816d12.
Report an issue: GitHub.
Appendix: source
Thrown at crates/tauri-bundler/src/bundle/windows/msi/mod.rs:985
struct MergeModule {
name: String,
path: String,
}
fn get_merge_modules(settings: &Settings) -> crate::Result<Vec<MergeModule>> {
let mut merge_modules = Vec::new();
let regex = Regex::new(r"[^\w\d\.]")?;
for msm in glob::glob(
&PathBuf::from(glob::Pattern::escape(
&settings.project_out_directory().to_string_lossy(),
))
.join("*.msm")
.to_string_lossy(),
)? {
let path = msm?;
let filename = path
.file_name()
.expect("failed to extract merge module filename")
.to_os_string()
.into_string()
.expect("failed to convert merge module filename to string");
merge_modules.push(MergeModule {
name: regex.replace_all(&filename, "").to_string(),
path: path.to_string_lossy().to_string(),
});
}
Ok(merge_modules)
}
/// Generates the data required for the resource bundling on wix
fn generate_resource_data(settings: &Settings) -> crate::Result<ResourceDirectory> {
let cwd = std::env::current_dir()?;
let mut root_resource_directory = ResourceDirectory::default();
let mut added_resources = HashSet::new();
View on GitHub (pinned to 460ec35447)