Beispiel #1
0
 @Provides
 @ManageLifecycle
 public ServiceEmitter getServiceEmitter(
     @Self Supplier<DruidNode> configSupplier, Emitter emitter) {
   final DruidNode config = configSupplier.get();
   final ServiceEmitter retVal =
       new ServiceEmitter(config.getServiceName(), config.getHost(), emitter);
   EmittingLogger.registerEmitter(retVal);
   return retVal;
 }
  @Test
  public void testRun() throws Exception {
    TestingCluster localCluster = new TestingCluster(1);
    localCluster.start();

    CuratorFramework localCf =
        CuratorFrameworkFactory.builder()
            .connectString(localCluster.getConnectString())
            .retryPolicy(new ExponentialBackoffRetry(1, 10))
            .compressionProvider(new PotentiallyGzippedCompressionProvider(false))
            .build();
    localCf.start();

    TestingCluster remoteCluster = new TestingCluster(1);
    remoteCluster.start();

    CuratorFramework remoteCf =
        CuratorFrameworkFactory.builder()
            .connectString(remoteCluster.getConnectString())
            .retryPolicy(new ExponentialBackoffRetry(1, 10))
            .compressionProvider(new PotentiallyGzippedCompressionProvider(false))
            .build();
    remoteCf.start();

    ObjectMapper jsonMapper = new DefaultObjectMapper();
    DruidClusterBridgeConfig config =
        new DruidClusterBridgeConfig() {
          @Override
          public String getTier() {
            return DruidServer.DEFAULT_TIER;
          }

          @Override
          public Duration getStartDelay() {
            return new Duration(0);
          }

          @Override
          public Duration getPeriod() {
            return new Duration(Long.MAX_VALUE);
          }

          @Override
          public String getBrokerServiceName() {
            return "testz0rz";
          }

          @Override
          public int getPriority() {
            return 0;
          }
        };

    ScheduledExecutorFactory factory = ScheduledExecutors.createFactory(new Lifecycle());

    DruidNode me = new DruidNode("me", "localhost", 8080);

    AtomicReference<LeaderLatch> leaderLatch =
        new AtomicReference<>(new LeaderLatch(localCf, "test"));

    ZkPathsConfig zkPathsConfig =
        new ZkPathsConfig() {
          @Override
          public String getZkBasePath() {
            return "/druid";
          }
        };
    DruidServerMetadata metadata =
        new DruidServerMetadata("test", "localhost", 1000, "bridge", DruidServer.DEFAULT_TIER, 0);
    DbSegmentPublisher dbSegmentPublisher = EasyMock.createMock(DbSegmentPublisher.class);
    EasyMock.replay(dbSegmentPublisher);
    DatabaseSegmentManager databaseSegmentManager =
        EasyMock.createMock(DatabaseSegmentManager.class);
    EasyMock.replay(databaseSegmentManager);
    ServerView serverView = EasyMock.createMock(ServerView.class);
    EasyMock.replay(serverView);

    BridgeZkCoordinator bridgeZkCoordinator =
        new BridgeZkCoordinator(
            jsonMapper,
            zkPathsConfig,
            new SegmentLoaderConfig(),
            metadata,
            remoteCf,
            dbSegmentPublisher,
            databaseSegmentManager,
            serverView);

    Announcer announcer = new Announcer(remoteCf, Executors.newSingleThreadExecutor());
    announcer.start();
    announcer.announce(
        zkPathsConfig.getAnnouncementsPath() + "/" + me.getHost(),
        jsonMapper.writeValueAsBytes(me));

    BatchDataSegmentAnnouncer batchDataSegmentAnnouncer =
        EasyMock.createMock(BatchDataSegmentAnnouncer.class);
    BatchServerInventoryView batchServerInventoryView =
        EasyMock.createMock(BatchServerInventoryView.class);
    EasyMock.expect(batchServerInventoryView.getInventory())
        .andReturn(
            Arrays.asList(
                new DruidServer("1", "localhost", 117, "historical", DruidServer.DEFAULT_TIER, 0),
                new DruidServer("2", "localhost", 1, "historical", DruidServer.DEFAULT_TIER, 0)));
    batchServerInventoryView.registerSegmentCallback(
        EasyMock.<Executor>anyObject(), EasyMock.<ServerView.SegmentCallback>anyObject());
    batchServerInventoryView.registerServerCallback(
        EasyMock.<Executor>anyObject(), EasyMock.<ServerView.ServerCallback>anyObject());
    EasyMock.expectLastCall();
    batchServerInventoryView.start();
    EasyMock.expectLastCall();
    batchServerInventoryView.stop();
    EasyMock.expectLastCall();
    EasyMock.replay(batchServerInventoryView);

    DruidClusterBridge bridge =
        new DruidClusterBridge(
            jsonMapper,
            config,
            factory,
            me,
            localCf,
            leaderLatch,
            bridgeZkCoordinator,
            announcer,
            batchDataSegmentAnnouncer,
            batchServerInventoryView);

    bridge.start();

    int retry = 0;
    while (!bridge.isLeader()) {
      if (retry > 5) {
        throw new ISE("Unable to become leader");
      }

      Thread.sleep(100);
      retry++;
    }

    String path = "/druid/announcements/localhost:8080";
    retry = 0;
    while (remoteCf.checkExists().forPath(path) == null) {
      if (retry > 5) {
        throw new ISE("Unable to announce");
      }

      Thread.sleep(100);
      retry++;
    }

    boolean verified = verifyUpdate(jsonMapper, path, remoteCf);
    retry = 0;
    while (!verified) {
      if (retry > 5) {
        throw new ISE("No updates to bridge node occurred");
      }

      Thread.sleep(100);
      retry++;

      verified = verifyUpdate(jsonMapper, path, remoteCf);
    }

    announcer.stop();
    bridge.stop();

    remoteCf.close();
    remoteCluster.close();
    localCf.close();
    localCluster.close();

    EasyMock.verify(batchServerInventoryView);
    EasyMock.verify(dbSegmentPublisher);
    EasyMock.verify(databaseSegmentManager);
    EasyMock.verify(serverView);
  }
  @Test(timeout = 2000L)
  public void testOverlordRun() throws Exception {
    // basic task master lifecycle test
    taskMaster.start();
    announcementLatch.await();
    while (!taskMaster.isLeading()) {
      // I believe the control will never reach here and thread will never sleep but just to be on
      // safe side
      Thread.sleep(10);
    }
    Assert.assertEquals(taskMaster.getLeader(), druidNode.getHostAndPort());
    // Test Overlord resource stuff
    overlordResource =
        new OverlordResource(
            taskMaster,
            new TaskStorageQueryAdapter(taskStorage),
            null,
            null,
            null,
            new AuthConfig());
    Response response = overlordResource.getLeader();
    Assert.assertEquals(druidNode.getHostAndPort(), response.getEntity());

    final String taskId_0 = "0";
    NoopTask task_0 = new NoopTask(taskId_0, 0, 0, null, null, null);
    response = overlordResource.taskPost(task_0, req);
    Assert.assertEquals(200, response.getStatus());
    Assert.assertEquals(ImmutableMap.of("task", taskId_0), response.getEntity());

    // Duplicate task - should fail
    response = overlordResource.taskPost(task_0, req);
    Assert.assertEquals(400, response.getStatus());

    // Task payload for task_0 should be present in taskStorage
    response = overlordResource.getTaskPayload(taskId_0);
    Assert.assertEquals(task_0, ((Map) response.getEntity()).get("payload"));

    // Task not present in taskStorage - should fail
    response = overlordResource.getTaskPayload("whatever");
    Assert.assertEquals(404, response.getStatus());

    // Task status of the submitted task should be running
    response = overlordResource.getTaskStatus(taskId_0);
    Assert.assertEquals(taskId_0, ((Map) response.getEntity()).get("task"));
    Assert.assertEquals(
        TaskStatus.running(taskId_0).getStatusCode(),
        ((TaskStatus) ((Map) response.getEntity()).get("status")).getStatusCode());

    // Simulate completion of task_0
    taskCompletionCountDownLatches[Integer.parseInt(taskId_0)].countDown();
    // Wait for taskQueue to handle success status of task_0
    waitForTaskStatus(taskId_0, TaskStatus.Status.SUCCESS);

    // Manually insert task in taskStorage
    // Verifies sync from storage
    final String taskId_1 = "1";
    NoopTask task_1 = new NoopTask(taskId_1, 0, 0, null, null, null);
    taskStorage.insert(task_1, TaskStatus.running(taskId_1));
    // Wait for task runner to run task_1
    runTaskCountDownLatches[Integer.parseInt(taskId_1)].await();

    response = overlordResource.getRunningTasks(req);
    // 1 task that was manually inserted should be in running state
    Assert.assertEquals(1, (((List) response.getEntity()).size()));
    final OverlordResource.TaskResponseObject taskResponseObject =
        ((List<OverlordResource.TaskResponseObject>) response.getEntity()).get(0);
    Assert.assertEquals(taskId_1, taskResponseObject.toJson().get("id"));
    Assert.assertEquals(TASK_LOCATION, taskResponseObject.toJson().get("location"));

    // Simulate completion of task_1
    taskCompletionCountDownLatches[Integer.parseInt(taskId_1)].countDown();
    // Wait for taskQueue to handle success status of task_1
    waitForTaskStatus(taskId_1, TaskStatus.Status.SUCCESS);

    // should return number of tasks which are not in running state
    response = overlordResource.getCompleteTasks(req);
    Assert.assertEquals(2, (((List) response.getEntity()).size()));
    taskMaster.stop();
    Assert.assertFalse(taskMaster.isLeading());
    EasyMock.verify(taskLockbox, taskActionClientFactory);
  }