Skip to content

Commit

Permalink
Merge pull request #114 from lanwen/xss
Browse files Browse the repository at this point in the history
prevent JS in link to github
  • Loading branch information
lanwen committed Mar 17, 2016
2 parents 44a8781 + 12aaa78 commit b61b10d
Show file tree
Hide file tree
Showing 3 changed files with 86 additions and 4 deletions.
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
package com.coravy.hudson.plugins.github;

import java.util.Collection;
import java.util.Collections;

import hudson.Extension;
import hudson.model.Action;
import hudson.model.Job;
import jenkins.model.TransientActionFactory;
import org.jenkinsci.plugins.github.util.XSSApi;

import java.util.Collection;
import java.util.Collections;

/**
* Add the Github Logo/Icon to the sidebar.
Expand All @@ -33,7 +34,7 @@ public String getIconFileName() {

@Override
public String getUrlName() {
return projectProperty.getProjectUrl().baseUrl();
return XSSApi.asValidHref(projectProperty.getProjectUrl().baseUrl());
}

@SuppressWarnings("rawtypes")
Expand Down
36 changes: 36 additions & 0 deletions src/main/java/org/jenkinsci/plugins/github/util/XSSApi.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
package org.jenkinsci.plugins.github.util;

import org.kohsuke.accmod.Restricted;
import org.kohsuke.accmod.restrictions.NoExternalUse;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.net.MalformedURLException;
import java.net.URL;

/**
* @author lanwen (Merkushev Kirill)
*/
@Restricted(NoExternalUse.class)
public final class XSSApi {
private static final Logger LOG = LoggerFactory.getLogger(XSSApi.class);

private XSSApi() {
}

/**
* Method to filter invalid url for XSS. This url can be inserted to href safely
*
* @param urlString unsafe url
*
* @return safe url
*/
public static String asValidHref(String urlString) {
try {
return new URL(urlString).toExternalForm();
} catch (MalformedURLException e) {
LOG.debug("Malformed url - {}, empty string will be returned", urlString);
return "";
}
}
}
45 changes: 45 additions & 0 deletions src/test/java/org/jenkinsci/plugins/github/util/XSSApiTest.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
package org.jenkinsci.plugins.github.util;

import com.tngtech.java.junit.dataprovider.DataProvider;
import com.tngtech.java.junit.dataprovider.DataProviderRunner;
import com.tngtech.java.junit.dataprovider.UseDataProvider;
import org.junit.Test;
import org.junit.runner.RunWith;

import static java.lang.String.format;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.is;

/**
* @author lanwen (Merkushev Kirill)
*/
@RunWith(DataProviderRunner.class)
public class XSSApiTest {

@DataProvider
public static Object[][] links() {
return new Object[][]{
new Object[]{"javascript:alert(1);//", ""},
new Object[]{"javascript:alert(1)://", ""},
new Object[]{"http://abcxyz.com?a=b&c=d';alert(1);//", "http://abcxyz.com?a=b&c=d';alert(1);//"},
new Object[]{"http://github.com/bla/bla", "http://github.com/bla/bla"},
new Object[]{"https://github.com/bla/bla", "https://github.com/bla/bla"},
new Object[]{"https://company.com/bla", "https://company.com/bla"},
new Object[]{"/company.com/bla", ""},
new Object[]{"//", ""},
new Object[]{"//text", ""},
new Object[]{"//text/", ""},
new Object[]{"ftp://", "ftp:"},
new Object[]{"ftp://a", "ftp://a"},
new Object[]{"text", ""},
new Object[]{"github.com/bla/bla", ""},
new Object[]{"http://127.0.0.1/", "http://127.0.0.1/"},
};
}

@Test
@UseDataProvider("links")
public void shouldSanitizeUrl(String url, String expected) throws Exception {
assertThat(format("For %s", url), XSSApi.asValidHref(url), is(expected));
}
}

0 comments on commit b61b10d

Please sign in to comment.