/** * Copyright (c) Codice Foundation * <p> * This is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser * General Public License as published by the Free Software Foundation, either version 3 of the * License, or any later version. * <p> * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without * even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. A copy of the GNU Lesser General Public License * is distributed along with this program and can be found at * <http://www.gnu.org/licenses/lgpl.html>. */ package org.codice.ddf.security.common.jaxrs; import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.core.Is.is; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertNotSame; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import static org.mockito.Mockito.mock; import static org.mockito.Mockito.when; import java.io.ByteArrayInputStream; import java.io.IOException; import java.io.InputStream; import java.util.ArrayList; import java.util.Date; import java.util.UUID; import java.util.zip.Inflater; import java.util.zip.InflaterInputStream; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import javax.xml.parsers.ParserConfigurationException; import org.apache.commons.lang.StringUtils; import org.apache.cxf.helpers.DOMUtils; import org.apache.cxf.helpers.IOUtils; import org.apache.cxf.jaxrs.client.WebClient; import org.apache.cxf.rs.security.saml.DeflateEncoderDecoder; import org.apache.cxf.ws.security.tokenstore.SecurityToken; import org.apache.shiro.subject.SimplePrincipalCollection; import org.junit.Test; import org.w3c.dom.Document; import org.w3c.dom.Element; import org.xml.sax.SAXException; import ddf.security.Subject; import ddf.security.assertion.SecurityAssertion; public class RestSecurityTest { public static Document readXml(InputStream is) throws SAXException, IOException, ParserConfigurationException { DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance(); dbf.setValidating(false); dbf.setIgnoringComments(false); dbf.setIgnoringElementContentWhitespace(true); dbf.setNamespaceAware(true); // dbf.setCoalescing(true); // dbf.setExpandEntityReferences(true); DocumentBuilder db = null; db = dbf.newDocumentBuilder(); db.setEntityResolver(new DOMUtils.NullResolver()); // db.setErrorHandler( new MyErrorHandler()); return db.parse(is); } @Test public void testSetSubjectOnClient() throws Exception { Element samlToken = readDocument("/saml.xml").getDocumentElement(); Subject subject = mock(Subject.class); SecurityAssertion assertion = mock(SecurityAssertion.class); SecurityToken token = new SecurityToken(UUID.randomUUID() .toString(), samlToken, new Date(), new Date()); when(assertion.getSecurityToken()).thenReturn(token); when(subject.getPrincipals()).thenReturn(new SimplePrincipalCollection(assertion, "sts")); WebClient client = WebClient.create("https://example.org"); RestSecurity.setSubjectOnClient(subject, client); assertNotNull(client.getHeaders() .get(RestSecurity.AUTH_HEADER)); ArrayList headers = (ArrayList) client.getHeaders() .get(RestSecurity.AUTH_HEADER); boolean containsSaml = false; for (Object header : headers) { if (StringUtils.contains(header.toString(), RestSecurity.SAML_HEADER_PREFIX)) { containsSaml = true; } } assertTrue(containsSaml); } @Test public void testNotSetSubjectOnClient() throws Exception { Element samlToken = readDocument("/saml.xml").getDocumentElement(); Subject subject = mock(Subject.class); SecurityAssertion assertion = mock(SecurityAssertion.class); SecurityToken token = new SecurityToken(UUID.randomUUID() .toString(), samlToken, new Date(), new Date()); when(assertion.getSecurityToken()).thenReturn(token); when(subject.getPrincipals()).thenReturn(new SimplePrincipalCollection(assertion, "sts")); WebClient client = WebClient.create("http://example.org"); RestSecurity.setSubjectOnClient(subject, client); assertNull(client.getHeaders() .get(RestSecurity.AUTH_HEADER)); } @Test public void testInflateDeflateWithTokenDuplication() throws Exception { String token = "valid_grant valid_grant valid_grant valid_grant valid_grant valid_grant"; DeflateEncoderDecoder deflateEncoderDecoder = new DeflateEncoderDecoder(); byte[] deflatedToken = deflateEncoderDecoder.deflateToken(token.getBytes()); String cxfInflatedToken = IOUtils.toString(deflateEncoderDecoder.inflateToken(deflatedToken)); String streamInflatedToken = IOUtils.toString(new InflaterInputStream(new ByteArrayInputStream(deflatedToken), new Inflater(true))); assertNotSame(cxfInflatedToken, token); assertEquals(streamInflatedToken, token); } @Test public void testInflateDeflate() throws Exception { String token = "valid_grant"; String encodedToken = RestSecurity.deflateAndBase64Encode(token); String decodedToken = RestSecurity.inflateBase64(encodedToken); assertThat(decodedToken, is(token)); } /** * Reads a classpath resource into a Document. * * @param name the name of the classpath resource */ private Document readDocument(String name) throws SAXException, IOException, ParserConfigurationException { InputStream inStream = getClass().getResourceAsStream(name); return readXml(inStream); } }