From 5c3a67b1100fc8b499250e39b7683ba2ad868540 Mon Sep 17 00:00:00 2001 From: Jesse Hallam Date: Tue, 15 Jul 2025 22:46:41 -0300 Subject: [PATCH] MM-62746: drop manual plugin deployment support (#30019) We no longer support system administrators manually unpacking plugins into the server's working directory for plugins. Instead, the server will be free to remove folders and files from this directory at will as it synchronizes installed plugins from the prepackaged cache and filestore. Fixes: https://mattermost.atlassian.net/browse/MM-62746 Co-authored-by: Mattermost Build --- server/channels/app/plugin.go | 14 +++--------- server/channels/app/plugin_install.go | 32 +++++---------------------- server/i18n/en.json | 4 ---- 3 files changed, 9 insertions(+), 41 deletions(-) diff --git a/server/channels/app/plugin.go b/server/channels/app/plugin.go index fbfd68f6575..f9ce0633ca8 100644 --- a/server/channels/app/plugin.go +++ b/server/channels/app/plugin.go @@ -284,17 +284,9 @@ func (ch *Channels) syncPlugins() *model.AppError { logger := ch.srv.Log().With(mlog.String("plugin_id", pluginID)) - // Only handle managed plugins with .filestore flag file. - _, err := os.Stat(filepath.Join(*ch.cfgSvc.Config().PluginSettings.Directory, pluginID, managedPluginFileName)) - if os.IsNotExist(err) { - logger.Warn("Skipping sync for unmanaged plugin") - } else if err != nil { - logger.Error("Skipping sync for plugin after failure to check if managed", mlog.Err(err)) - } else { - logger.Info("Removing local installation of managed plugin before sync") - if err := ch.removePluginLocally(pluginID); err != nil { - logger.Error("Failed to remove local installation of managed plugin before sync", mlog.Err(err)) - } + logger.Info("Removing local installation of managed plugin before sync") + if err := ch.removePluginLocally(pluginID); err != nil { + logger.Error("Failed to remove local installation of managed plugin before sync", mlog.Err(err)) } }(plugin.Manifest.Id) } diff --git a/server/channels/app/plugin_install.go b/server/channels/app/plugin_install.go index 629763d7896..b00ee339d13 100644 --- a/server/channels/app/plugin_install.go +++ b/server/channels/app/plugin_install.go @@ -12,7 +12,6 @@ // - plugins prepackged with the server in the prepackaged_plugins/ directory // - plugins transitionally prepackaged with the server in the prepackaged_plugins/ directory // - plugins installed to the filestore (amazons3 or local, alongisde files and images) -// - unmanaged plugins manually extracted to the confgured local directory // ┌────────────────────────────┐ // │ ┌────────────────────────┐ │ // │ │prepackaged_plugins/ │ │ @@ -23,14 +22,11 @@ // │ │ │ // │ ▼ │ // │ ┌────────────────────────┐ │ -// │ │plugins/ │ │ -// │ │ unmanaged/ │ │ -// │ │ filestore/ │ │ ┌────────────────────────┐ -// │ │ .filestore │ │ │s3://bucket/plugins/ │ +// │ │plugins/ │ │ ┌────────────────────────┐ +// │ │ filestore/ │ │ │s3://bucket/plugins/ │ // │ │ prepackaged/ │◀┼───│ filestore.tar.gz │ -// │ │ .filestore │ │ │ transitional.tar.gz │ -// │ │ transitional/ │ │ └────────────────────────┘ -// │ │ .filestore │ │ +// │ │ transitional/ │ │ │ transitional.tar.gz │ +// │ │ │ │ └────────────────────────┘ // │ └────────────────────────┘ │ // │ ┌────────┤ // │ │ server │ @@ -45,13 +41,8 @@ // release. On first startup, they are unpacked just like prepackaged plugins, but also get copied // to the filestore. On future startups, the server uses the version in the filestore. // -// Plugins are installed to the filestore when the user installs via the marketplace or manually -// uploads a plugin bundle. (Or because the plugin is transitionally prepackaged). -// -// Unmanaged plugins were manually extracted by into the configured local directory. This legacy -// method of installing plugins is distinguished from other extracted plugins by the absence of a -// flag file (.filestore). Managed plugins unconditionally override unmanaged plugins. A future -// version of Mattermost will likely drop support for unmanaged plugins. +// Plugins are installed to the filestore when the user installs via the marketplace or system +// console. (Or because the plugin is transitionally prepackaged). // // ### Enabling a Plugin // @@ -98,10 +89,6 @@ import ( "github.com/mattermost/mattermost/server/v8/platform/shared/filestore" ) -// managedPluginFileName is the file name of the flag file that marks -// a local plugin folder as "managed" by the file store. -const managedPluginFileName = ".filestore" - // fileStorePluginFolder is the folder name in the file store of the plugin bundles installed. const fileStorePluginFolder = "plugins" @@ -506,13 +493,6 @@ func (ch *Channels) installExtractedPlugin(manifest *model.Manifest, fromPluginD return nil, model.NewAppError("installExtractedPlugin", "app.plugin.mvdir.app_error", nil, "", http.StatusInternalServerError).Wrap(err) } - // Flag plugin locally as managed by the filestore. - f, err := os.Create(filepath.Join(bundlePath, managedPluginFileName)) - if err != nil { - return nil, model.NewAppError("installExtractedPlugin", "app.plugin.flag_managed.app_error", nil, "", http.StatusInternalServerError).Wrap(err) - } - f.Close() - if manifest.HasWebapp() { updatedManifest, err := pluginsEnvironment.UnpackWebappBundle(manifest.Id) if err != nil { diff --git a/server/i18n/en.json b/server/i18n/en.json index 1baf6f5e939..9e6223db54b 100644 --- a/server/i18n/en.json +++ b/server/i18n/en.json @@ -6458,10 +6458,6 @@ "id": "app.plugin.filesystem.app_error", "translation": "Encountered filesystem error." }, - { - "id": "app.plugin.flag_managed.app_error", - "translation": "Unable to set plugin as managed by the file store." - }, { "id": "app.plugin.get_cluster_plugin_statuses.app_error", "translation": "Unable to get plugin statuses from the cluster."