/src/main/groovy/com/onresolve/jira/groovy/CannedScriptRunner.groovy
Groovy | 308 lines | 217 code | 54 blank | 37 comment | 35 complexity | 481d66ae84deec194ab560829357c784 MD5 | raw file
- package com.onresolve.jira.groovy
-
- import com.atlassian.jira.ComponentManager
- import com.atlassian.jira.util.BuildUtils
- import com.atlassian.jira.util.ErrorCollection
- import com.atlassian.jira.util.SimpleErrorCollection
- import com.opensymphony.util.TextUtils
- import java.util.regex.Matcher
- import javax.servlet.ServletRequest
- import webwork.action.ServletActionContext
- import com.atlassian.jira.project.ProjectManager
-
- class CannedScriptRunner extends GroovyRunner {
-
- private String preview
- private ErrorCollection errorCollection
- private URL scriptURL
-
- CannedScriptRunner(ScriptManager scriptManager) {
- super(scriptManager)
- }
-
- public List<String> getScriptArgs(String className) throws Exception {
- GroovyClassLoader gcl = getGcl();
- List<String> rt = new ArrayList<String>();
-
- def script = gcl.loadClass(className, true, false).newInstance();
-
- return script.getParameters(null)*."Name" ?: []
- }
-
- public String getCannedScriptHumanDesc (String className, Map actualArgs, boolean forPreview) throws Exception {
- GroovyClassLoader gcl = getGcl();
- def script = gcl.loadClass(className, true, false).newInstance();
- return script.getDescription(actualArgs, forPreview)
- }
-
- public ErrorCollection getValidationErrors (String className, Map actualArgs, boolean forPreview) throws Exception {
- GroovyClassLoader gcl = getGcl();
- def script = gcl.loadClass(className, true, false).newInstance();
- return script.doValidate(actualArgs, forPreview) ?: new SimpleErrorCollection()
- }
-
- public Map runCannedScript (String className, Map bindVars) throws Exception {
- GroovyClassLoader gcl = getGcl();
-
- // ensure script loaded else need to load, possibly reading a different filename for the class from properties file
- // above should alread by be managed by the custom resource loader
- Map returnVars = [:]
- def script = gcl.loadClass(className, true, false).newInstance();
-
- // hack to get the script manager into test classes
- if (script.respondsTo("setScriptManager")) {
- script.setScriptManager(scriptManager)
- }
-
- returnVars = script.doScript(bindVars);
-
- return returnVars;
- }
-
- public Object getScriptDef(String className) {
- GroovyClassLoader gcl = getGcl();
- try {
- def script = gcl.loadClass(className, true, false).newInstance();
- URL scriptURL = gcl.resourceLoader.loadGroovySource(className)
- setScriptURL(scriptURL)
- return script
- } catch (Exception e) {
- log.warn("Class " + className + " failed to load: " + e.getMessage(), e);
- }
- null
- }
-
- private void mergeParamsWithArgsOBSOLETE(Map<String, Object> bindVars) throws Exception {
- List<String> scriptParams = getScriptArgs(getCannedScript());
- List<String> scriptArgs = getCannedScriptArgs();
- for (int i = 0; i < scriptArgs.size(); i++) {
- bindVars.put(scriptParams.get(i), scriptArgs.get(i));
- }
- }
-
- public List getCannedScripts() {
- getCannedScripts(null)
- }
-
- public List getCannedScripts(String packageName) {
- packageName = packageName ?: "com.onresolve.jira.groovy.canned"
- List a = [];
- GroovyClassLoader gcl = getGcl();
-
- Properties props = scriptManager.getProperties()
-
- Long currentBuildNumber = BuildUtils.getCurrentBuildNumber() as Long
-
- // dev mode only, to get around reloading issues
- // List<String> arrayList = new ArrayList<String>();
- // arrayList.add("com/onresolve/jira/groovy/canned/admin/ExampleBuiltinScript.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/admin/GetUser.groovy");
- /*
- arrayList.add("com/onresolve/jira/groovy/canned/admin/WontCompile.groovy");
- arrayList.add("com/onresolve/jira/groovy/canned/admin/BulkFixResolutions.groovy");
- arrayList.add("com/onresolve/jira/groovy/canned/admin/CopyProject.groovy");
- arrayList.add("com/onresolve/jira/groovy/canned/admin/RunUnitTests.groovy");
- arrayList.add("com/onresolve/jira/groovy/canned/admin/CopyCustomField.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/workflow/conditions/TestCondition.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/workflow/conditions/AllSubtasksResolvedCondition.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/workflow/postfunctions/ResolveParentAfterSubtasks.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/workflow/postfunctions/FireEventWhen.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/workflow/postfunctions/CloneIssue.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/workflow/postfunctions/CreateSubTask.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/workflow/postfunctions/SendCustomEmail.groovy");
- // arrayList.add("com/onresolve/jira/groovy/canned/workflow/postfunctions/FasttrackTransition.groovy");
- log.debug ("class forPackage ($packageName): $arrayList")
- for (String fileName: arrayList) {
- */
-
- // Set<String> forPackage = arrayList;
- Set<String> forPackage = PackageScanner.getClassesForPackage(packageName)
-
- // log.debug ("class forPackage ($packageName): $forPackage")
- for (String fileName : forPackage) {
-
- // CannedScript i/f is in a different classloader so we can't cast
- def scriptDef = null;
- try {
- boolean isValidForVersion
- boolean specificInstructions = false
-
- fileName = fileName.replaceAll(/\.groovy$/, "").replaceAll("/", ".")
- List hasValidVersions = props.collect {
- Matcher matcher = (it.key =~ /${fileName}\.(\d+)\.to\.(\d+)$/)
- if (matcher.matches()) {
- specificInstructions = true
- Long minVersion = matcher[0][1] as Long
- Long maxVersion = matcher[0][2] as Long
-
- return (currentBuildNumber >= minVersion && (maxVersion == 0 || currentBuildNumber <= maxVersion))
- }
- false
- }
-
- isValidForVersion = (!specificInstructions) || hasValidVersions.contains(true)
-
- if (isValidForVersion) {
- // this is slow
- String className = fileName.replaceAll(/\.groovy$/, "").replaceAll("/", ".")
- def clazz = gcl.loadClass(className)
- def cannedScrClazz = gcl.loadClass("com.onresolve.jira.groovy.canned.CannedScript")
- if (clazz.interfaces.toList().contains(cannedScrClazz)) {
- scriptDef = clazz.newInstance()
- a.add(scriptDef);
- }
- }
- else {
- // log.debug ("File $fileName out of range for this build $currentBuildNumber")
- }
-
- } catch (Exception e) {
- log.warn("Class " + fileName + " failed to load: " + e.getMessage(), e);
- }
- }
- return a;
- }
-
- protected void doValidation() {
- // log.debug ("CannedScriptRunner.doValidation");
- }
-
- protected String doExecute() {
-
- ComponentManager.getInstance().getWebResourceManager().requireResource("com.onresolve.jira.groovy.groovyrunner:codemirror");
-
- try {
- Map<String, Object> bindVars = new HashMap<String, Object>();
-
- if (TextUtils.stringSet(getCannedScript())) {
- ServletRequest servletRequest = ServletActionContext.getRequest();
-
- Map paramMap = servletRequest.getParameterMap()
- // log.debug ("keyset: " + paramMap*.key)
-
- Map<String,Object> sortedParams = [:] as Map<String,Object>
- for (String pKey in paramMap*.key) {
- if (pKey.startsWith("cannedScriptArgs_Hidden_")) {
- List p = servletRequest.getParameterValues(pKey).toList()
- sortedParams.put(pKey.replace("cannedScriptArgs_Hidden_", ""), (p.size() < 2 ? p.first() : p))
- }
- }
-
- for (String pKey in paramMap*.key) {
- if (pKey.startsWith("cannedScriptArgs_") && ! pKey.startsWith("cannedScriptArgs_Hidden_")) {
- // log.debug ("Key: $pKey value: " + paramMap.get(pKey))
- List p = servletRequest.getParameterValues(pKey).toList()
- // log.debug("p: $p")
- sortedParams.put(pKey.replace("cannedScriptArgs_", ""), (p.size() < 2 ? p.first() : p))
- }
- }
- // log.debug ("sortedParams: " + sortedParams.sort())
- setCannedScriptArgs(sortedParams);
- // log.debug("CannedScriptArgs: " + getCannedScriptArgs());
-
- if (TextUtils.stringSet(servletRequest.getParameter("Preview"))) {
- setErrorCollection(getValidationErrors(getCannedScript(), getCannedScriptArgs(), true))
- if (errorCollection.hasAnyErrors()) {
- return ERROR
- }
-
- def preview = getCannedScriptHumanDesc(getCannedScript(), getCannedScriptArgs(), true)
- setPreview (preview)
- }
- else if (TextUtils.stringSet(servletRequest.getParameter("Next"))) {
- setErrorCollection(getValidationErrors(getCannedScript(), getCannedScriptArgs(), false))
- if (errorCollection.hasAnyErrors()) {
- return ERROR
- }
- log.debug(getCannedScriptArgs())
- }
- else if (TextUtils.stringSet(servletRequest.getParameter("AddListener"))) {
- setErrorCollection(getValidationErrors(getCannedScript(), getCannedScriptArgs(), false))
- if (errorCollection.hasAnyErrors()) {
- return ERROR
- }
- }
- else if (TextUtils.stringSet(servletRequest.getParameter("RunCanned"))) {
- setErrorCollection(getValidationErrors(getCannedScript(), getCannedScriptArgs(), false))
- if (errorCollection.hasAnyErrors()) {
- return ERROR
- }
-
- // get param values
- // mergeParamsWithArgs(bindVars);
- run(getCannedScript(), getCannedScriptArgs());
- }
- }
- else {
- return SUCCESS;
- }
- } catch (Exception e) {
- result = e.toString();
-
- ByteArrayOutputStream baos = new ByteArrayOutputStream();
- PrintStream ps = new PrintStream(baos);
- e.printStackTrace(ps);
- setScriptExceptionStackTrace(baos.toString("UTF8"));
-
- log.error("The script failed : " + result, e);
- setScriptException(e);
- }
- return SUCCESS;
- }
-
- public void setGcl(GroovyClassLoader gcl) {
- this.gcl = gcl;
- }
-
- public boolean isAdminPanel() {
- return true
- }
-
- public String getPreview() {
- return preview;
- }
-
- public ErrorCollection getErrorCollection() {
- return errorCollection
- }
-
- public boolean getHasErrors() {
- return (errorCollection && errorCollection.getErrorMessages()) as boolean
- }
-
- public ErrorCollection setErrorCollection(ErrorCollection errorCollection) {
- this.errorCollection = errorCollection
- }
-
- public void setPreview(String preview) {
- this.preview = preview;
- }
-
- public static boolean isCannedScript(String s) {
- s.startsWith("com.onresolve.jira.groovy.canned")
- }
-
- public void setScriptURL(URL scriptURL) {
- this.scriptURL = scriptURL
- }
-
- public URL getScriptURL() {
- return this.scriptURL
- }
-
- public ProjectManager getProjectManager() {
- ComponentManager.getInstance().getProjectManager()
- }
-
- public boolean isInStringOrList(what, obj) {
- if (obj instanceof String) {
- what == obj
- }
- else if (obj instanceof List) {
- obj.contains(what)
- }
- else {
- false
- }
- }
- }