/* * Licensed to Elasticsearch under one or more contributor * license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright * ownership. Elasticsearch licenses this file to you under * the Apache License, Version 2.0 (the "License"); you may * not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, * software distributed under the License is distributed on an * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY * KIND, either express or implied. See the License for the * specific language governing permissions and limitations * under the License. */ package org.elasticsearch.rest; import com.carrotsearch.randomizedtesting.generators.CodepointSetGenerator; import org.elasticsearch.client.node.NodeClient; import org.elasticsearch.common.logging.DeprecationLogger; import org.elasticsearch.test.ESTestCase; import org.mockito.InOrder; import static org.mockito.Mockito.inOrder; import static org.mockito.Mockito.mock; /** * Tests {@link DeprecationRestHandler}. */ public class DeprecationRestHandlerTests extends ESTestCase { private final RestHandler handler = mock(RestHandler.class); /** * Note: Headers should only use US ASCII (and this inevitably becomes one!). */ private final String deprecationMessage = randomAlphaOfLengthBetween(1, 30); private final DeprecationLogger deprecationLogger = mock(DeprecationLogger.class); public void testNullHandler() { expectThrows(NullPointerException.class, () -> new DeprecationRestHandler(null, deprecationMessage, deprecationLogger)); } public void testInvalidDeprecationMessageThrowsException() { String invalidDeprecationMessage = randomFrom("", null, " "); expectThrows(IllegalArgumentException.class, () -> new DeprecationRestHandler(handler, invalidDeprecationMessage, deprecationLogger)); } public void testNullDeprecationLogger() { expectThrows(NullPointerException.class, () -> new DeprecationRestHandler(handler, deprecationMessage, null)); } public void testHandleRequestLogsWarningThenForwards() throws Exception { RestRequest request = mock(RestRequest.class); RestChannel channel = mock(RestChannel.class); NodeClient client = mock(NodeClient.class); DeprecationRestHandler deprecatedHandler = new DeprecationRestHandler(handler, deprecationMessage, deprecationLogger); // test it deprecatedHandler.handleRequest(request, channel, client); InOrder inOrder = inOrder(handler, request, channel, deprecationLogger); // log, then forward inOrder.verify(deprecationLogger).deprecated(deprecationMessage); inOrder.verify(handler).handleRequest(request, channel, client); inOrder.verifyNoMoreInteractions(); } public void testValidHeaderValue() { ASCIIHeaderGenerator generator = new ASCIIHeaderGenerator(); String value = generator.ofCodeUnitsLength(random(), 1, 50); if (value.trim().length() == 0) { // empty text, not a valid header assertFalse(DeprecationRestHandler.validHeaderValue(value)); Exception e = expectThrows(IllegalArgumentException.class, () -> DeprecationRestHandler.requireValidHeader(value)); assertEquals("header value must contain only US ASCII text", e.getMessage()); } else { assertTrue(DeprecationRestHandler.validHeaderValue(value)); assertSame(value, DeprecationRestHandler.requireValidHeader(value)); } } public void testInvalidHeaderValue() { ASCIIHeaderGenerator generator = new ASCIIHeaderGenerator(); String value = generator.ofCodeUnitsLength(random(), 0, 25) + randomFrom('\t', '\0', '\n', (char)27 /* ESC */, (char)31 /* unit separator*/, (char)127 /* DEL */) + generator.ofCodeUnitsLength(random(), 0, 25); assertFalse(DeprecationRestHandler.validHeaderValue(value)); expectThrows(IllegalArgumentException.class, () -> DeprecationRestHandler.requireValidHeader(value)); } public void testInvalidHeaderValueNull() { assertFalse(DeprecationRestHandler.validHeaderValue(null)); expectThrows(IllegalArgumentException.class, () -> DeprecationRestHandler.requireValidHeader(null)); } public void testInvalidHeaderValueEmpty() { String blank = randomFrom("", "\t", " "); assertFalse(DeprecationRestHandler.validHeaderValue(blank)); expectThrows(IllegalArgumentException.class, () -> DeprecationRestHandler.requireValidHeader(blank)); } /** * {@code ASCIIHeaderGenerator} only uses characters expected to be valid in headers (simplified US-ASCII). */ private static class ASCIIHeaderGenerator extends CodepointSetGenerator { /** * Create a character array for characters [{@code from}, {@code to}]. * * @param from Starting code point (inclusive). * @param to Ending code point (inclusive). * @return Never {@code null}. */ static char[] asciiFromTo(int from, int to) { char[] chars = new char[to - from + 1]; for (int i = from; i <= to; ++i) { chars[i - from] = (char)i; } return chars; } /** * Create a generator for characters [32, 126]. */ ASCIIHeaderGenerator() { super(asciiFromTo(32, 126)); } } }