All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.emc.mongoose.api.model.io.task.data.BasicDataIoTaskBuilder Maven / Gradle / Ivy

There is a newer version: 4.0.0-alpha5
Show newest version
package com.emc.mongoose.api.model.io.task.data;

import com.github.akurilov.commons.collection.Range;
import com.emc.mongoose.api.model.io.task.composite.data.BasicCompositeDataIoTask;
import com.emc.mongoose.api.model.io.task.BasicIoTaskBuilder;
import com.emc.mongoose.api.model.item.DataItem;
import com.emc.mongoose.api.model.storage.Credential;
import static com.emc.mongoose.api.model.item.DataItem.getRangeCount;

import com.github.akurilov.commons.math.Random;
import static com.github.akurilov.commons.system.SizeInBytes.formatFixedSize;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

/**
 Created by kurila on 14.07.16.
 */
public class BasicDataIoTaskBuilder>
extends BasicIoTaskBuilder
implements DataIoTaskBuilder {

	private final Random rnd = new Random();

	protected volatile List srcItemsForConcat = null;
	protected volatile int srcItemsCount = 0;
	protected volatile int srcItemsCountMin = 0;
	protected volatile int srcItemsCountMax = 0;
	protected volatile List fixedRanges = null;
	protected volatile int randomRangesCount = 0;
	protected volatile long sizeThreshold = 0;
	
	@Override
	public BasicDataIoTaskBuilder setFixedRanges(final List fixedRanges) {
		this.fixedRanges = fixedRanges;
		return this;
	}
	
	@Override
	public BasicDataIoTaskBuilder setRandomRangesCount(final int count) {
		this.randomRangesCount = count;
		return this;
	}
	
	@Override
	public BasicDataIoTaskBuilder setSizeThreshold(final long sizeThreshold) {
		this.sizeThreshold = sizeThreshold > 0 ? sizeThreshold : Long.MAX_VALUE;
		return this;
	}

	@Override
	public BasicDataIoTaskBuilder setSrcItemsCount(final int min, final int max) {
		this.srcItemsCountMin = min;
		this.srcItemsCountMax = max;
		return this;
	}

	@Override
	public BasicDataIoTaskBuilder setSrcItemsForConcat(final List srcItemsForConcat) {
		this.srcItemsForConcat = srcItemsForConcat;
		if(this.srcItemsForConcat != null) {
			this.srcItemsCount = srcItemsForConcat.size();
		}
		return this;
	}
	
	@Override
	public List getFixedRanges() {
		return fixedRanges;
	}
	
	@Override
	public int getRandomRangesCount() {
		return randomRangesCount;
	}
	
	@Override
	public long getSizeThreshold() {
		return sizeThreshold;
	}
	
	@Override @SuppressWarnings("unchecked")
	public O getInstance(final I dataItem)
	throws IOException, IllegalArgumentException {
		final String uid;
		if(dataItem.size() > sizeThreshold) {
			if(randomRangesCount > 0 || (fixedRanges != null && fixedRanges.size() > 0)) {
				throw new IllegalArgumentException(
					"Not supported - both byte ranges configured and size threshold"
				);
			}
			return (O) new BasicCompositeDataIoTask<>(
				originCode, ioType, dataItem, inputPath, getNextOutputPath(),
				Credential.getInstance(uid = getNextUid(), getNextSecret(uid)),
				fixedRanges, randomRangesCount, sizeThreshold
			);
		} else if(srcItemsCount > 0) {
			return (O) new BasicDataIoTask<>(
				originCode, ioType, dataItem, inputPath, getNextOutputPath(),
				Credential.getInstance(uid = getNextUid(), getNextSecret(uid)),
				fixedRanges, randomRangesCount, getNextSrcItemsForConcat()
			);
		} else {
			if(randomRangesCount > getRangeCount(dataItem.size())) {
				throw new IllegalArgumentException(
					"Configured random ranges count (" + randomRangesCount + ") is more than " +
						"allowed for the data item w/ size " + formatFixedSize(dataItem.size())
				);
			}
			return (O) new BasicDataIoTask<>(
				originCode, ioType, dataItem, inputPath, getNextOutputPath(),
				Credential.getInstance(uid = getNextUid(), getNextSecret(uid)),
				fixedRanges, randomRangesCount
			);
		}
	}

	@Override @SuppressWarnings("unchecked")
	public void getInstances(final List items, final List buff)
	throws IOException, IllegalArgumentException {
		String uid;
		for(final I nextItem : items) {
			if(nextItem.size() > sizeThreshold) {
				if(randomRangesCount > 0 || (fixedRanges != null && fixedRanges.size() > 0)) {
					throw new IllegalArgumentException(
						"Not supported - both byte ranges configured and size threshold"
					);
				}
				buff.add(
					(O) new BasicCompositeDataIoTask<>(
						originCode, ioType, nextItem, inputPath, getNextOutputPath(),
						Credential.getInstance(uid = getNextUid(), getNextSecret(uid)),
						fixedRanges, randomRangesCount, sizeThreshold
					)
				);
			} else if(srcItemsCount > 0) {
				buff.add(
					(O) new BasicDataIoTask<>(
						originCode, ioType, nextItem, inputPath, getNextOutputPath(),
						Credential.getInstance(uid = getNextUid(), getNextSecret(uid)),
						fixedRanges, randomRangesCount, getNextSrcItemsForConcat()
					)
				);
			} else {
				if(randomRangesCount > getRangeCount(nextItem.size())) {
					throw new IllegalArgumentException(
						"Configured random ranges count (" + randomRangesCount + ") is more than " +
							"allowed for the data item w/ size " + formatFixedSize(nextItem.size())
					);
				}
				buff.add(
					(O) new BasicDataIoTask<>(
						originCode, ioType, nextItem, inputPath, getNextOutputPath(),
						Credential.getInstance(uid = getNextUid(), getNextSecret(uid)),
						fixedRanges, randomRangesCount
					)
				);
			}
		}
	}

	@Override
	public void close()
	throws IOException {
		super.close();
		if(srcItemsForConcat != null) {
			srcItemsForConcat.clear();
			srcItemsForConcat = null;
		}
		if(fixedRanges != null) {
			fixedRanges.clear();
			fixedRanges = null;
		}
	}

	protected List getNextSrcItemsForConcat() {
		final int n = srcItemsCountMin < srcItemsCountMax ?
			srcItemsCountMin + rnd.nextInt(srcItemsCountMax - srcItemsCountMin + 1) :
			srcItemsCountMin;
		final List selectedItems = new ArrayList<>(n);
		for(int i = 0; i < n; i ++) {
			selectedItems.add(srcItemsForConcat.get(rnd.nextInt(srcItemsCount)));
		}
		return selectedItems;
	}
}