package uk.ac.ebi.atlas.model.experiment.baseline;

import com.google.common.base.Joiner;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Sets;
import org.apache.commons.lang.math.RandomUtils;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.junit.MockitoJUnitRunner;
import uk.ac.ebi.atlas.model.AssayGroup;

import java.util.*;

import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.is;
import static org.mockito.Mockito.mock;

@RunWith(MockitoJUnitRunner.class)
public class BaselineProfileTest {

    private static final String GENE_ID = "geneId_1";
    private static final String GENE_NAME = "geneName_1";

    private AssayGroup g1 = new AssayGroup("g1", "run11","run12","run13");
    private AssayGroup g2 = new AssayGroup("g2", "run21");
    private AssayGroup g3 = new AssayGroup("g3", "run31","run32");
    private AssayGroup g4 = new AssayGroup("g4", "g41");

    private BaselineExpression expression_1 = new BaselineExpression(2.2D);
    private BaselineExpression expression_2 = new BaselineExpression(3D);
    private BaselineExpression expression_3 = new BaselineExpression(3.001D);

    private BaselineProfile subject;

    @Before
    public void setUp() throws Exception {
        subject = new BaselineProfile(GENE_ID, GENE_NAME);
        subject.add(g1, expression_1);
        subject.add(g2, expression_2);
        subject.add(g3, expression_3);
    }

    @Test
    public void getSpecificityOnAssayGroups(){
        assertThat(subject.getSpecificity(ImmutableList.of(g1)), is(1L));
        assertThat(subject.getSpecificity(ImmutableList.of()), is(0L));
        assertThat(subject.getSpecificity(ImmutableList.of(g4)), is(0L));
    }

    @Test
    public void testGetGeneSpecificity() throws Exception {
        assertThat(subject.getSpecificity(), is(3L));
    }

    @Test(expected = IllegalArgumentException.class)
    public void shouldThrowExceptionWhenQueryFactorsIsEmpty() {
        subject.getAverageExpressionLevelOn(new HashSet<>());
    }

    @Test
    public void averageExpressionLevelOnEmptyCollection() {
        //given
        Set<AssayGroup> queryFactors = ImmutableSet.of(mock(AssayGroup.class));
        //when
        double averageExpressionLevel = subject.getAverageExpressionLevelOn(queryFactors);
        //then
        assertThat(averageExpressionLevel, is(0D));
    }

    @Test
    public void averageExpressionLevel() {
        double averageExpressionLevel = subject.getAverageExpressionLevelOn(Sets.newHashSet(g1, g3));
        assertThat(averageExpressionLevel, is(2.6005000000000003D));

        averageExpressionLevel = subject.getAverageExpressionLevelOn(Sets.newHashSet(g1, g3, g4));
        assertThat(averageExpressionLevel, is(1.733666666666667D));
    }

    @Test
    public void isExpressedAnywhereIsLikeSpecificityGreaterThanZeroButPossiblyFaster(){
        List<AssayGroup> assayGroups = new ArrayList<>();
        while (assayGroups.isEmpty()) {
            if(RandomUtils.nextBoolean()) assayGroups.add(g1);
            if(RandomUtils.nextBoolean()) assayGroups.add(g2);
            if(RandomUtils.nextBoolean()) assayGroups.add(g3);
            if(RandomUtils.nextBoolean()) assayGroups.add(g4);
        }
        Collections.shuffle(assayGroups);

        assertThat(
                subject.isExpressedAnywhereOn(assayGroups),
                is(subject.getSpecificity() > 0)
        );
    }
}
@@ -49,46 +49,8 @@
 e;%0A%0A
-import com.google.common.base.Joiner;%0A
 impo
@@ -796,16 +796,17 @@
 11%22,
+ 
 %22run12%22,
 %22run
@@ -801,16 +801,17 @@
 %22run12%22,
+ 
 %22run13%22)
@@ -928,16 +928,17 @@
 %22run31%22,
+ 
 %22run32%22)
@@ -1557,16 +1557,17 @@
 Groups()
+ 
 %7B%0A      
@@ -2945,17 +2945,19 @@
 Faster()
-%7B
+ %7B%0A
 %0A       
@@ -3053,32 +3053,33 @@
 %7B%0A            if
+ 
 (RandomUtils.nex
@@ -3117,32 +3117,33 @@
 ;%0A            if
+ 
 (RandomUtils.nex
@@ -3181,32 +3181,33 @@
 ;%0A            if
+ 
 (RandomUtils.nex
@@ -3253,16 +3253,17 @@
       if
+ 
 (RandomU
@@ -3376,16 +3376,56 @@
 rtThat(%0A
+                assayGroups.toString(),%0A
         
@@ -3518,16 +3518,27 @@
 ificity(
+assayGroups
 ) %3E 0)%0A 
@@ -3553,9 +3553,10 @@
 ;%0A    %7D%0A
+%0A
 %7D

Fix an assumption in the test - was testing a wrong thing