package hudson.plugins.jira;

import hudson.Extension;
import hudson.model.AbstractProject;
import hudson.model.Job;
import hudson.model.JobProperty;
import hudson.model.JobPropertyDescriptor;
import hudson.util.CopyOnWriteList;
import net.sf.json.JSONObject;
import org.kohsuke.stapler.DataBoundConstructor;
import org.kohsuke.stapler.StaplerRequest;

import java.util.logging.Logger;

/**
 * Associates {@link AbstractProject} with {@link JiraSite}.
 * 
 * @author Kohsuke Kawaguchi 
 */
public class JiraProjectProperty extends JobProperty<AbstractProject<?, ?>> {

	/**
	 * Used to find {@link JiraSite}. Matches {@link JiraSite#getName()}. Always
	 * non-null (but beware that this value might become stale if the system
	 * config is changed.)
	 */
	public final String siteName;

	@DataBoundConstructor
	public JiraProjectProperty(String siteName) {
		if (siteName == null) {
			// defaults to the first one
			JiraSite[] sites = DESCRIPTOR.getSites();
			if (sites.length > 0)
				siteName = sites[0].getName();
		}
		this.siteName = siteName;
	}

	/**
	 * Gets the {@link JiraSite} that this project belongs to.
	 * 
	 * @return null if the configuration becomes out of sync.
	 */
	public JiraSite getSite() {
		JiraSite[] sites = DESCRIPTOR.getSites();
		if (siteName == null && sites.length > 0)
			// default
			return sites[0];

		for (JiraSite site : sites) {
			if (site.getName().equals(siteName))
				return site;
		}
		return null;
	}

	@Override
	public DescriptorImpl getDescriptor() {
		return DESCRIPTOR;
	}

	@Extension
	public static final DescriptorImpl DESCRIPTOR = new DescriptorImpl();

	public static final class DescriptorImpl extends JobPropertyDescriptor {
		private final CopyOnWriteList<JiraSite> sites = new CopyOnWriteList<JiraSite>();

		public DescriptorImpl() {
			super(JiraProjectProperty.class);
			load();
		}

		@Override
		@SuppressWarnings("unchecked")
		public boolean isApplicable(Class<? extends Job> jobType) {
			return AbstractProject.class.isAssignableFrom(jobType);
		}

		@Override
		public String getDisplayName() {
			return Messages.JiraProjectProperty_DisplayName();
		}

		public void setSites(JiraSite site) {
			sites.add(site);
		}

		public JiraSite[] getSites() {
			return sites.toArray(new JiraSite[0]);
		}

		@Override
		public JobProperty<?> newInstance(StaplerRequest req, JSONObject formData)
				throws FormException {
			JiraProjectProperty jpp = req.bindParameters(
					JiraProjectProperty.class, "jira.");
			if (jpp.siteName == null)
				jpp = null; // not configured
			return jpp;
		}

		@Override
		public boolean configure(StaplerRequest req, JSONObject formData) {
			sites.replaceBy(req.bindJSONToList(JiraSite.class, formData.get("sites")));
			save();
			return true;
		}
	}

	private static final Logger LOGGER = Logger
			.getLogger(JiraProjectProperty.class.getName());
}

@@ -249,24 +249,71 @@
 JSONObject;%0A
+import org.apache.commons.beanutils.Converter;%0A
 import org.k
@@ -387,17 +387,113 @@
 pler
-Request;%0A
+;%0Aimport org.kohsuke.stapler.StaplerRequest;%0A%0Aimport java.net.MalformedURLException;%0Aimport java.net.URL;
 %0Aimp
@@ -2780,27 +2780,833 @@
 formData) %7B%0A
-%09%09%09
+            //Fix%5EH%5EH%5EHDirty hack for empty string to URL conversion error%0A            Stapler.CONVERT_UTILS.deregister(java.net.URL.class);%0A            Converter tmpUrlConverter = new Converter() %7B%0A                public Object convert(Class aClass, Object o) %7B%0A                    if(o == null %7C%7C %22%22.equals(o) %7C%7C %22null%22.equals(o)) return null;%0A                    try %7B%0A                        return new URL((String) o);%0A                    %7D catch (MalformedURLException e) %7B%0A                        e.printStackTrace();  //To change body of catch statement use File %7C Settings %7C File Templates.%0A                        return null;%0A                    %7D%0A                %7D%0A            %7D;%0A            Stapler.CONVERT_UTILS.register(tmpUrlConverter, java.net.URL.class);%0A            //End hack%0A%0A            
 sites.replac

Add hack to get around the "" -> java.net.URL exception (JENKINS-18229)