title: XMPP SASL authentication on Ejabberd with PHP
body: <p>I'm trying to authenticate with an XMPP server using SASL. </p>
  
  <pre><code>/**
       * Send Authentication, SASL
       * @return Bool
       * @param $username String
       * @param $password String
       */
      function authenticate($username, $password) {
          $this-&gt;username = $username;
          $this-&gt;password = $password;
  
          var_dump($username, $password, $this-&gt;domain);
  
          $auth = base64_encode($username.'@'.$this-&gt;domain."\u0000".$username."\u0000".$password);
          $xml = '&lt;auth mechanism="PLAIN" xmlns="urn:ietf:params:xml:ns:xmpp-sasl"&gt;'.$auth.'&lt;/auth&gt;';
          if ($this-&gt;write($xml)) {
              if ($xml = $this-&gt;listen(1, true)) {
                  if (preg_match("/&lt;success/i", $xml)) {
                      $this-&gt;authenticated = $this-&gt;_sendStream();
                  }
              }
          }
          $this-&gt;events-&gt;trigger('authenticate', $this-&gt;authenticated);
          return $this-&gt;authenticated;
      }
  </code></pre>
  
  <p>The XMPP server however responds with:</p>
  
  <pre><code>&lt;failure xmlns='urn:ietf:params:xml:ns:xmpp-sasl'&gt;&lt;bad-protocol/&gt;&lt;/failure&gt;
  </code></pre>
  
  <p>This is against an Ejabberd server. When I open the XMPP stream, it advertises:</p>
  
  <pre><code>&lt;stream:features&gt;&lt;starttls xmlns='urn:ietf:params:xml:ns:xmpp-tls'/&gt;&lt;mechanisms xmlns='urn:ietf:params:xml:ns:xmpp-sasl'&gt;&lt;mechanism&gt;DIGEST-MD5&lt;/mechanism&gt;&lt;mechanism&gt;PLAIN&lt;/mechanism&gt;&lt;/mechanisms&gt;&lt;register xmlns='http://jabber.org/features/iq-register'/&gt;&lt;/stream:features&gt;
  </code></pre>
  
  <p>So it seams to me that SASL - PLAIN should work. I have a JavaScript version, that works perfectly on OpenFire server. (I can't test it on Ejabberd at the moment) </p>
  
  <pre><code>sendAuthentication: function() {
          clearTimeout(XMPP.sendAuthentication_timer);
          var auth = Base64.encode(XMPP.username+'@'+XMPP.domain+'\u0000'+XMPP.username+'\u0000'+XMPP.password);
          mySocket.events.receive.observe(XMPP.receivedAuthSuccess, function() {
              mySocket.send('&lt;auth mechanism="PLAIN" xmlns="urn:ietf:params:xml:ns:xmpp-sasl"&gt;' + auth + '&lt;/auth&gt;');
          });
      }
  </code></pre>
  
  <p>So I can't get why the PHP version is not working.</p>