Example #1
0
  /**
   * @param request
   * @param connection
   * @return
   */
  public LogicalNode handleSubscriberRequest(
      SubscribeRequestTuple request, AbstractLengthPrependerClient connection) {
    String identifier = request.getIdentifier();
    String type = request.getStreamType();
    String upstream_identifier = request.getUpstreamIdentifier();

    // Check if there is a logical node of this type, if not create it.
    LogicalNode ln;
    if (subscriberGroups.containsKey(type)) {
      // logger.debug("adding to exiting group = {}", subscriberGroups.get(type));
      /*
       * close previous connection with the same identifier which is guaranteed to be unique.
       */
      AbstractLengthPrependerClient previous = subscriberChannels.put(identifier, connection);
      if (previous != null) {
        eventloop.disconnect(previous);
      }

      ln = subscriberGroups.get(type);
      ln.boot(eventloop);
      ln.addConnection(connection);
    } else {
      /*
       * if there is already a datalist registered for the type in which this client is interested,
       * then get a iterator on the data items of that data list. If the datalist is not registered,
       * then create one and register it. Hopefully this one would be used by future upstream nodes.
       */
      DataList dl;
      if (publisherBuffers.containsKey(upstream_identifier)) {
        dl = publisherBuffers.get(upstream_identifier);
        // logger.debug("old list = {}", dl);
      } else {
        dl =
            Tuple.FAST_VERSION.equals(request.getVersion())
                ? new FastDataList(upstream_identifier, blockSize, numberOfCacheBlocks)
                : new DataList(upstream_identifier, blockSize, numberOfCacheBlocks);
        publisherBuffers.put(upstream_identifier, dl);
        // logger.debug("new list = {}", dl);
      }

      long skipWindowId = (long) request.getBaseSeconds() << 32 | request.getWindowId();
      ln =
          new LogicalNode(
              upstream_identifier, type, dl.newIterator(identifier, skipWindowId), skipWindowId);

      int mask = request.getMask();
      if (mask != 0) {
        for (Integer bs : request.getPartitions()) {
          ln.addPartition(bs, mask);
        }
      }

      subscriberGroups.put(type, ln);
      ln.addConnection(connection);
      dl.addDataListener(ln);
    }

    return ln;
  }
Example #2
0
    @Override
    public void onMessage(byte[] buffer, int offset, int size) {
      if (ignore) {
        return;
      }

      Tuple request = Tuple.getTuple(buffer, offset, size);
      switch (request.getType()) {
        case PUBLISHER_REQUEST:

          /*
           * unregister the unidentified client since its job is done!
           */
          unregistered(key);
          logger.info("Received publisher request: {}", request);
          PublishRequestTuple publisherRequest = (PublishRequestTuple) request;

          DataList dl = handlePublisherRequest(publisherRequest, this);
          dl.setAutoFlushExecutor(serverHelperExecutor);

          Publisher publisher;
          if (publisherRequest.getVersion().equals(Tuple.FAST_VERSION)) {
            publisher =
                new Publisher(dl, (long) request.getBaseSeconds() << 32 | request.getWindowId()) {
                  @Override
                  public int readSize() {
                    if (writeOffset - readOffset < 2) {
                      return -1;
                    }

                    short s = buffer[readOffset++];
                    return s | (buffer[readOffset++] << 8);
                  }
                };
          } else {
            publisher =
                new Publisher(dl, (long) request.getBaseSeconds() << 32 | request.getWindowId());
          }

          key.attach(publisher);
          key.interestOps(SelectionKey.OP_READ);
          publisher.registered(key);

          int len = writeOffset - readOffset - size;
          if (len > 0) {
            publisher.transferBuffer(this.buffer, readOffset + size, len);
          }
          ignore = true;

          break;

        case SUBSCRIBER_REQUEST:
          /*
           * unregister the unidentified client since its job is done!
           */
          unregistered(key);
          ignore = true;
          logger.info("Received subscriber request: {}", request);

          SubscribeRequestTuple subscriberRequest = (SubscribeRequestTuple) request;
          AbstractLengthPrependerClient subscriber;

          //          /* for backward compatibility - set the buffer size to 16k - EXPERIMENTAL */
          int bufferSize = subscriberRequest.getBufferSize();
          //          if (bufferSize == 0) {
          //            bufferSize = 16 * 1024;
          //          }
          if (subscriberRequest.getVersion().equals(Tuple.FAST_VERSION)) {
            subscriber =
                new Subscriber(
                    subscriberRequest.getStreamType(),
                    subscriberRequest.getMask(),
                    subscriberRequest.getPartitions(),
                    bufferSize);
          } else {
            subscriber =
                new Subscriber(
                    subscriberRequest.getStreamType(),
                    subscriberRequest.getMask(),
                    subscriberRequest.getPartitions(),
                    bufferSize) {
                  @Override
                  public int readSize() {
                    if (writeOffset - readOffset < 2) {
                      return -1;
                    }

                    short s = buffer[readOffset++];
                    return s | (buffer[readOffset++] << 8);
                  }
                };
          }
          key.attach(subscriber);
          key.interestOps(SelectionKey.OP_WRITE | SelectionKey.OP_READ);
          subscriber.registered(key);

          final LogicalNode logicalNode = handleSubscriberRequest(subscriberRequest, subscriber);
          serverHelperExecutor.submit(
              new Runnable() {
                @Override
                public void run() {
                  logicalNode.catchUp();
                }
              });
          break;

        case PURGE_REQUEST:
          logger.info("Received purge request: {}", request);
          try {
            handlePurgeRequest((PurgeRequestTuple) request, this);
          } catch (IOException io) {
            throw new RuntimeException(io);
          }
          break;

        case RESET_REQUEST:
          logger.info("Received reset all request: {}", request);
          try {
            handleResetRequest((ResetRequestTuple) request, this);
          } catch (IOException io) {
            throw new RuntimeException(io);
          }
          break;

        default:
          throw new RuntimeException("unexpected message: " + request.toString());
      }
    }