public IoFuture<Connection> connect(
      CallbackHandler handler, Map<String, String> saslOptions, SSLContext sslContext)
      throws IOException {
    OptionMap.Builder builder = OptionMap.builder();
    builder.addAll(configuration.getOptionMap());
    builder.set(SASL_POLICY_NOANONYMOUS, Boolean.FALSE);
    builder.set(SASL_POLICY_NOPLAINTEXT, Boolean.FALSE);
    if (isLocal() == false) {
      builder.set(Options.SASL_DISALLOWED_MECHANISMS, Sequence.of(JBOSS_LOCAL_USER));
    }
    List<Property> tempProperties =
        new ArrayList<Property>(saslOptions != null ? saslOptions.size() : 1);
    tempProperties.add(Property.of("jboss.sasl.local-user.quiet-auth", "true"));
    if (saslOptions != null) {
      for (String currentKey : saslOptions.keySet()) {
        tempProperties.add(Property.of(currentKey, saslOptions.get(currentKey)));
      }
    }
    builder.set(Options.SASL_PROPERTIES, Sequence.of(tempProperties));

    builder.set(Options.SSL_ENABLED, true);
    builder.set(Options.SSL_STARTTLS, true);

    CallbackHandler actualHandler = handler != null ? handler : new AnonymousCallbackHandler();
    return endpoint.connect(uri, builder.getMap(), actualHandler, sslContext);
  }
  // This duplicates the RealmSecurityProvider of AS7 to mimic the same security set-up
  private OptionMap createOptionMap() {
    List<String> mechanisms = new LinkedList<String>();
    Set<Property> properties = new HashSet<Property>();
    Builder builder = OptionMap.builder();

    if (saslMechanisms.contains(JBOSS_LOCAL_USER)) {
      mechanisms.add(JBOSS_LOCAL_USER);
      builder.set(SASL_POLICY_NOPLAINTEXT, false);
      properties.add(Property.of(LOCAL_DEFAULT_USER, DOLLAR_LOCAL));
    }

    if (saslMechanisms.contains(DIGEST_MD5)) {
      mechanisms.add(DIGEST_MD5);
      properties.add(Property.of(REALM_PROPERTY, REALM));
    }

    if (saslMechanisms.contains(PLAIN)) {
      mechanisms.add(PLAIN);
      builder.set(SASL_POLICY_NOPLAINTEXT, false);
    }

    if (saslMechanisms.isEmpty() || saslMechanisms.contains(ANONYMOUS)) {
      mechanisms.add(ANONYMOUS);
      builder.set(SASL_POLICY_NOANONYMOUS, false);
    }

    // TODO - SSL Options will be added in a subsequent task.
    builder.set(SSL_ENABLED, false);

    builder.set(SASL_MECHANISMS, Sequence.of(mechanisms));
    builder.set(SASL_PROPERTIES, Sequence.of(properties));

    return builder.getMap();
  }
  public static ChannelServer create(final Configuration configuration) throws IOException {
    if (configuration == null) {
      throw new IllegalArgumentException("Null configuration");
    }
    configuration.validate();

    final Endpoint endpoint =
        Remoting.createEndpoint(configuration.getEndpointName(), configuration.getOptionMap());

    Registration registration =
        endpoint.addConnectionProvider(
            configuration.getUriScheme(),
            new RemoteConnectionProviderFactory(),
            OptionMap.create(Options.SSL_ENABLED, Boolean.FALSE));

    final NetworkServerProvider networkServerProvider =
        endpoint.getConnectionProviderInterface(
            configuration.getUriScheme(), NetworkServerProvider.class);
    SimpleServerAuthenticationProvider provider = new SimpleServerAuthenticationProvider();
    // There is currently a probable bug in jboss remoting, so the user realm name MUST be the same
    // as
    // the endpoint name.
    provider.addUser("bob", configuration.getEndpointName(), "pass".toCharArray());
    AcceptingChannel<? extends ConnectedStreamChannel> streamServer =
        networkServerProvider.createServer(
            configuration.getBindAddress(),
            OptionMap.create(Options.SASL_MECHANISMS, Sequence.of("CRAM-MD5")),
            provider,
            null);

    return new ChannelServer(endpoint, registration, streamServer);
  }
  static OptionMap createOptionMap(final ModelNode parameters) {
    final OptionMap.Builder builder = OptionMap.builder();

    if (parameters.hasDefined(SASL)) {
      final ModelNode sasl = parameters.require(SASL);
      builder.set(Options.SASL_SERVER_AUTH, sasl.get(SERVER_AUTH).asBoolean());
      builder.set(Options.SASL_STRENGTH, SaslStrength.valueOf(sasl.get(STRENGTH).asString()));
      builder.set(Options.SASL_QOP, Sequence.of(asQopSet(sasl.get(QOP))));
      builder.set(Options.SASL_MECHANISMS, Sequence.of(asStringSet(sasl.get(INCLUDE_MECHANISMS))));

      if (sasl.hasDefined(POLICY)) {
        final ModelNode policy = sasl.require(POLICY);
        builder.set(Options.SASL_POLICY_FORWARD_SECRECY, policy.get(FORWARD_SECRECY).asBoolean());
        builder.set(Options.SASL_POLICY_NOACTIVE, policy.get(NO_ACTIVE).asBoolean());
        builder.set(Options.SASL_POLICY_NOANONYMOUS, policy.get(NO_ANONYMOUS).asBoolean());
        builder.set(Options.SASL_POLICY_NODICTIONARY, policy.get(NO_DICTIONARY).asBoolean());
        builder.set(Options.SASL_POLICY_NOPLAINTEXT, policy.get(NO_PLAIN_TEXT).asBoolean());
        builder.set(Options.SASL_POLICY_PASS_CREDENTIALS, policy.get(PASS_CREDENTIALS).asBoolean());
      }
    }
    return builder.getMap();
  }