1 /* 2 * Licensed to the Apache Software Foundation (ASF) under one 3 * or more contributor license agreements. See the NOTICE file 4 * distributed with this work for additional information 5 * regarding copyright ownership. The ASF licenses this file 6 * to you under the Apache License, Version 2.0 (the 7 * "License"); you may not use this file except in compliance 8 * with the License. You may obtain a copy of the License at 9 * 10 * https://www.apache.org/licenses/LICENSE-2.0 11 * 12 * Unless required by applicable law or agreed to in writing, 13 * software distributed under the License is distributed on an 14 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 15 * KIND, either express or implied. See the License for the 16 * specific language governing permissions and limitations 17 * under the License. 18 */ 19 package org.apache.commons.compress.archivers.sevenz; 20 21 import java.io.IOException; 22 import java.io.InputStream; 23 import java.io.OutputStream; 24 import java.util.Objects; 25 import java.util.stream.Stream; 26 27 import org.apache.commons.compress.utils.ByteUtils; 28 29 /** 30 * Abstracts a base Codec class. 31 */ 32 abstract class AbstractCoder { 33 34 /** 35 * If the option represents a number, return its integer value, otherwise return the given default value. 36 * 37 * @param options A Number. 38 * @param defaultValue A default value if options is not a number. 39 * @return The given number or default value. 40 */ 41 protected static int toInt(final Object options, final int defaultValue) { 42 return options instanceof Number ? ((Number) options).intValue() : defaultValue; 43 } 44 45 private final Class<?>[] optionClasses; 46 47 /** 48 * Constructs a new instance. 49 * 50 * @param optionClasses types that can be used as options for this codec. 51 */ 52 protected AbstractCoder(final Class<?>... optionClasses) { 53 this.optionClasses = Objects.requireNonNull(optionClasses, "optionClasses"); 54 } 55 56 /** 57 * Decodes using stream that reads from in using the configured coder and password. 58 * 59 * @return a stream that reads from in using the configured coder and password. 60 */ 61 abstract InputStream decode(String archiveName, InputStream in, long uncompressedLength, Coder coder, byte[] password, int maxMemoryLimitKiB) 62 throws IOException; 63 64 /** 65 * Encodes using a stream that writes to out using the given configuration. 66 * 67 * @return a stream that writes to out using the given configuration. 68 * @throws IOException Optionally thrown by subclassses. 69 */ 70 OutputStream encode(final OutputStream out, final Object options) throws IOException { 71 throw new UnsupportedOperationException("Method doesn't support writing"); 72 } 73 74 /** 75 * Gets property bytes to write in a Folder block. 76 * 77 * @return property bytes to write in a Folder block. 78 * @throws IOException Optionally thrown by subclassses. 79 */ 80 byte[] getOptionsAsProperties(final Object options) throws IOException { 81 return ByteUtils.EMPTY_BYTE_ARRAY; 82 } 83 84 /** 85 * Gets configuration options that have been used to create the given InputStream from the given Coder. 86 * 87 * @return configuration options that have been used to create the given InputStream from the given Coder 88 * @throws IOException Optionally thrown by subclassses. 89 */ 90 Object getOptionsFromCoder(final Coder coder, final InputStream in) throws IOException { 91 return null; 92 } 93 94 /** 95 * Tests whether this method can extract options from the given object. 96 * 97 * @return whether this method can extract options from the given object. 98 */ 99 boolean isOptionInstance(final Object opts) { 100 return Stream.of(optionClasses).anyMatch(c -> c.isInstance(opts)); 101 } 102 }