Package ru.decipher.proxy

Source Code of ru.decipher.proxy.Task

package ru.decipher.proxy;

import org.junit.Before;
import org.junit.Test;
import ru.decipher.mock.Mock3GoodHttpProxyNoDelayLoader;
import ru.decipher.mock.Mock3GoodHttpProxySlowLoader;
import ru.decipher.mock.MockIncrementalGoodHttpProxyNoDelayLoader;
import ru.decipher.proxy.impl.DefaultProxyManager;
import ru.decipher.proxy.impl.HttpProxyConfig;
import ru.decipher.proxy.impl.LocalhostNoProxyLoader;

import java.util.*;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.concurrent.atomic.AtomicInteger;

import static java.lang.Thread.sleep;
import static junit.framework.Assert.*;

/**
* User: Alexander Paderin (apocarteres@gmail.com)
* Date: 1/17/14
* Time: 8:39 PM
*/
public class DefaultProxyManagerTest {

    private static final HttpProxyConfig PROXY1 = new HttpProxyConfig("test1.host", 31337);
    private static final HttpProxyConfig PROXY2 = new HttpProxyConfig("test2.host", 31337);
    private static final HttpProxyConfig PROXY3 = new HttpProxyConfig("test3.host", 31337);
    private static final HttpProxyConfig PROXY4 = new HttpProxyConfig("test4.host", 31337);
    private ProxyManager manager;

    @Before
    public void setUp() throws Exception {
        manager = new DefaultProxyManager(new MockIncrementalGoodHttpProxyNoDelayLoader(), 10, 100, 10, 0);
    }

    @Test
    public void testThatProxyTakeWell() throws Exception {
        assertEquals(PROXY1, manager.take());
    }

    @Test
    public void testThatManagerReturnsProxyInAscendingOrder() throws Exception {
        List<HttpProxyConfig> actual = new ArrayList<HttpProxyConfig>() {{
            add(manager.take());
            add(manager.take());
            add(manager.take());
        }};
        List<HttpProxyConfig> expected = new ArrayList<HttpProxyConfig>() {{
            add(PROXY1);
            add(PROXY2);
            add(PROXY3);
        }};
        assertEquals(expected, actual);
    }

    @Test
    public void testThatProxyRotatingWell() throws Exception {
        Set<HttpProxyConfig> expected = new HashSet<HttpProxyConfig>() {{
            add(PROXY1);
            add(PROXY2);
            add(PROXY3);
        }};
        Set<HttpProxyConfig> actual = new LinkedHashSet<>();
        for (int i = 0; i < 3; i++) {
            actual.add(manager.take());
        }
        assertEquals(expected, actual);
    }

    @Test
    public void testThatProxyBroughtBackWell() throws Exception {
        final HttpProxyConfig proxy = manager.take();
        for (int i = 0; i < 2; i++) {
            manager.take();
        }
        manager.compliment(proxy);
        assertEquals(PROXY1, manager.take());
    }

    @Test(expected = IllegalStateException.class)
    public void testThatCanNotBackUnknownProxy() throws Exception {
        manager.compliment(new HttpProxyConfig("testX.host", 31337));
    }

    @Test
    public void testThatUsageRatePerProxyWorksWell() throws Exception {
        long time = System.currentTimeMillis();
        final HttpProxyConfig proxy = manager.take();
        for (int i = 0; i < 2; i++) {
            manager.take();
        }
        manager.compliment(proxy);
        manager.take();
        time = System.currentTimeMillis() - time;
        assertTrue("proxy usage rate fails", time >= 100);
    }

    @Test
    public void testThatUsageRatePerProxyWorksWellInConcurrency() throws Exception {
        final DefaultProxyManager manager =
                new DefaultProxyManager(new Mock3GoodHttpProxyNoDelayLoader(), 0, 1000, 10, 0);
        class Task implements Runnable {
            @Override
            public void run() {
                try {
                    final HttpProxyConfig proxy = manager.take();
                    //do something
                    manager.compliment(proxy);
                } catch (Exception e) {
                    e.printStackTrace();
                    throw new RuntimeException(e);
                }
            }
        }
        ExecutorService service = Executors.newFixedThreadPool(30);
        Collection<Callable<Object>> tasks = new ArrayList<>();
        for (int i = 0; i < 30; i++) {
            tasks.add(Executors.callable(new Task()));
        }
        long time = System.currentTimeMillis();
        final List<Future<Object>> futures = service.invokeAll(tasks);
        for (Future<Object> future : futures) {
            future.get();
        }
        time = System.currentTimeMillis() - time;
        service.shutdown();
        // 3 proxies with usage rate 1 second, thus we have performance: 3 task per 1 second
        // 30 total tasks / 3 task = 10 seconds - 1 second for first fast call
        // and total time of execution should be at least 9 sec
        assertTrue("proxy usage rate in concurrency fails", time >= 9000);
    }

    @Test
    public void testThatNewProxyWillBeLoadedFromSourceWhenAllProxiesAreDropped() throws Exception {
        int blameTimes = 0;
        while (blameTimes < 30) {
            final HttpProxyConfig proxy = manager.take();
            manager.blame(proxy);
            blameTimes++;
        }
        assertEquals(PROXY1, manager.take());
    }

    @Test
    public void testThatBadProxyWillBeGoneWhenFailedRequestsLimitHit() throws Exception {
        int blameTimes = 0;
        while (blameTimes < 10) {
            final HttpProxyConfig proxy = manager.take();
            if (proxy.equals(PROXY1)) {
                blameTimes++;
            }
            manager.blame(proxy);
        }
        Set<HttpProxyConfig> expected = new HashSet<HttpProxyConfig>() {{
            add(PROXY2);
            add(PROXY3);
            add(PROXY1); // returns back from proxy loader
        }};
        Set<HttpProxyConfig> actual = new LinkedHashSet<>();
        for (int i = 0; i < 3; i++) {
            actual.add(manager.take());
        }
        assertEquals(expected, actual);
    }

    @Test
    public void testThatBadProxyWillBeForgivenOnSuccessRequest() throws Exception {
        int blameTimes = 0;
        boolean back = false;
        while (blameTimes < 10) {
            final HttpProxyConfig proxy = manager.take();
            if (proxy.equals(PROXY1)) {
                if (blameTimes == 1 && !back) {
                    manager.compliment(proxy);
                    back = true;
                }
                blameTimes++;
            }
            manager.blame(proxy);
        }
        Set<HttpProxyConfig> expected = new HashSet<HttpProxyConfig>() {{
            add(PROXY1);
            add(PROXY2);
            add(PROXY3);
        }};
        Set<HttpProxyConfig> actual = new LinkedHashSet<>();
        for (int i = 0; i < 3; i++) {
            actual.add(manager.take());
        }
        assertEquals(expected, actual);
    }

    @Test(expected = IllegalStateException.class)
    public void testThatDroppedProxyCanNotBeBroughtBack() throws Exception {
        int blameTimes = 0;
        while (blameTimes < 10) {
            final HttpProxyConfig proxy = manager.take();
            if (proxy.equals(PROXY1)) {
                blameTimes++;
            }
            manager.blame(proxy);
        }
        manager.compliment(PROXY1);
    }

    @Test(expected = IllegalStateException.class)
    public void testThatDroppedProxyCanNotBeBlamed() throws Exception {
        int blameTimes = 0;
        while (blameTimes < 10) {
            final HttpProxyConfig proxy = manager.take();
            if (proxy.equals(PROXY1)) {
                blameTimes++;
            }
            manager.blame(proxy);
        }
        manager.blame(PROXY1);
    }

    @Test(expected = IllegalStateException.class)
    public void testThatDroppedProxyCanNotBeBanned() throws Exception {
        int blameTimes = 0;
        while (blameTimes < 10) {
            final HttpProxyConfig proxy = manager.take();
            if (proxy.equals(PROXY1)) {
                blameTimes++;
            }
            manager.blame(proxy);
        }
        manager.ban(PROXY1);
    }

    @Test
    public void testConcurrentTakeAndBack() throws Exception {
        final DefaultProxyManager manager = new DefaultProxyManager(new MockIncrementalGoodHttpProxyNoDelayLoader(), 10, 100, 10, 0);
        ExecutorService service = Executors.newFixedThreadPool(20);
        Collection<Callable<Object>> tasks = new ArrayList<>();
        final AtomicInteger done = new AtomicInteger(0);
        final Random random = new Random();
        for (int i = 0; i < 100; i++) {
            tasks.add(Executors.callable(new Runnable() {
                @Override
                public void run() {
                    HttpProxyConfig take = manager.take();
                    try {
                        sleep(100);
                    } catch (InterruptedException ignored) {
                    }
                    manager.compliment(take);
                    take = manager.take();
                    try {
                        sleep(100);
                    } catch (InterruptedException ignored) {
                    }
                    if (random.nextBoolean()) {
                        manager.blame(take);
                    } else {
                        manager.ban(take);
                    }
                    done.incrementAndGet();
                }
            }));
        }
        final List<Future<Object>> futures = service.invokeAll(tasks);
        for (Future<Object> future : futures) {
            future.get();
        }
        service.shutdown();
        assertEquals(100, done.get());
    }

    @Test
    public void testThatManagerDoesNotBlockQueueDuringProxiesUpdate() throws Exception {
        manager = new DefaultProxyManager(new Mock3GoodHttpProxySlowLoader(), 1, 100, 10, 0);
        final HttpProxyConfig firstProxy = manager.take();
        final HttpProxyConfig secondProxy = manager.take();
        manager.ban(secondProxy);
        new Thread(new Runnable() {
            @Override
            public void run() {
                manager.take();
            }
        }).start();
        manager.compliment(firstProxy);
        final HttpProxyConfig actual = manager.take();
        assertNotNull(actual);
    }

    @Test
    public void testThatCheckedProxiesGoFirst() throws Exception {
        manager = new DefaultProxyManager(new MockIncrementalGoodHttpProxyNoDelayLoader(), 10, 100, 10, 0);
        final HttpProxyConfig firstProxy = manager.take();
        final HttpProxyConfig secondProxy = manager.take();
        final HttpProxyConfig third = manager.take();
        final HttpProxyConfig fourth = manager.take();

        manager.blame(firstProxy);
        manager.blame(secondProxy);
        manager.compliment(fourth);
        manager.compliment(third);

        Set<HttpProxyConfig> expected = new HashSet<HttpProxyConfig>() {{
            add(PROXY4);
            add(PROXY3);
        }};

        Set<HttpProxyConfig> actual = new HashSet<HttpProxyConfig>() {{
            add(manager.take());
            add(manager.take());
        }};

        assertEquals(expected, actual);
    }

    @Test
    public void testThatUpdateRateLimitWorksWell() throws Exception {
        final DefaultProxyManager manager = new DefaultProxyManager(new LocalhostNoProxyLoader(), 0, 0, 0, 1000);
        final HttpProxyConfig config = manager.take();
        manager.ban(config);
        long time = System.currentTimeMillis();
        manager.take();
        time = System.currentTimeMillis() - time;
        assertTrue("update rate limits failed", time >= 1000);

    }
}
TOP

Related Classes of ru.decipher.proxy.Task

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.