code: public int subscribe(final String subscriptionName, Object[] params) {
          // add the subscription to the HashMap with its initial value "false" which says that it is not ready
          subscriptionsAreReady.put(subscriptionName, false);
          
          // subscribe to a Meteor collection with given params
          // test error handling for invalid subscription
          return getDDP().subscribe(subscriptionName, params, new DDPListener() {
              @Override
              public void onReady(String id) {
                  // mark subscription ready
                  subscriptionsAreReady.replace(subscriptionName, true);
  
                  // broadcast that subscription has been updated
                  broadcastSubscriptionChanged(subscriptionName,
                          DdpMessageType.READY, null);
              }
  
              @Override
              public void onResult(Map<String, Object> jsonFields) {
                  String msgtype = (String) jsonFields
                          .get(DdpMessageField.MSG);
                  // ignore {"server_id":"GqrKrbcSeDfTYDkzQ"} web socket msgs
                  if ((msgtype != null) && (msgtype.equals(DdpMessageType.ERROR))) {
                      broadcastDDPError((String) jsonFields
                              .get(DdpMessageField.ERRORMSG));
                  }
              }
          });
      }
docs: Subscribes to specified subscription (note: this can be different from collection)
  @param subscriptionName name of subscription
  @param params parameters for subscription function (e.g., doc ID, etc.)
  @return subscription ID