From 8ed0d92050c92bf278541ec6727bf3f3632601b7 Mon Sep 17 00:00:00 2001 From: David Pursehouse Date: Fri, 18 Oct 2013 18:57:56 +0900 Subject: [PATCH] Allow plugins to get their canonical web URL injected This change allows a plugin to get its canonical web URL injected at runtime. The URL is composed of the server's canonical web URL and the plugin's name, i.e. `http://review.example.com:8080/plugins/plugin-name/`. The canonical web URL may be injected into any .jar plugin regardless of whether or not the plugin provides an HTTP servlet. Change-Id: Id1a8489d49bfebff4ffdb8de58e9d0445113a09b --- Documentation/dev-plugins.txt | 23 ++++++++++ .../annotations/PluginCanonicalWebUrl.java | 42 +++++++++++++++++++ .../gerrit/server/plugins/JarPlugin.java | 7 ++++ .../gerrit/server/plugins/PluginLoader.java | 15 ++++++- 4 files changed, 85 insertions(+), 2 deletions(-) create mode 100644 gerrit-extension-api/src/main/java/com/google/gerrit/extensions/annotations/PluginCanonicalWebUrl.java diff --git a/Documentation/dev-plugins.txt b/Documentation/dev-plugins.txt index 11f7721da0..173ee79627 100644 --- a/Documentation/dev-plugins.txt +++ b/Documentation/dev-plugins.txt @@ -191,6 +191,29 @@ public class MyClass { } ---- +A plugin can get its canonical web URL injected at runtime: + +[source,java] +---- +public class MyClass { + + private final String url; + + @Inject + public MyClass(@PluginCanonicalWebUrl String url) { + this.url = url; + } + + [...] +} +---- + +The URL is composed of the server's canonical web URL and the plugin's +name, i.e. `http://review.example.com:8080/plugin-name`. + +The canonical web URL may be injected into any .jar plugin regardless of +whether or not the plugin provides an HTTP servlet. + [[reload_method]] Reload Method ~~~~~~~~~~~~~ diff --git a/gerrit-extension-api/src/main/java/com/google/gerrit/extensions/annotations/PluginCanonicalWebUrl.java b/gerrit-extension-api/src/main/java/com/google/gerrit/extensions/annotations/PluginCanonicalWebUrl.java new file mode 100644 index 0000000000..fd144298b7 --- /dev/null +++ b/gerrit-extension-api/src/main/java/com/google/gerrit/extensions/annotations/PluginCanonicalWebUrl.java @@ -0,0 +1,42 @@ +// Copyright (C) 2013 The Android Open Source Project +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package com.google.gerrit.extensions.annotations; + +import static java.lang.annotation.RetentionPolicy.RUNTIME; + +import com.google.inject.BindingAnnotation; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.Target; + +/** + * Annotation applied to a String containing the plugin canonical web URL. + *

+ * A plugin or extension may receive this string by Guice injection to discover + * the canonical web URL under which the plugin is available: + * + *

+ *  @Inject
+ *  MyType(@PluginCanonicalWebUrl String myUrl) {
+ *  ...
+ *  }
+ * 
+ */ +@Target({ElementType.PARAMETER, ElementType.FIELD}) +@Retention(RUNTIME) +@BindingAnnotation +public @interface PluginCanonicalWebUrl { +} diff --git a/gerrit-server/src/main/java/com/google/gerrit/server/plugins/JarPlugin.java b/gerrit-server/src/main/java/com/google/gerrit/server/plugins/JarPlugin.java index 6adc677ffa..1568997b43 100644 --- a/gerrit-server/src/main/java/com/google/gerrit/server/plugins/JarPlugin.java +++ b/gerrit-server/src/main/java/com/google/gerrit/server/plugins/JarPlugin.java @@ -17,6 +17,7 @@ package com.google.gerrit.server.plugins; import com.google.common.base.Strings; import com.google.common.collect.Lists; import com.google.gerrit.common.Nullable; +import com.google.gerrit.extensions.annotations.PluginCanonicalWebUrl; import com.google.gerrit.extensions.annotations.PluginData; import com.google.gerrit.extensions.annotations.PluginName; import com.google.gerrit.extensions.registration.RegistrationHandle; @@ -59,6 +60,7 @@ class JarPlugin extends Plugin { private final JarFile jarFile; private final Manifest manifest; private final File dataDir; + private final String pluginCanonicalWebUrl; private final ClassLoader classLoader; private Class sysModule; private Class sshModule; @@ -71,6 +73,7 @@ class JarPlugin extends Plugin { private List> reloadableHandles; public JarPlugin(String name, + String pluginCanonicalWebUrl, PluginUser pluginUser, File srcJar, FileSnapshot snapshot, @@ -83,6 +86,7 @@ class JarPlugin extends Plugin { @Nullable Class sshModule, @Nullable Class httpModule) { super(name, srcJar, pluginUser, snapshot, apiType); + this.pluginCanonicalWebUrl = pluginCanonicalWebUrl; this.jarFile = jarFile; this.manifest = manifest; this.dataDir = dataDir; @@ -193,6 +197,9 @@ class JarPlugin extends Plugin { bind(String.class) .annotatedWith(PluginName.class) .toInstance(getName()); + bind(String.class) + .annotatedWith(PluginCanonicalWebUrl.class) + .toInstance(pluginCanonicalWebUrl); bind(File.class) .annotatedWith(PluginData.class) diff --git a/gerrit-server/src/main/java/com/google/gerrit/server/plugins/PluginLoader.java b/gerrit-server/src/main/java/com/google/gerrit/server/plugins/PluginLoader.java index 75697446bf..ea19fe3410 100644 --- a/gerrit-server/src/main/java/com/google/gerrit/server/plugins/PluginLoader.java +++ b/gerrit-server/src/main/java/com/google/gerrit/server/plugins/PluginLoader.java @@ -14,6 +14,7 @@ package com.google.gerrit.server.plugins; +import com.google.common.base.CharMatcher; import com.google.common.base.Joiner; import com.google.common.base.Objects; import com.google.common.base.Predicate; @@ -30,6 +31,7 @@ import com.google.gerrit.extensions.events.LifecycleListener; import com.google.gerrit.extensions.systemstatus.ServerInformation; import com.google.gerrit.extensions.webui.JavaScriptPlugin; import com.google.gerrit.server.PluginUser; +import com.google.gerrit.server.config.CanonicalWebUrl; import com.google.gerrit.server.config.ConfigUtil; import com.google.gerrit.server.config.GerritServerConfig; import com.google.gerrit.server.config.SitePaths; @@ -86,6 +88,7 @@ public class PluginLoader implements LifecycleListener { private final Queue toCleanup; private final Provider cleaner; private final PluginScannerThread scanner; + private final Provider urlProvider; @Inject public PluginLoader(SitePaths sitePaths, @@ -93,7 +96,8 @@ public class PluginLoader implements LifecycleListener { ServerInformationImpl sii, PluginUser.Factory puf, Provider pct, - @GerritServerConfig Config cfg) { + @GerritServerConfig Config cfg, + @CanonicalWebUrl Provider provider) { pluginsDir = sitePaths.plugins_dir; dataDir = sitePaths.data_dir; tmpDir = sitePaths.tmp_dir; @@ -106,6 +110,7 @@ public class PluginLoader implements LifecycleListener { toCleanup = Queues.newArrayDeque(); cleanupHandles = Maps.newConcurrentMap(); cleaner = pct; + urlProvider = provider; long checkFrequency = ConfigUtil.getTimeUnit(cfg, "plugins", null, "checkFrequency", @@ -504,7 +509,13 @@ public class PluginLoader implements LifecycleListener { Class sysModule = load(sysName, pluginLoader); Class sshModule = load(sshName, pluginLoader); Class httpModule = load(httpName, pluginLoader); - Plugin plugin = new JarPlugin(name, pluginUserFactory.create(name), + + String url = String.format("%s/plugins/%s/", + CharMatcher.is('/').trimTrailingFrom(urlProvider.get()), + name); + + Plugin plugin = new JarPlugin(name, url, + pluginUserFactory.create(name), srcJar, snapshot, jarFile, manifest, new File(dataDir, name), type, pluginLoader,