001package org.unix4j.unix.tail;
002
003import java.util.Collections;
004import java.util.Iterator;
005
006import org.unix4j.convert.OptionSetConverters.OptionSetConverter;
007import org.unix4j.convert.ValueConverter;
008import org.unix4j.option.DefaultOptionSet;
009import org.unix4j.option.Option;
010import org.unix4j.option.OptionSet;
011
012import org.unix4j.unix.Tail;
013import org.unix4j.unix.tail.TailOption;
014
015/**
016 * Interface implemented by all option sets for the {@link Tail tail} command.
017 * It is recommended to use {@link Tail#Options} to specify a valid 
018 * combination of options.
019 * <p>
020 * The options for the tail command are: 
021 * <p>
022 * <table>
023 * <tr valign="top"><td width="10px"></td><td nowrap="nowrap">{@code -c}</td><td>&nbsp;&nbsp;</td><td nowrap="nowrap">{@code --chars}</td><td>&nbsp;</td><td>The {@code count} argument is in units of characters instead of 
024                        lines. Starts from 1 and includes line ending characters.</td></tr>
025 * <tr valign="top"><td width="10px"></td><td nowrap="nowrap">{@code -q}</td><td>&nbsp;&nbsp;</td><td nowrap="nowrap">{@code --suppressHeaders}</td><td>&nbsp;</td><td>Suppresses printing of headers when multiple files are being
026                        examined.</td></tr>
027 * <tr valign="top"><td width="10px"></td><td nowrap="nowrap">{@code -s}</td><td>&nbsp;&nbsp;</td><td nowrap="nowrap">{@code --countFromStart}</td><td>&nbsp;</td><td>The {@code count} argument is relative to the beginning of the file
028                        instead of counting from the end of the file. For instance, 
029                        {@code tail -s 10} prints the lines starting from line 10;
030                        {@code tail -s 1} prints the whole file.</td></tr>
031 * </table>
032 * <p>
033 * This interface serves as an alias for the extended interface to simplify the
034 * command signature methods by avoiding generic parameters.
035 */
036public interface TailOptions extends OptionSet<TailOption> {
037        /**
038         * Constant for an empty option set.
039         */
040        TailOptions EMPTY = new TailOptions() {
041                @Override
042                public Class<TailOption> optionType() {
043                        return TailOption.class;
044                }
045                @Override
046                public boolean isSet(TailOption option) {
047                        return false;
048                }
049                /**
050                 * Returns 0 as this is a set with no active options.
051                 * 
052                 * @return zero
053                 */
054                @Override
055                public int size() {
056                        return 0;
057                }
058                /**
059                 * Returns an immutable empty set.
060                 * 
061                 * @return an immutable empty set.
062                 */
063                @Override
064                public java.util.Set<TailOption> asSet() {
065                        return Collections.emptySet();
066                }
067                
068                /**
069                 * Returns an iterator returning no elements. 
070                 * 
071                 * @return an immutable iterator with no elements.
072                 */
073                @Override
074                public Iterator<TailOption> iterator() {
075                        return asSet().iterator();
076                }
077                
078                /**
079                 * Returns true if the {@link Option#acronym() acronym} should be used
080                 * for the specified {@code option} in string representations. 
081                 * <p>
082                 * This method returns always true;
083                 *  
084                 * @param option
085                 *            the option of interest
086                 * @return always true
087                 */
088                @Override
089                public boolean useAcronymFor(TailOption option) {
090                        return true;
091                }
092        };
093        /**
094         * Default implementation for a modifiable option set.
095         */
096        class Default extends DefaultOptionSet<TailOption> implements TailOptions {
097                /**
098                 * Default constructor for an empty option set with no active options.
099                 */
100                public Default() {
101                        super(TailOption.class);
102                }
103                /**
104                 * Constructor for an option set with a single active option.
105                 * @param option the option to be set
106                 */
107                public Default(TailOption option) {
108                        super(option);
109                }
110                /**
111                 * Constructor for an option set with the given active options.
112                 * @param options the options to be set
113                 */
114                public Default(TailOption... options) {
115                        this();
116                        setAll(options);
117                }
118                /**
119                 * Constructor for an option set initialized with the options given by
120                 * another option set.
121                 * 
122                 * @param optionSet set with the options to be active
123                 */
124                public Default(OptionSet<TailOption> optionSet) {
125                        this();
126                        setAll(optionSet);
127                }
128        }
129        
130        /**
131         * Value converter for {@link TailOptions} based on an {@link OptionSetConverter}. 
132         */
133        ValueConverter<TailOptions> CONVERTER = new ValueConverter<TailOptions>() {
134                private final OptionSetConverter<TailOption> converter = new OptionSetConverter<TailOption>(TailOption.class);
135                @Override
136                public TailOptions convert(Object value) {
137                        final OptionSet<TailOption> set = converter.convert(value);
138                        return set == null ? null : new Default(set);
139                }
140        };
141}