Ben Woskow avatar Ben Woskow committed 0189215

initial commit for tutorial

Comments (0)

Files changed (13)

+To avoid future confusion, we recommend that you include a license with your plugin.
+This file is simply a reminder.
+
+For a template license you can have a look at: http://www.opensource.org/licenses/
+
+Atlassian releases most of its modules under a BSD license: http://www.opensource.org/licenses/bsd-license.php
+You have successfully created a plugin using the JIRA plugin archetype!
+
+Here are the SDK commands you'll use immediately:
+
+* atlas-run   -- installs this plugin into JIRA and starts it on http://localhost:2990/jira
+* atlas-debug -- same as atlas-run, but allows a debugger to attach at port 5005
+* atlas-cli   -- after atlas-run or atlas-debug, opens a Maven command line window:
+                 - 'pi' reinstalls the plugin into the running JIRA instance
+* atlas-help  -- prints description for all commands in the SDK
+
+Full documentation is always available at:
+
+https://developer.atlassian.com/display/DOCS/Developing+with+the+Atlassian+Plugin+SDK
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+    <groupId>com.example.plugins.tutorial</groupId>
+    <artifactId>plugin-license-compatibility-tutorial</artifactId>
+    <packaging>atlassian-plugin</packaging>
+    <name>plugin-license-compatibility-tutorial</name>
+    <version>1.0-SNAPSHOT</version>
+    <description>This is the com.example.plugins.tutorial:plugin-license-compatibility-tutorial plugin for Atlassian JIRA.
+    </description>
+    <organization>
+        <name>Example Company</name>
+        <url>http://www.example.com/</url>
+    </organization>
+    <build>
+        <plugins>
+            <plugin>
+                <groupId>com.atlassian.maven.plugins</groupId>
+                <artifactId>maven-jira-plugin</artifactId>
+                <version>3.7.2</version>
+                <extensions>true</extensions>
+                <configuration>
+                    <instructions>
+                        <Import-Package>
+                            com.atlassian.plugin*;version="0.0",
+                            com.atlassian.sal*;version="0.0",
+                            com.google.common*;version="1.0",
+                            javax.servlet*;version="0.0",
+                            org.apache.commons*;version="0.0",
+                            org.osgi.framework*;version="0.0",
+                            org.osgi.util*;version="0.0",
+                            org.slf4j*;version="1.5",
+                            org.springframework.beans*;version="0.0",
+                            org.springframework.context*;version="0.0",
+                            org.springframework.osgi*;version="0.0"
+                        </Import-Package>
+                        <Private-Package>
+                            com.atlassian.upm.license.storage.lib*
+                        </Private-Package>
+                        <DynamicImport-Package>
+                            com.atlassian.upm.api.license;version="2.0",
+                            com.atlassian.upm.api.license.entity;version="2.0",
+                            com.atlassian.upm.api.util;version="2.0",
+                            com.atlassian.upm.license.storage.plugin;version="2.0"
+                        </DynamicImport-Package>
+                    </instructions>
+                    <productVersion>${jira.version}</productVersion>
+                    <productDataVersion>${jira.version}</productDataVersion>
+                    <bundledArtifacts>
+                        <bundledArtifact>
+                            <groupId>com.atlassian.upm</groupId>
+                            <artifactId>atlassian-universal-plugin-manager-plugin</artifactId>
+                            <version>1.6.3</version>
+                        </bundledArtifact>
+                    </bundledArtifacts>
+                </configuration>
+            </plugin>
+            <plugin>
+                <artifactId>maven-compiler-plugin</artifactId>
+                <configuration>
+                    <source>1.6</source>
+                    <target>1.6</target>
+                </configuration>
+            </plugin>
+        </plugins>
+    </build>
+    <dependencies>
+        <dependency>
+            <groupId>com.atlassian.jira</groupId>
+            <artifactId>jira-api</artifactId>
+            <version>${jira.version}</version>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>junit</groupId>
+            <artifactId>junit</artifactId>
+            <version>4.8.1</version>
+            <scope>test</scope>
+        </dependency>
+        <dependency>
+            <groupId>com.atlassian.jira</groupId>
+            <artifactId>jira-tests</artifactId>
+            <version>${jira.version}</version>
+            <scope>test</scope>
+        </dependency>
+        <dependency>
+            <groupId>com.atlassian.jira</groupId>
+            <artifactId>jira-func-tests</artifactId>
+            <version>${jira.version}</version>
+            <scope>test</scope>
+        </dependency>
+        <dependency>
+            <groupId>javax.servlet</groupId>
+            <artifactId>servlet-api</artifactId>
+            <version>2.4</version>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>org.mockito</groupId>
+            <artifactId>mockito-all</artifactId>
+            <version>1.8.5</version>
+            <scope>test</scope>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.httpcomponents</groupId>
+            <artifactId>httpclient</artifactId>
+            <version>4.1.1</version>
+            <scope>test</scope>
+        </dependency>
+
+        <dependency>
+            <groupId>com.atlassian.upm</groupId>
+            <artifactId>plugin-license-storage-lib</artifactId>
+            <version>${upm.license.compatibility.version}</version>
+            <scope>compile</scope> <!-- intentionally compile scoped -->
+        </dependency>
+        <dependency>
+            <groupId>com.atlassian.upm</groupId>
+            <artifactId>plugin-license-storage-plugin</artifactId>
+            <version>${upm.license.compatibility.version}</version>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>com.atlassian.upm</groupId>
+            <artifactId>licensing-api</artifactId>
+            <version>${upm.license.compatibility.version}</version>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>com.atlassian.upm</groupId>
+            <artifactId>upm-api</artifactId>
+            <version>${upm.license.compatibility.version}</version>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>com.atlassian.sal</groupId>
+            <artifactId>sal-api</artifactId>
+            <version>2.4.0</version>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>org.springframework.osgi</groupId>
+            <artifactId>spring-osgi-core</artifactId>
+            <version>1.1.3</version>
+            <scope>provided</scope>
+        </dependency>
+        <dependency>
+            <groupId>commons-lang</groupId>
+            <artifactId>commons-lang</artifactId>
+            <version>2.4</version>
+            <scope>provided</scope>
+        </dependency>
+
+    </dependencies>
+    <properties>
+        <amps.version>3.7.2</amps.version>
+        <jira.version>5.0-rc2</jira.version>
+        <upm.license.compatibility.version>2.1-m2</upm.license.compatibility.version>
+    </properties>
+</project>
+

src/main/java/com/example/plugins/tutorial/MyPlugin.java

+package com.example.plugins.tutorial;
+
+public class MyPlugin
+{
+}

src/main/java/com/example/plugins/tutorial/servlet/LicenseServlet.java

+package com.example.plugins.tutorial.servlet;
+
+import java.io.IOException;
+
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServlet;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+import com.atlassian.sal.api.ApplicationProperties;
+import com.atlassian.upm.api.license.entity.PluginLicense;
+import com.atlassian.upm.api.util.Option;
+import com.atlassian.upm.license.storage.lib.ThirdPartyPluginLicenseStorageManager;
+
+import org.apache.commons.lang.StringUtils;
+
+public class LicenseServlet extends HttpServlet
+{
+    private final ThirdPartyPluginLicenseStorageManager thirdPartyPluginLicenseStorageManager;
+    private final ApplicationProperties applicationProperties;
+
+    public LicenseServlet(ThirdPartyPluginLicenseStorageManager thirdPartyPluginLicenseStorageManager,
+                          ApplicationProperties applicationProperties)
+    {
+        this.thirdPartyPluginLicenseStorageManager = thirdPartyPluginLicenseStorageManager;
+        this.applicationProperties = applicationProperties;
+    }
+
+    @Override
+    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException
+    {
+        resp.setContentType("text/html");
+        resp.getWriter().write("<html><body>");
+        outputBody(resp);
+        resp.getWriter().write("</body></html>");
+        resp.getWriter().close();
+    }
+
+    @Override
+    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException
+    {
+        resp.setContentType("text/html");
+        resp.getWriter().write("<html><body><b>");
+
+        if (!thirdPartyPluginLicenseStorageManager.isUpmLicensingAware())
+        {
+            String license = req.getParameter("license");
+            if (!StringUtils.isEmpty(license))
+            {
+                //we have a non-empty license parameter - let's update the license if it is valid.
+                Option<PluginLicense> validatedLicense = thirdPartyPluginLicenseStorageManager.validateLicense(license);
+                if (validatedLicense.isDefined())
+                {
+                    thirdPartyPluginLicenseStorageManager.setRawLicense(license);
+                    resp.getWriter().write("Valid license. License has been updated.");
+                }
+                else
+                {
+                    resp.getWriter().write("Invalid license. License has not been updated.");
+                }
+            }
+            else
+            {
+                //we have an empty/null license parameter - let's remove the stored license
+                thirdPartyPluginLicenseStorageManager.removeRawLicense();
+                resp.getWriter().write("License has been removed.");
+            }
+        }
+        else
+        {
+            //don't allow POSTs to occur to our license servlet if UPM is licensing-aware
+            resp.getWriter().write("Nice try! You cannot update your plugin license with this API when UPM is licensing-aware.");
+        }
+
+        resp.getWriter().write("</b>");
+        outputBody(resp);
+        resp.getWriter().write("</body></html>");
+        resp.getWriter().close();
+    }
+
+    private void outputBody(HttpServletResponse resp) throws ServletException, IOException
+    {
+        resp.getWriter().write("<br><br>UPM is licensing-aware: " + thirdPartyPluginLicenseStorageManager.isUpmLicensingAware());
+        resp.getWriter().write("<br>Plugin key: " + thirdPartyPluginLicenseStorageManager.getPluginKey());
+
+        if (!thirdPartyPluginLicenseStorageManager.isUpmLicensingAware())
+        {
+            resp.getWriter().write("<br><br>Update your license");
+            resp.getWriter().write("<br><form action=\"" + applicationProperties.getBaseUrl() + "/plugins/servlet/licenseservlet\" method=\"POST\">");
+            resp.getWriter().write("<textarea name=\"license\" cols=\"80\" rows=\"10\">");
+            for (String storedRawLicense : thirdPartyPluginLicenseStorageManager.getRawLicense())
+            {
+                //enter the stored license into the textarea, if the license has been stored
+                resp.getWriter().write(storedRawLicense);
+            }
+            resp.getWriter().write("</textarea>");
+            resp.getWriter().write("<br><input type=\"submit\" value=\"Save\" />");
+            resp.getWriter().write("</form>");
+        }
+        else
+        {
+            resp.getWriter().write("<br>Cannot modify plugin licenses with this API when UPM is licensing-aware. Please use ");
+            resp.getWriter().write("<a href=\"" + thirdPartyPluginLicenseStorageManager.getPluginManagementUri() + "\">UPM's licensing UI</a>.");
+        }
+    }
+}

src/main/resources/atlassian-plugin.properties

+#
+#Wed Jan 18 14:37:39 PST 2012
+license-servlet.name=License Servlet
+license-servlet.description=The License Servlet Plugin

src/main/resources/atlassian-plugin.xml

+<?xml version="1.0" encoding="UTF-8"?>
+
+<atlassian-plugin key="${project.groupId}.${project.artifactId}" name="${project.name}" plugins-version="2">
+  <plugin-info>
+    <description>${project.description}</description>
+    <version>${project.version}</version>
+    <vendor name="${project.organization.name}" url="${project.organization.url}"/>
+    <param name="atlassian-licensing-enabled">true</param>
+  </plugin-info>
+
+  <component-import key="pluginAccessor" interface="com.atlassian.plugin.PluginAccessor"/>
+  <component-import key="pluginController" interface="com.atlassian.plugin.PluginController"/>
+  <component-import key="txTemplate" interface="com.atlassian.sal.api.transaction.TransactionTemplate"/>
+  <component-import key="applicationProperties" interface="com.atlassian.sal.api.ApplicationProperties"/>
+
+  <component key="pluginLicenseStoragePluginInstaller" class="com.atlassian.upm.license.storage.lib.PluginLicenseStoragePluginInstaller"/>
+  <component key="thirdPartyPluginLicenseStorageManager" class="com.atlassian.upm.license.storage.lib.ThirdPartyPluginLicenseStorageManagerImpl"/>
+
+  <servlet name="License Servlet" i18n-name-key="license-servlet.name" key="license-servlet" class="com.example.plugins.tutorial.servlet.LicenseServlet">
+    <description key="license-servlet.description">The License Servlet Plugin</description>
+    <url-pattern>/licenseservlet</url-pattern>
+  </servlet>
+
+  <resource type="i18n" name="i18n" location="atlassian-plugin"/>
+
+</atlassian-plugin>

src/test/java/com/example/plugins/tutorial/MyPluginTest.java

+package com.example.plugins.tutorial;
+
+import org.junit.Test;
+
+public class MyPluginTest
+{
+    @Test
+    public void testSomething()
+    {
+    }
+}

src/test/java/com/example/plugins/tutorial/servlet/LicenseServletTest.java

+package com.example.plugins.tutorial.servlet;
+
+import org.junit.Test;
+import org.junit.After;
+import org.junit.Before;
+import org.mockito.Mockito;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+import static org.junit.Assert.*;
+import static org.mockito.Mockito.*;
+
+public class LicenseServletTest {
+
+    HttpServletRequest mockRequest;
+    HttpServletResponse mockResponse;
+
+    @Before
+    public void setup() {
+        mockRequest = mock(HttpServletRequest.class);
+        mockResponse = mock(HttpServletResponse.class);
+    }
+
+    @After
+    public void tearDown() {
+
+    }
+
+    @Test
+    public void testSomething() {
+        String expected = "test";
+        when(mockRequest.getParameter(Mockito.anyString())).thenReturn(expected);
+        assertEquals(expected,mockRequest.getParameter("some string"));
+
+    }
+}

src/test/java/it/MyPluginTest.java

+package it;
+
+import org.junit.Test;
+
+public class MyPluginTest
+{
+    @Test
+    public void integrationTest()
+    {
+    }
+}

src/test/java/it/com/example/plugins/tutorial/servlet/LicenseServletFuncTest.java

+package it.com.example.plugins.tutorial.servlet;
+
+import org.apache.http.client.HttpClient;
+import org.apache.http.client.ResponseHandler;
+import org.apache.http.client.methods.HttpGet;
+import org.apache.http.impl.client.BasicResponseHandler;
+import org.apache.http.impl.client.DefaultHttpClient;
+import org.junit.Test;
+import org.junit.After;
+import org.junit.Before;
+
+import java.io.IOException;
+
+import static org.junit.Assert.*;
+
+
+public class LicenseServletFuncTest {
+
+    HttpClient httpClient;
+    String baseUrl;
+    String servletUrl;
+
+    @Before
+    public void setup() {
+        httpClient = new DefaultHttpClient();
+        baseUrl = System.getProperty("baseurl");
+        servletUrl = baseUrl + "/plugins/servlet/licenseservlet";
+    }
+
+    @After
+    public void tearDown() {
+        httpClient.getConnectionManager().shutdown();
+    }
+
+    @Test
+    public void testSomething() throws IOException {
+        HttpGet httpget = new HttpGet(servletUrl);
+
+        // Create a response handler
+        ResponseHandler<String> responseHandler = new BasicResponseHandler();
+        String responseBody = httpClient.execute(httpget, responseHandler);
+        assertTrue(null != responseBody && !"".equals(responseBody));
+    }
+}

src/test/resources/TEST_RESOURCES_README

+Create any of the test resources you might need in this directory.
+
+Please remove this file before releasing your plugin.

src/test/xml/TEST_XML_RESOURCES_README

+Create all XML test resources here - these might be needed for populating JIRA instance at the integration-test phase with test data.
+
+Please remove this file before releasing your plugin.
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.