diff options
author | Denis Anisimov <denis@vaadin.com> | 2014-09-26 20:44:32 +0300 |
---|---|---|
committer | Sauli Tähkäpää <sauli@vaadin.com> | 2014-10-13 09:54:56 +0300 |
commit | b3de415c25f89b7a23d977caa47bc7fafa3344ed (patch) | |
tree | 1937d24fb57885205fdfe1e684b1b84172ebeb1b /server | |
parent | fbdbd0cf1e078034890fdd75379716648af1706c (diff) | |
download | vaadin-framework-b3de415c25f89b7a23d977caa47bc7fafa3344ed.tar.gz vaadin-framework-b3de415c25f89b7a23d977caa47bc7fafa3344ed.zip |
Read input stream logic is corrected (#14533).
Change-Id: I1a8a895d631889e04f7acbde29306e86da344a23
Diffstat (limited to 'server')
-rw-r--r-- | server/src/com/vaadin/ui/CustomLayout.java | 25 | ||||
-rw-r--r-- | server/tests/src/com/vaadin/tests/server/component/customlayout/CustomLayoutTest.java | 148 |
2 files changed, 160 insertions, 13 deletions
diff --git a/server/src/com/vaadin/ui/CustomLayout.java b/server/src/com/vaadin/ui/CustomLayout.java index 7f1aa1ce46..f4fe7fa66c 100644 --- a/server/src/com/vaadin/ui/CustomLayout.java +++ b/server/src/com/vaadin/ui/CustomLayout.java @@ -16,6 +16,7 @@ package com.vaadin.ui; +import java.io.BufferedReader; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; @@ -101,22 +102,20 @@ public class CustomLayout extends AbstractLayout implements LegacyComponent { protected void initTemplateContentsFromInputStream( InputStream templateStream) throws IOException { - InputStreamReader reader = new InputStreamReader(templateStream, - "UTF-8"); - StringBuilder b = new StringBuilder(BUFFER_SIZE); - - char[] cbuf = new char[BUFFER_SIZE]; - int offset = 0; - - while (true) { - int nrRead = reader.read(cbuf, offset, BUFFER_SIZE); - b.append(cbuf, 0, nrRead); - if (nrRead < BUFFER_SIZE) { - break; + BufferedReader reader = new BufferedReader(new InputStreamReader( + templateStream, "UTF-8")); + StringBuilder builder = new StringBuilder(BUFFER_SIZE); + try { + char[] cbuf = new char[BUFFER_SIZE]; + int nRead; + while ((nRead = reader.read(cbuf, 0, BUFFER_SIZE)) > 0) { + builder.append(cbuf, 0, nRead); } + } finally { + reader.close(); } - setTemplateContents(b.toString()); + setTemplateContents(builder.toString()); } @Override diff --git a/server/tests/src/com/vaadin/tests/server/component/customlayout/CustomLayoutTest.java b/server/tests/src/com/vaadin/tests/server/component/customlayout/CustomLayoutTest.java new file mode 100644 index 0000000000..4d327e70a6 --- /dev/null +++ b/server/tests/src/com/vaadin/tests/server/component/customlayout/CustomLayoutTest.java @@ -0,0 +1,148 @@ +/* + * Copyright 2000-2014 Vaadin Ltd. + * + * Licensed 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 com.vaadin.tests.server.component.customlayout; + +import java.io.ByteArrayInputStream; +import java.io.FilterInputStream; +import java.io.IOException; +import java.io.InputStream; +import java.lang.reflect.Field; +import java.lang.reflect.Modifier; +import java.nio.charset.Charset; +import java.util.ArrayList; +import java.util.List; +import java.util.Locale; + +import org.junit.Assert; +import org.junit.Test; + +import com.vaadin.ui.CustomLayout; + +/** + * + * Tests for {@link CustomLayout} + * + * @author Vaadin Ltd + */ +public class CustomLayoutTest { + + @Test + public void ctor_inputStreamProvided_inputStreamIsRead() + throws IOException, IllegalArgumentException, + IllegalAccessException { + Integer buffer = getBufferSize(); + StringBuilder builder = new StringBuilder(); + for (int i = 0; i < buffer; i++) { + builder.append('a'); + } + byte[] bytes = builder.toString().getBytes(Charset.forName("UTF-8")); + ByteArrayInputStream inputStream = new ByteArrayInputStream(bytes); + InputStreamImpl stream = new InputStreamImpl(inputStream, buffer / 2); + new CustomLayout(stream); + + Assert.assertTrue("Stream is not closed in CustomLayout CTOR ", + stream.isClosed()); + Assert.assertEquals("Number of read bytes is incorrect", bytes.length, + stream.getCount()); + } + + private Integer getBufferSize() throws IllegalAccessException { + Field[] fields = CustomLayout.class.getDeclaredFields(); + List<Field> list = new ArrayList<Field>(fields.length); + for (Field field : fields) { + if ((field.getModifiers() & Modifier.STATIC) > 0) { + list.add(field); + } + } + Field field = null; + if (list.size() == 1) { + field = list.get(0); + } else { + for (Field fld : list) { + if (fld.getName().toLowerCase(Locale.ENGLISH) + .startsWith("buffer")) { + field = fld; + break; + } + } + } + Assert.assertNotNull( + "Unable to find default buffer size in CustomLayout class", + field); + field.setAccessible(true); + Integer buffer = (Integer) field.get(null); + return buffer; + } + + private static class InputStreamImpl extends FilterInputStream { + + InputStreamImpl(InputStream inputStream, int maxArrayLength) { + super(inputStream); + this.maxArrayLength = maxArrayLength; + } + + @Override + public int read() throws IOException { + int read = super.read(); + if (read != -1) { + readCount++; + } + return read; + } + + @Override + public int read(byte[] b) throws IOException { + if (b.length > maxArrayLength) { + return read(b, 0, maxArrayLength); + } + int count = super.read(b); + if (count != -1) { + readCount += count; + } + return count; + } + + @Override + public int read(byte[] b, int off, int len) throws IOException { + if (len > maxArrayLength) { + return read(b, off, maxArrayLength); + } + int count = super.read(b, off, len); + if (count != -1) { + readCount += count; + } + return count; + } + + @Override + public void close() throws IOException { + isClosed = true; + super.close(); + } + + int getCount() { + return readCount; + } + + boolean isClosed() { + return isClosed; + } + + private int readCount; + private boolean isClosed; + private int maxArrayLength; + } +} |