Skip to content

fix: return clear error for duplicate plugin names (fix #13798)#14919

Open
akuligowski9 wants to merge 3 commits intotauri-apps:devfrom
akuligowski9:fix/duplicate-plugin-error
Open

fix: return clear error for duplicate plugin names (fix #13798)#14919
akuligowski9 wants to merge 3 commits intotauri-apps:devfrom
akuligowski9:fix/duplicate-plugin-error

Conversation

@akuligowski9
Copy link
Copy Markdown

Summary

  • Adds a PluginNameAlreadyExists(String) error variant (consistent with WindowLabelAlreadyExists / WebviewLabelAlreadyExists)
  • PluginStore::register() now returns Result<()> and rejects duplicates
  • AppHandle::plugin() checks for duplicates before running initialize(), then propagates the error
  • Builder::plugin() warns via log::warn! and replaces the old plugin (preserves backward compat since it returns Self)

Motivation

When a user registers two plugins with the same name, the duplicate silently replaces the original. If the replaced plugin was a core plugin (e.g. "path", "event", "window"), the app later panics with an inscrutable state() called before manage() — giving zero indication that a duplicate plugin name was the root cause.

How it works

Scenario Behavior
Two plugins with the same name on Builder log::warn!, second replaces first (backward compat)
User plugin collides with core plugin name register_core_plugins()Err(PluginNameAlreadyExists("window")) — clear error
Runtime duplicate via AppHandle::plugin() Err(PluginNameAlreadyExists("my-plugin")) — caller can handle it

Test plan

  • cargo check -p tauri compiles
  • cargo clippy -p tauri -- -D warnings passes
  • cargo test -p tauri — all 52 unit tests + 86 doc-tests pass

🤖 Generated with Claude Code

@akuligowski9 akuligowski9 requested a review from a team as a code owner February 9, 2026 21:54
@github-project-automation github-project-automation Bot moved this to 📬Proposal in Roadmap Feb 9, 2026
Copy link
Copy Markdown
Member

@FabianLars FabianLars left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the PR! Would you mind signing (and force-pushing) your commit? Our branch protection rules require that :)

Comment thread crates/tauri/src/plugin.rs Outdated
Comment on lines +886 to +888
if self.has(plugin.name()) {
return Err(crate::Error::PluginNameAlreadyExists(plugin.name().to_string()));
}
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think it makes sense to have the very same check both here and in the 2 register() methods above

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point — I've moved the duplicate check to Builder::plugin() only, so it catches mistakes early at app setup. Runtime registration via AppHandle::plugin() keeps the existing replace behavior, so devs still have the choice to handle duplicates themselves.

Comment thread crates/tauri/src/app.rs Outdated
let name = plugin.name().to_string();
if self.plugins.has(&name) {
log::warn!("plugin `{name}` already registered, replacing with new instance");
self.plugins.unregister(&name);
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

not the biggest fan of the behavior change. i think devs should handle that themselves so they have a choice

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed — I've updated the approach. The duplicate check now only applies at build time in Builder::plugin(), where it's clearly a developer mistake (registering the same plugin twice in setup code). Runtime registration via AppHandle::plugin() keeps the existing silent-replace behavior, so devs retain full control.

@akuligowski9 akuligowski9 force-pushed the fix/duplicate-plugin-error branch from 34d8a9f to 82b277a Compare February 16, 2026 19:42
@github-actions
Copy link
Copy Markdown
Contributor

Package Changes Through 82b277a

There are 4 changes which include tauri-cli with patch, @tauri-apps/cli with patch, tauri-bundler with patch, tauri with patch

Planned Package Versions

The following package releases are the planned based on the context of changes in this pull request.

package current next
tauri-bundler 2.8.0 2.8.1
tauri 2.10.2 2.10.3
@tauri-apps/cli 2.10.0 2.10.1
tauri-cli 2.10.0 2.10.1

Add another change file through the GitHub UI by following this link.


Read about change files or the docs at github.com/jbolda/covector

@akuligowski9 akuligowski9 force-pushed the fix/duplicate-plugin-error branch from 8867a39 to 2e53f1e Compare February 20, 2026 18:49
…3798)

Move the duplicate plugin check to Builder::plugin() only, so it
catches mistakes early at app setup. Runtime registration via
AppHandle::plugin() keeps the existing replace behavior, giving
devs the choice to handle duplicates themselves.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@akuligowski9 akuligowski9 force-pushed the fix/duplicate-plugin-error branch from 2e53f1e to c3466e4 Compare February 20, 2026 18:51
@Legend-Master Legend-Master added the ai-slop Low effort content, see https://github.com/tauri-apps/tauri?tab=contributing-ov-file#ai-tool-policy label Mar 4, 2026
@akuligowski9
Copy link
Copy Markdown
Author

Hi! Just a gentle ping — this PR adds a clear error message for duplicate plugin names (resolves #13798) and has been ready for review since February. Let me know if there's anything I should adjust!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

ai-slop Low effort content, see https://github.com/tauri-apps/tauri?tab=contributing-ov-file#ai-tool-policy

Projects

Status: 📬Proposal

Development

Successfully merging this pull request may close these issues.

3 participants