This is a Polarion extension which provides common part to other extensions reducing code duplication.
An extension which inherits from this generic extension will automatically get following functionality:
- An "about" page on administrative section of Polarion with basic information about this extension
- API to manipulate settings of this extension - to read, save settings and reverting them to default values as well as getting list of settings history revisions
- API to serialize/deserialize XML data (
JAXBUtils
) - REST application and end points giving access to settings functionality described above as well as access to extension information and version
- Swagger UI page listing information about REST API provided
To properly inherit from this generic extension and to take advantage of all mentioned above functionality out of the box certain steps should be done, see below.
Maven's pom.xml
should contain following content:
- Reference to parent POM (don't forget to use proper version of it):
<parent>
<groupId>ch.sbb.polarion.extensions</groupId>
<artifactId>ch.sbb.polarion.extension.generic</artifactId>
<version><!-- version goes here --></version>
</parent>
- Specify extension context, automatic module name, discover base package and web application name in POM's properties:
<properties>
<maven-jar-plugin.Extension-Context>pdf-exporter</maven-jar-plugin.Extension-Context>
<maven-jar-plugin.Automatic-Module-Name>ch.sbb.polarion.extension.pdf_exporter</maven-jar-plugin.Automatic-Module-Name>
<maven-jar-plugin.Discover-Base-Package>ch.sbb.polarion.extension.pdf_exporter</maven-jar-plugin.Discover-Base-Package>
<maven-jar-plugin.Configuration-Properties-Prefix>ch.sbb.polarion.extension.pdf-exporter</maven-jar-plugin.Configuration-Properties-Prefix>
<web.app.name>${maven-jar-plugin.Extension-Context}</web.app.name>
</properties>
- Reference or extend following build plugins:
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-clean-plugin</artifactId>
</plugin>
<plugin>
<groupId>ch.sbb.maven.plugins</groupId>
<artifactId>markdown2html-maven-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-javadoc-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-source-plugin</artifactId>
</plugin>
<plugin>
<groupId>io.swagger.core.v3</groupId>
<artifactId>swagger-maven-plugin</artifactId>
<configuration>
<outputFormat>YAML</outputFormat>
<resourcePackages>
<package>ch.sbb.polarion.extension.generic.rest.controller</package>
<package>ch.sbb.polarion.extension.generic.rest.model</package>
<package>ch.sbb.polarion.extension.pdf.exporter.rest.controller</package>
<package>ch.sbb.polarion.extension.pdf.exporter.rest.model</package>
</resourcePackages>
</configuration>
</plugin>
</plugins>
</build>
File MANIFEST.MF
should be created in src/main/resources/META-INF/MANIFEST.MF
with following content:
- Property
Bundle-Name
should contain extension name, eg.
Bundle-Name: PDF Exporter Extension for Polarion ALM
- Property
Require-Bundle
should list all bundles from which this extension depends, eg.
Require-Bundle: com.polarion.portal.tomcat,
com.polarion.alm.ui,
com.polarion.platform.guice,
com.polarion.alm.tracker,
org.glassfish.jersey,
com.fasterxml.jackson,
com.fasterxml.jackson.jaxrs,
io.swagger,
org.apache.commons.logging,
slf4j.api,
org.springframework.spring-core,
org.springframework.spring-web
- If Polarion's form extension is implemented, property
Guice-Modules
should specify a class which does this, eg.
Guice-Modules: ch.sbb.polarion.extension.pdf.exporter.PdfExporterModule
If new extension should provide functionality to manipulate its settings, settings classes should be implemented extending
GenericNamedSettings<T extends SettingsModel>
, eg:
public class CssSettings extends GenericSettings<CssModel> {
private static final String FEATURE_NAME = "css";
public CssSettings() {
super(FEATURE_NAME);
}
public CssSettings(SettingsService settingsService) {
super(FEATURE_NAME, settingsService);
}
@Override
public @NotNull CssModel defaultValues() {
return CssModel.builder().css(ScopeUtils.getFileContent("default/dle-pdf-export.css")).build();
}
}
...and settings model class from example above like this:
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
@ToString
@EqualsAndHashCode(callSuper = false)
@JsonInclude(JsonInclude.Include.NON_NULL)
public class CssModel extends SettingsModel {
public static final String CSS = "CSS";
private String css;
@Override
protected String serializeModelData() {
return serializeEntry(CSS, css);
}
@Override
protected void deserializeModelData(String serializedString) {
css = deserializeEntry(CSS, serializedString);
}
}
REST application class should inherit from GenericRestApplication
of generic extension,
registering settings classes and extending classes of REST controller, web application filters and exception mappers:
public class PdfExporterRestApplication extends GenericRestApplication {
private final Logger logger = Logger.getLogger(PdfExporterRestApplication.class);
public PdfExporterRestApplication() {
logger.debug("Creating PDF-Exporter REST Application...");
try {
NamedSettingsRegistry.INSTANCE.register(
Arrays.asList(
new StylePackageSettings(),
new HeaderFooterSettings(),
new CssSettings(),
new LocalizationSettings(),
new CoverPageSettings(),
new FileNameTemplateSettings()
)
);
} catch (Exception e) {
logger.error("Error during registration of named settings", e);
}
logger.debug("PDF-Exporter REST Application has been created");
}
...
}
If new extension will contain UI parts/pages/artifacts, UI servlet class should be created extending GenericUiServlet
simply specifying servlet name in constructor:
public class PdfExporterAdminUiServlet extends GenericUiServlet {
@Serial
private static final long serialVersionUID = -6337912330074718317L;
public PdfExporterAdminUiServlet() {
super("pdf-exporter-admin");
}
}
In order to register additional configuration properties a subclass of ExtensionConfiguration
must be marked with the @Discoverable
:
@Discoverable
public class PdfExporterExtensionConfiguration extends ExtensionConfiguration {
@Override
public @NotNull List<String> getSupportedProperties() {
List<String> supportedProperties = new ArrayList<>(super.getSupportedProperties());
supportedProperties.add("weasyprint.service");
...
return supportedProperties;
}
...
}