Package com.indeed.proctor.consumer

Source Code of com.indeed.proctor.consumer.AbstractGroups

package com.indeed.proctor.consumer;

import com.google.common.base.Objects;
import com.google.common.base.Preconditions;
import com.google.common.collect.Maps;
import com.indeed.proctor.common.ProctorResult;
import com.indeed.proctor.common.model.ConsumableTestDefinition;
import com.indeed.proctor.common.model.Payload;
import com.indeed.proctor.common.model.TestBucket;

import javax.annotation.Nonnull;
import javax.annotation.Nullable;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

public abstract class AbstractGroups {
    private final ProctorResult proctorResult;
    private final LinkedHashMap<String, TestBucket> buckets;

    protected AbstractGroups(final ProctorResult proctorResult) {
        this.proctorResult = proctorResult;
        this.buckets = Maps.newLinkedHashMap();
        for (final Entry<String, TestBucket> entry : proctorResult.getBuckets().entrySet()) {
            final TestBucket testBucket = entry.getValue();
            this.buckets.put(entry.getKey(), testBucket);
        }
    }

    public Map<String, String> getTestVersions() {
        return proctorResult.getTestVersions();
    }

    /**
     * @deprecated Use {@link #isBucketActive(String, int, int)} instead
     */
    protected boolean isBucketActive(final String testName, final int value) {
        final TestBucket testBucket = buckets.get(testName);
        return ((testBucket != null) && (value == testBucket.getValue()));
    }

    protected boolean isBucketActive(final String testName, final int value, final int defaultValue) {
        final TestBucket testBucket = buckets.get(testName);
        if (null == testBucket) {
            return value == defaultValue;
        } else {
            return value == testBucket.getValue();
        }
    }

    protected int getValue(final String testName, final int defaultValue) {
        final TestBucket testBucket = buckets.get(testName);
        if (testBucket == null) {
            return defaultValue;
        }
        return testBucket.getValue();
    }

    public Map<String, String> getTestVersions(final Set<String> tests) {
        final Map<String, String> selectedTestVersions = Maps.newLinkedHashMap();
        final Map<String, ConsumableTestDefinition> testDefinitions = proctorResult.getTestDefinitions();
        for (final String testName : tests) {
            final ConsumableTestDefinition testDefinition = testDefinitions.get(testName);
            if (testDefinition != null) {
                selectedTestVersions.put(testName, testDefinition.getVersion());
            }
        }
        return selectedTestVersions;
    }

    /**
     * Return the Payload attached to the current active bucket for |test|.
     * Always returns a payload so the client doesn't crash on a malformed
     * test definition.
     *
     * @deprecated Use {@link #getPayload(String, Bucket)} instead
     */
    @Nonnull
    protected Payload getPayload(final String testName) {
        // Get the current bucket.
        final TestBucket testBucket = buckets.get(testName);

        // Lookup Payloads for this test
        if (testBucket != null) {
            final Payload payload = testBucket.getPayload();
            if (null != payload) {
                return payload;
            }
        }

        return Payload.EMPTY_PAYLOAD;
    }

    @Nonnull
    protected Payload getPayload(final String testName, @Nonnull final Bucket<?> fallbackBucket) {
        // Get the current bucket.
        final TestBucket testBucket = buckets.get(testName);

        // Lookup Payloads for this test
        @Nullable final Payload payload;
        if (testBucket != null) {
            payload = testBucket.getPayload();

        } else {
            final TestBucket fallbackTestBucket = getTestBucketForBucket(testName, fallbackBucket);

            if (null != fallbackTestBucket) {
                payload = fallbackTestBucket.getPayload();

            } else {
                payload = null;
            }
        }

        return Objects.firstNonNull(payload, Payload.EMPTY_PAYLOAD);
    }


     /**
     * Return the TestBucket, as defined in the current test matrix, for the test called testName with bucket value targetBucket.getValue().
     *
     * Can return null if it can't find any such bucket.
     *
     * This does a linear search over the list of defined buckets.  There shouldn't be too many buckets in any test,
     * so this should be fast enough.
     */
    protected @Nullable
    TestBucket getTestBucketForBucket(final String testName, Bucket<?> targetBucket) {
        final @Nullable Map<String, ConsumableTestDefinition> testDefinitions = proctorResult.getTestDefinitions();
        if (testDefinitions != null) {
            final @Nullable ConsumableTestDefinition testDefinition = testDefinitions.get(testName);
            if (testDefinition != null) {
                final @Nullable List<TestBucket> buckets = testDefinition.getBuckets();
                if (buckets != null) {
                    for (final TestBucket testBucket : buckets) {
                        if (targetBucket.getValue() == testBucket.getValue()) {
                            return testBucket;
                        }
                    }
                }
            }
        }
        return null;
    }

    public String toLongString() {
        if (proctorResult.getBuckets().isEmpty()) {
            return "";
        }
        final StringBuilder sb = new StringBuilder();
        for (final Entry<String, TestBucket> entry : proctorResult.getBuckets().entrySet()) {
            final String testName = entry.getKey();
            final TestBucket testBucket = entry.getValue();
            sb.append(testName).append('-').append(testBucket.getName()).append(',');
        }
        return sb.deleteCharAt(sb.length() - 1)
                .toString();
    }

    /**
     * To be called when logging ONLY
     */
    @Override
    public String toString() {
        if (isEmpty()) {
            return "";
        }
        final StringBuilder sb = buildTestGroupString();
        if (sb.length() == 0) {
            return "";
        }
        sb.deleteCharAt(sb.length() - 1);
        return sb.toString();
    }

    public StringBuilder buildTestGroupString() {
        final StringBuilder sb = new StringBuilder();
        appendTestGroups(sb);
        return sb;
    }

    public void appendTestGroups(final StringBuilder sb) {
        appendTestGroups(sb, ',');
    }

    /**
     * Return a value indicating if the groups are empty
     * and should be represented by an empty-string
     * {@link #toString()}
     * @return
     */
    protected boolean isEmpty() {
        return proctorResult.getBuckets().isEmpty();
    }

    /**
     * Appends each group to the StringBuilder using the separator to delimit
     * group names. the separator should be appended for each group added
       * to the string builder
     *
     * {@link #toString()}
     * {@link #buildTestGroupString()} or {@link #appendTestGroups(StringBuilder)}
     * @param sb
     */
    public void appendTestGroups(final StringBuilder sb, char separator) {
        for (final Entry<String, TestBucket> entry : proctorResult.getBuckets().entrySet()) {
            final String testName = entry.getKey();
            final TestBucket testBucket = entry.getValue();
            if (testBucket.getValue() < 0) {
                continue;
            }
            sb.append(testName).append(testBucket.getValue()).append(separator);
        }
    }

    /**
     * Generates a Map that be serialized to JSON and used with
     * indeed.proctor.groups.init and
     * indeed.proctor.groups.inGroup(tstName, bucketValue)
     *
     * When we create a generated JavaScript representation of indeed.proctor.AbstractGroups,
     * this config can be updated for use in it's constructor.
     *
     * @return
     */
    public Map<String, Integer> getJavaScriptConfig() {
        // For now this is a simple mapping from {testName to bucketValue}
        final Map<String, Integer> groups = Maps.newHashMapWithExpectedSize(proctorResult.getBuckets().size());
        for (final Entry<String, TestBucket> entry : proctorResult.getBuckets().entrySet()) {
            final String testName = entry.getKey();
            final TestBucket testBucket = entry.getValue();
            // mirrors appendTestGroups method by skipping *inactive* tests
            if (testBucket.getValue() < 0) {
                continue;
            }
            groups.put(testName, testBucket.getValue());
        }
        return groups;
    }

    public ProctorResult getProctorResult() {
        return proctorResult;
    }
}
TOP

Related Classes of com.indeed.proctor.consumer.AbstractGroups

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.