1 package com.atlassian.plugin;
2
3 import org.dom4j.Element;
4
5 import javax.annotation.Nonnull;
6 import java.util.Map;
7
8 public interface ModuleDescriptor<T> extends ScopeAware, Resourced {
9 /**
10 * The complete key for this module, including the plugin key.
11 * <p>
12 * Format is plugin.key:module.key
13 *
14 * @return The complete key for this module.
15 * @see #getKey()
16 * @see #getPluginKey()
17 */
18 String getCompleteKey();
19
20 /**
21 * The plugin key for this module, derived from the complete key.
22 *
23 * @return The plugin key for this module.
24 * @see #getKey()
25 * @see #getCompleteKey()
26 */
27 String getPluginKey();
28
29 /**
30 * The key for this module, unique within the plugin.
31 *
32 * @return The key for this module.
33 * @see #getCompleteKey()
34 * @see #getPluginKey()
35 */
36 String getKey();
37
38 /**
39 * A simple string name for this descriptor.
40 *
41 * @return The name for this ModuleDescriptor.
42 */
43 String getName();
44
45 /**
46 * A simple description of this descriptor.
47 *
48 * @return The description for this ModuleDescriptor.
49 */
50 String getDescription();
51
52 /**
53 * The class of the module this descriptor creates.
54 *
55 * @return The class of the module this descriptor creates.
56 * @see #getModule()
57 */
58 Class<T> getModuleClass();
59
60 /**
61 * The particular module object created by this plugin.
62 *
63 * @return The module object created by this plugin.
64 * @see #getModuleClass()
65 */
66 T getModule();
67
68 /**
69 * Initialise a module given it's parent plugin and the XML element
70 * representing the module.
71 * <p>
72 * Since atlassian-plugins v2.2, you can no longer load classes from the
73 * plugin in this method, because the OSGi bundle that they will live in is
74 * not built yet. Load classes in the {@link StateAware#enabled()}
75 * method instead.
76 *
77 * @param plugin The plugin that the module belongs to. Must not be null.
78 * @param element XML element representing the module. Must not be null.
79 * @throws PluginParseException Can be thrown if an error occurs while
80 * parsing the XML element.
81 */
82 void init(@Nonnull Plugin plugin, @Nonnull Element element) throws PluginParseException;
83
84 /**
85 * Whether or not this plugin module is enabled by default.
86 *
87 * @return {@code true} if this plugin module is enabled by default.
88 */
89 boolean isEnabledByDefault();
90
91 /**
92 * Whether or not this plugin module is a "system" module that shouldn't be
93 * made visible/disable-able to the user. System plugin modules also don't
94 * have their permissions checked, as they may be created dynamically in
95 * response to another, more safe module
96 *
97 * @return {@code true} if this plugin module is a "system" plugin that
98 * shouldn't be made visible/disable-able to the user.
99 */
100 boolean isSystemModule();
101
102 /**
103 * Override this if your plugin needs to clean up when it's been removed.
104 */
105 void destroy();
106
107 Float getMinJavaVersion();
108
109 /**
110 * If a min java version has been specified this will return true if the
111 * running jvm is >= to the specified version. If this is not set then it is
112 * treated as not having a preference.
113 *
114 * @return true if satisfied, false otherwise.
115 */
116 boolean satisfiesMinJavaVersion();
117
118 Map<String, String> getParams();
119
120 /**
121 * Key used to override {@link #getName()} when using internationalisation.
122 *
123 * @return the i18n key. May be null.
124 */
125 String getI18nNameKey();
126
127 /**
128 * Key used to override {@link #getDescription()} when using
129 * internationalisation.
130 *
131 * @return the i18n key. May be null.
132 */
133 String getDescriptionKey();
134
135 /**
136 * @return The plugin this module descriptor is associated with
137 */
138 Plugin getPlugin();
139
140 /**
141 * Compares the specified object with this module descriptor for equality.
142 * <p>
143 * Returns <tt>true</tt> if the given object is also a module descriptor and the two descriptors have the same
144 * "complete key" as determined by {@link #getCompleteKey()}.
145 * <p>
146 * This ensures that the <tt>equals</tt> method works properly across
147 * different implementations of the <tt>ModuleDescriptor</tt> interface.
148 *
149 * @param obj object to be compared for equality with this module descriptor.
150 * @return <tt>true</tt> if the specified object is equal to this module descriptor.
151 * @since 2.8.0
152 */
153 boolean equals(Object obj);
154
155 /**
156 * Returns the hash code value for this module descriptor. The hash code
157 * of a module descriptor <tt>d</tt> is defined to be: <pre>
158 * getCompleteKey() == null ? 0 : getCompleteKey().hashCode()
159 * </pre>
160 * This ensures that <tt>d1.equals(d2)</tt> implies that
161 * <tt>d1.hashCode()==d2.hashCode()</tt> for any two Module Descriptors
162 * <tt>d1</tt> and <tt>d2</tt>, as required by the general
163 * contract of <tt>Object.hashCode</tt>.
164 *
165 * @return the hash code value for this module descriptor.
166 * @see Object#hashCode()
167 * @see Object#equals(Object)
168 * @see #equals(Object)
169 * @since 2.8.0
170 */
171 int hashCode();
172
173 /**
174 * Get whether this plugin module is enabled.
175 *
176 * @return If this module is enabled
177 * @since 3.1
178 */
179 boolean isEnabled();
180
181 /**
182 * Changes state to "broken"
183 * <p>
184 * Being breakable is something subclasses can opt in to, therefore by default {@link ModuleDescriptor}s
185 * are unbreakable, this is a no-op, and {@link #isBroken()} returns {@code false}
186 */
187 default void setBroken() {
188 }
189
190 /**
191 * Returns true if this Module is "broken".
192 * <p>
193 * A "broken" module means that even though this ModuleDescriptor is enabled, calling {@code getModule()} results
194 * in an error. This typically occurs when the plugin version is not compatible with the version of the host product.
195 * <p>
196 * Note that some modules are lazy-loaded, and so this method is optimistic:
197 * it will return false until we discover that the Module is not loadable.
198 *
199 * @return {@code true} if broken, {@code false} otherwise
200 */
201 default boolean isBroken() {
202 return false;
203 }
204
205 /**
206 * Returns the display name of this descriptor, e.g. for use in log messages. Does not identify the owning plugin.
207 *
208 * @return a non-blank name
209 * @since 4.6.3
210 */
211 default String getDisplayName() {
212 return getName() == null ? getKey() : getName();
213 }
214 }