PageRenderTime 26ms CodeModel.GetById 26ms RepoModel.GetById 1ms app.codeStats 0ms

/trunk/org.mwc.asset.comms/docs/restlet_src/org.restlet/org/restlet/engine/application/EncodeRepresentation.java

https://bitbucket.org/haris_peco/debrief
Java | 326 lines | 185 code | 36 blank | 105 comment | 45 complexity | 5b5906cf3e0cdd83a3a17d42e2f03559 MD5 | raw file
  1. /**
  2. * Copyright 2005-2010 Noelios Technologies.
  3. *
  4. * The contents of this file are subject to the terms of one of the following
  5. * open source licenses: LGPL 3.0 or LGPL 2.1 or CDDL 1.0 or EPL 1.0 (the
  6. * "Licenses"). You can select the license that you prefer but you may not use
  7. * this file except in compliance with one of these Licenses.
  8. *
  9. * You can obtain a copy of the LGPL 3.0 license at
  10. * http://www.opensource.org/licenses/lgpl-3.0.html
  11. *
  12. * You can obtain a copy of the LGPL 2.1 license at
  13. * http://www.opensource.org/licenses/lgpl-2.1.php
  14. *
  15. * You can obtain a copy of the CDDL 1.0 license at
  16. * http://www.opensource.org/licenses/cddl1.php
  17. *
  18. * You can obtain a copy of the EPL 1.0 license at
  19. * http://www.opensource.org/licenses/eclipse-1.0.php
  20. *
  21. * See the Licenses for the specific language governing permissions and
  22. * limitations under the Licenses.
  23. *
  24. * Alternatively, you can obtain a royalty free commercial license with less
  25. * limitations, transferable or non-transferable, directly at
  26. * http://www.noelios.com/products/restlet-engine
  27. *
  28. * Restlet is a registered trademark of Noelios Technologies.
  29. */
  30. package org.restlet.engine.application;
  31. import java.io.IOException;
  32. import java.io.InputStream;
  33. import java.io.OutputStream;
  34. import java.nio.channels.ReadableByteChannel;
  35. import java.nio.channels.WritableByteChannel;
  36. import java.util.Arrays;
  37. import java.util.Collection;
  38. import java.util.Iterator;
  39. import java.util.List;
  40. import java.util.zip.DeflaterOutputStream;
  41. import java.util.zip.GZIPOutputStream;
  42. import java.util.zip.ZipEntry;
  43. import java.util.zip.ZipOutputStream;
  44. import org.restlet.data.Disposition;
  45. import org.restlet.data.Encoding;
  46. import org.restlet.engine.io.BioUtils;
  47. import org.restlet.engine.io.NioUtils;
  48. import org.restlet.representation.Representation;
  49. import org.restlet.util.WrapperList;
  50. import org.restlet.util.WrapperRepresentation;
  51. // [excludes gwt]
  52. /**
  53. * Content that encodes a wrapped content. Allows to apply only one encoding.
  54. *
  55. * @author Jerome Louvel
  56. */
  57. public class EncodeRepresentation extends WrapperRepresentation {
  58. /**
  59. * Returns the list of supported encodings.
  60. *
  61. * @return The list of supported encodings.
  62. */
  63. public static List<Encoding> getSupportedEncodings() {
  64. return Arrays.<Encoding> asList(Encoding.GZIP, Encoding.DEFLATE,
  65. Encoding.ZIP, Encoding.IDENTITY);
  66. }
  67. /** Indicates if the encoding can happen. */
  68. private volatile boolean canEncode;
  69. /** The encoding to apply. */
  70. private volatile Encoding encoding;
  71. /** The applied encodings. */
  72. private volatile List<Encoding> encodings;
  73. /**
  74. * Constructor.
  75. *
  76. * @param encoding
  77. * Encoder algorithm.
  78. * @param wrappedRepresentation
  79. * The wrapped representation.
  80. */
  81. public EncodeRepresentation(Encoding encoding,
  82. Representation wrappedRepresentation) {
  83. super(wrappedRepresentation);
  84. this.canEncode = getSupportedEncodings().contains(encoding);
  85. this.encodings = null;
  86. this.encoding = encoding;
  87. }
  88. /**
  89. * Indicates if the encoding can happen.
  90. *
  91. * @return True if the encoding can happen.
  92. */
  93. public boolean canEncode() {
  94. return this.canEncode;
  95. }
  96. /**
  97. * Returns the available size in bytes of the encoded representation if
  98. * known, UNKNOWN_SIZE (-1) otherwise.
  99. *
  100. * @return The available size in bytes if known, UNKNOWN_SIZE (-1)
  101. * otherwise.
  102. */
  103. @Override
  104. public long getAvailableSize() {
  105. long result = UNKNOWN_SIZE;
  106. if (canEncode()) {
  107. if (this.encoding.equals(Encoding.IDENTITY)) {
  108. result = getWrappedRepresentation().getAvailableSize();
  109. }
  110. } else {
  111. result = getWrappedRepresentation().getAvailableSize();
  112. }
  113. return result;
  114. }
  115. /**
  116. * Returns a readable byte channel. If it is supported by a file a read-only
  117. * instance of FileChannel is returned.
  118. *
  119. * @return A readable byte channel.
  120. */
  121. @Override
  122. public ReadableByteChannel getChannel() throws IOException {
  123. if (canEncode()) {
  124. return NioUtils.getChannel(getStream());
  125. }
  126. return getWrappedRepresentation().getChannel();
  127. }
  128. /**
  129. * Returns the applied encodings.
  130. *
  131. * @return The applied encodings.
  132. */
  133. @Override
  134. public List<Encoding> getEncodings() {
  135. if (this.encodings == null) {
  136. this.encodings = new WrapperList<Encoding>() {
  137. @Override
  138. public boolean add(Encoding element) {
  139. if (element == null) {
  140. throw new IllegalArgumentException(
  141. "Cannot add a null encoding.");
  142. }
  143. return super.add(element);
  144. }
  145. @Override
  146. public void add(int index, Encoding element) {
  147. if (element == null) {
  148. throw new IllegalArgumentException(
  149. "Cannot add a null encoding.");
  150. }
  151. super.add(index, element);
  152. }
  153. @Override
  154. public boolean addAll(Collection<? extends Encoding> elements) {
  155. boolean addNull = (elements == null);
  156. if (!addNull) {
  157. for (final Iterator<? extends Encoding> iterator = elements
  158. .iterator(); !addNull && iterator.hasNext();) {
  159. addNull = (iterator.next() == null);
  160. }
  161. }
  162. if (addNull) {
  163. throw new IllegalArgumentException(
  164. "Cannot add a null encoding.");
  165. }
  166. return super.addAll(elements);
  167. }
  168. @Override
  169. public boolean addAll(int index,
  170. Collection<? extends Encoding> elements) {
  171. boolean addNull = (elements == null);
  172. if (!addNull) {
  173. for (final Iterator<? extends Encoding> iterator = elements
  174. .iterator(); !addNull && iterator.hasNext();) {
  175. addNull = (iterator.next() == null);
  176. }
  177. }
  178. if (addNull) {
  179. throw new IllegalArgumentException(
  180. "Cannot add a null encoding.");
  181. }
  182. return super.addAll(index, elements);
  183. }
  184. };
  185. this.encodings.addAll(getWrappedRepresentation().getEncodings());
  186. if (canEncode()) {
  187. this.encodings.add(this.encoding);
  188. }
  189. }
  190. return this.encodings;
  191. }
  192. /**
  193. * Returns the size in bytes of the encoded representation if known,
  194. * UNKNOWN_SIZE (-1) otherwise.
  195. *
  196. * @return The size in bytes if known, UNKNOWN_SIZE (-1) otherwise.
  197. */
  198. @Override
  199. public long getSize() {
  200. long result = UNKNOWN_SIZE;
  201. if (canEncode()) {
  202. if (this.encoding.equals(Encoding.IDENTITY)) {
  203. result = getWrappedRepresentation().getSize();
  204. }
  205. } else {
  206. result = getWrappedRepresentation().getSize();
  207. }
  208. return result;
  209. }
  210. /**
  211. * Returns a stream with the representation's content.
  212. *
  213. * @return A stream with the representation's content.
  214. */
  215. @Override
  216. public InputStream getStream() throws IOException {
  217. if (canEncode()) {
  218. return BioUtils.getStream(this);
  219. }
  220. return getWrappedRepresentation().getStream();
  221. }
  222. /**
  223. * Converts the representation to a string value. Be careful when using this
  224. * method as the conversion of large content to a string fully stored in
  225. * memory can result in OutOfMemoryErrors being thrown.
  226. *
  227. * @return The representation as a string value.
  228. */
  229. @Override
  230. public String getText() throws IOException {
  231. String result = null;
  232. if (canEncode()) {
  233. result = BioUtils.toString(getStream(), getCharacterSet());
  234. } else {
  235. result = getWrappedRepresentation().getText();
  236. }
  237. return result;
  238. }
  239. /**
  240. * Writes the representation to a byte stream.
  241. *
  242. * @param outputStream
  243. * The output stream.
  244. */
  245. @Override
  246. public void write(OutputStream outputStream) throws IOException {
  247. if (canEncode()) {
  248. DeflaterOutputStream encoderOutputStream = null;
  249. if (this.encoding.equals(Encoding.GZIP)) {
  250. encoderOutputStream = new GZIPOutputStream(outputStream);
  251. } else if (this.encoding.equals(Encoding.DEFLATE)) {
  252. encoderOutputStream = new DeflaterOutputStream(outputStream);
  253. } else if (this.encoding.equals(Encoding.ZIP)) {
  254. final ZipOutputStream stream = new ZipOutputStream(outputStream);
  255. String name = "entry";
  256. if (getWrappedRepresentation().getDisposition() != null) {
  257. name = getWrappedRepresentation().getDisposition()
  258. .getParameters().getFirstValue(
  259. Disposition.NAME_FILENAME, true, name);
  260. }
  261. stream.putNextEntry(new ZipEntry(name));
  262. encoderOutputStream = stream;
  263. } else if (this.encoding.equals(Encoding.IDENTITY)) {
  264. // Encoder unnecessary for identity encoding
  265. }
  266. if (encoderOutputStream != null) {
  267. getWrappedRepresentation().write(encoderOutputStream);
  268. encoderOutputStream.finish();
  269. } else {
  270. getWrappedRepresentation().write(outputStream);
  271. }
  272. } else {
  273. getWrappedRepresentation().write(outputStream);
  274. }
  275. }
  276. /**
  277. * Writes the representation to a byte channel.
  278. *
  279. * @param writableChannel
  280. * A writable byte channel.
  281. */
  282. @Override
  283. public void write(WritableByteChannel writableChannel) throws IOException {
  284. if (canEncode()) {
  285. write(NioUtils.getStream(writableChannel));
  286. } else {
  287. getWrappedRepresentation().write(writableChannel);
  288. }
  289. }
  290. }