001package org.unix4j.unix.xargs; 002 003import java.util.ArrayList; 004import java.util.Collections; 005import java.util.List; 006 007import org.unix4j.variable.Arg; 008import org.unix4j.variable.VariableResolver; 009 010class DefaultItemStorage implements ItemStorage, VariableResolver { 011 012 private final XargsLineProcessor processor; 013// private final VariableContext variables; 014 015 private final long maxLines; 016 private final int maxArgs; 017 private final boolean isNoRunIfEmpty; 018 019 private int lineCount; 020 private final List<String> items = new ArrayList<String>(); 021 private int runCountForLine = 0; 022 private int runCountOverall = 0; 023 024 public DefaultItemStorage(XargsLineProcessor processor) { 025 this.processor = processor; 026 final XargsArguments args = processor.getArguments(); 027 this.maxLines = args.isMaxLinesSet() ? args.getMaxLines() : 1; 028 this.maxArgs = args.isMaxArgsSet() ? args.getMaxArgs() : Integer.MAX_VALUE; 029 this.isNoRunIfEmpty = args.isNoRunIfEmpty(); 030 } 031 032 @Override 033 public void storeItem(String item) { 034 items.add(item); 035 if (items.size() >= maxArgs) { 036 invokeCommandAndClearAllItems(); 037 } 038 } 039 040 @Override 041 public void incrementLineCount() { 042 lineCount++; 043 if ((lineCount % maxLines) == 0 && (runCountForLine == 0 || !items.isEmpty())) { 044 invokeCommandAndClearAllItems(); 045 runCountForLine = 0; 046 } 047 } 048 049 protected void flush() { 050 if ((lineCount % maxLines) != 0 && (runCountForLine == 0 || !items.isEmpty())) { 051 invokeCommandAndClearAllItems(); 052 } 053 if (runCountOverall == 0 && !isNoRunIfEmpty) { 054 invokeCommandAndClearAllItems(); 055 } 056 lineCount = 0; 057 runCountForLine = 0; 058 runCountOverall = 0; 059 } 060 061 private void invokeCommandAndClearAllItems() { 062 processor.invoke(); 063 runCountForLine++; 064 runCountOverall++; 065 items.clear(); 066 } 067 068 @Override 069 public Object getValue(String name) { 070 //(a) is variable a reference to all items? 071 if (Arg.$all.equals(name)) { 072 return Collections.unmodifiableList(items); 073 } 074 //(b) is variable a reference to one specific item? 075 final int index = Arg.argIndex(name); 076 if (index >= 0) { 077 return index < items.size() ? items.get(index) : null; 078 } 079 //(c) is variable a reference to all items from a given index? 080 final int from = Arg.argsFromIndex(name); 081 if (from >= 0) { 082 if (from < items.size()) { 083 return Collections.unmodifiableList(from == 0 ? items : items.subList(from, items.size())); 084 } 085 return Collections.EMPTY_LIST; 086 } 087 //no, not a variable that we know 088 return null; 089 } 090 091}