+++ /dev/null
-<?php
-/**
- * StatusNet, the distributed open-source microblogging tool
- *
- * Superclass for plugins that do authentication and/or authorization
- *
- * PHP version 5
- *
- * LICENCE: This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Affero General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Affero General Public License for more details.
- *
- * You should have received a copy of the GNU Affero General Public License
- * along with this program. If not, see <http://www.gnu.org/licenses/>.
- *
- * @category Plugin
- * @package StatusNet
- * @author Craig Andrews <candrews@integralblue.com>
- * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
- * @link http://status.net/
- */
-
-if (!defined('STATUSNET') && !defined('LACONICA')) {
- exit(1);
-}
-
-/**
- * Superclass for plugins that do authentication
- *
- * @category Plugin
- * @package StatusNet
- * @author Craig Andrews <candrews@integralblue.com>
- * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
- * @link http://status.net/
- */
-
-abstract class AuthPlugin extends Plugin
-{
- //is this plugin authoritative for authentication?
- public $authn_authoritative = false;
-
- //should accounts be automatically created after a successful login attempt?
- public $autoregistration = false;
-
- //can the user change their email address
- public $email_changeable=true;
-
- //can the user change their email address
- public $password_changeable=true;
-
- //------------Auth plugin should implement some (or all) of these methods------------\\
- /**
- * Check if a nickname/password combination is valid
- * @param nickname
- * @param password
- * @return boolean true if the credentials are valid, false if they are invalid.
- */
- function checkPassword($nickname, $password)
- {
- return false;
- }
-
- /**
- * Automatically register a user when they attempt to login with valid credentials.
- * User::register($data) is a very useful method for this implementation
- * @param nickname
- * @return boolean true if the user was created, false if autoregistration is not allowed, null if this plugin is not responsible for this nickname
- */
- function autoRegister($nickname)
- {
- return null;
- }
-
- /**
- * Change a user's password
- * The old password has been verified to be valid by this plugin before this call is made
- * @param nickname
- * @param oldpassword
- * @param newpassword
- * @return boolean true if the password was changed, false if password changing failed for some reason, null if this plugin is not responsible for this nickname
- */
- function changePassword($nickname,$oldpassword,$newpassword)
- {
- return null;
- }
-
- /**
- * Can a user change this field in his own profile?
- * @param nickname
- * @param field
- * @return boolean true if the field can be changed, false if not allowed to change it, null if this plugin is not responsible for this nickname
- */
- function canUserChangeField($nickname, $field)
- {
- return null;
- }
-
- //------------Below are the methods that connect StatusNet to the implementing Auth plugin------------\\
- function __construct()
- {
- parent::__construct();
- }
-
- function StartCheckPassword($nickname, $password, &$authenticatedUser){
- if($this->password_changeable){
- $authenticated = $this->checkPassword($nickname, $password);
- if($authenticated){
- $authenticatedUser = User::staticGet('nickname', $nickname);
- if(!$authenticatedUser && $this->autoregistration){
- if($this->autoregister($nickname)){
- $authenticatedUser = User::staticGet('nickname', $nickname);
- }
- }
- return false;
- }else{
- if($this->authn_authoritative){
- return false;
- }
- }
- //we're not authoritative, so let other handlers try
- }else{
- if($this->authn_authoritative){
- //since we're authoritative, no other plugin could do this
- throw new Exception(_('Password changing is not allowed'));
- }
- }
- }
-
- function onStartChangePassword($nickname,$oldpassword,$newpassword)
- {
- if($this->password_changeable){
- $authenticated = $this->checkPassword($nickname, $oldpassword);
- if($authenticated){
- $result = $this->changePassword($nickname,$oldpassword,$newpassword);
- if($result){
- //stop handling of other handlers, because what was requested was done
- return false;
- }else{
- throw new Exception(_('Password changing failed'));
- }
- }else{
- if($this->authn_authoritative){
- //since we're authoritative, no other plugin could do this
- throw new Exception(_('Password changing failed'));
- }else{
- //let another handler try
- return null;
- }
- }
- }else{
- if($this->authn_authoritative){
- //since we're authoritative, no other plugin could do this
- throw new Exception(_('Password changing is not allowed'));
- }
- }
- }
-
- function onStartAccountSettingsPasswordMenuItem($widget)
- {
- if($this->authn_authoritative && !$this->password_changeable){
- //since we're authoritative, no other plugin could change passwords, so do render the menu item
- return false;
- }
- }
-}
-
--- /dev/null
+<?php
+/**
+ * StatusNet, the distributed open-source microblogging tool
+ *
+ * Superclass for plugins that do authentication and/or authorization
+ *
+ * PHP version 5
+ *
+ * LICENCE: This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * @category Plugin
+ * @package StatusNet
+ * @author Craig Andrews <candrews@integralblue.com>
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+
+if (!defined('STATUSNET') && !defined('LACONICA')) {
+ exit(1);
+}
+
+/**
+ * Superclass for plugins that do authentication
+ *
+ * @category Plugin
+ * @package StatusNet
+ * @author Craig Andrews <candrews@integralblue.com>
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+
+abstract class AuthenticationPlugin extends Plugin
+{
+ //is this plugin authoritative for authentication?
+ public $authoritative = false;
+
+ //should accounts be automatically created after a successful login attempt?
+ public $autoregistration = false;
+
+ //can the user change their email address
+ public $email_changeable=true;
+
+ //can the user change their email address
+ public $password_changeable=true;
+
+ //------------Auth plugin should implement some (or all) of these methods------------\\
+ /**
+ * Check if a nickname/password combination is valid
+ * @param nickname
+ * @param password
+ * @return boolean true if the credentials are valid, false if they are invalid.
+ */
+ function checkPassword($nickname, $password)
+ {
+ return false;
+ }
+
+ /**
+ * Automatically register a user when they attempt to login with valid credentials.
+ * User::register($data) is a very useful method for this implementation
+ * @param nickname
+ * @return boolean true if the user was created, false if autoregistration is not allowed, null if this plugin is not responsible for this nickname
+ */
+ function autoRegister($nickname)
+ {
+ return null;
+ }
+
+ /**
+ * Change a user's password
+ * The old password has been verified to be valid by this plugin before this call is made
+ * @param nickname
+ * @param oldpassword
+ * @param newpassword
+ * @return boolean true if the password was changed, false if password changing failed for some reason, null if this plugin is not responsible for this nickname
+ */
+ function changePassword($nickname,$oldpassword,$newpassword)
+ {
+ return null;
+ }
+
+ /**
+ * Can a user change this field in his own profile?
+ * @param nickname
+ * @param field
+ * @return boolean true if the field can be changed, false if not allowed to change it, null if this plugin is not responsible for this nickname
+ */
+ function canUserChangeField($nickname, $field)
+ {
+ return null;
+ }
+
+ //------------Below are the methods that connect StatusNet to the implementing Auth plugin------------\\
+ function __construct()
+ {
+ parent::__construct();
+ }
+
+ function StartCheckPassword($nickname, $password, &$authenticatedUser){
+ if($this->password_changeable){
+ $authenticated = $this->checkPassword($nickname, $password);
+ if($authenticated){
+ $authenticatedUser = User::staticGet('nickname', $nickname);
+ if(!$authenticatedUser && $this->autoregistration){
+ if($this->autoregister($nickname)){
+ $authenticatedUser = User::staticGet('nickname', $nickname);
+ }
+ }
+ return false;
+ }else{
+ if($this->authoritative){
+ return false;
+ }
+ }
+ //we're not authoritative, so let other handlers try
+ }else{
+ if($this->authoritative){
+ //since we're authoritative, no other plugin could do this
+ throw new Exception(_('Password changing is not allowed'));
+ }
+ }
+ }
+
+ function onStartChangePassword($nickname,$oldpassword,$newpassword)
+ {
+ if($this->password_changeable){
+ $authenticated = $this->checkPassword($nickname, $oldpassword);
+ if($authenticated){
+ $result = $this->changePassword($nickname,$oldpassword,$newpassword);
+ if($result){
+ //stop handling of other handlers, because what was requested was done
+ return false;
+ }else{
+ throw new Exception(_('Password changing failed'));
+ }
+ }else{
+ if($this->authoritative){
+ //since we're authoritative, no other plugin could do this
+ throw new Exception(_('Password changing failed'));
+ }else{
+ //let another handler try
+ return null;
+ }
+ }
+ }else{
+ if($this->authoritative){
+ //since we're authoritative, no other plugin could do this
+ throw new Exception(_('Password changing is not allowed'));
+ }
+ }
+ }
+
+ function onStartAccountSettingsPasswordMenuItem($widget)
+ {
+ if($this->authoritative && !$this->password_changeable){
+ //since we're authoritative, no other plugin could change passwords, so do render the menu item
+ return false;
+ }
+ }
+}
+
+++ /dev/null
-<?php
-/**
- * StatusNet, the distributed open-source microblogging tool
- *
- * Plugin to enable LDAP Authentication and Authorization
- *
- * PHP version 5
- *
- * LICENCE: This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Affero General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Affero General Public License for more details.
- *
- * You should have received a copy of the GNU Affero General Public License
- * along with this program. If not, see <http://www.gnu.org/licenses/>.
- *
- * @category Plugin
- * @package StatusNet
- * @author Craig Andrews <candrews@integralblue.com>
- * @copyright 2009 Craig Andrews http://candrews.integralblue.com
- * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
- * @link http://status.net/
- */
-
-if (!defined('STATUSNET') && !defined('LACONICA')) {
- exit(1);
-}
-
-require_once INSTALLDIR.'/plugins/Auth/AuthPlugin.php';
-require_once 'Net/LDAP2.php';
-
-class LdapPlugin extends AuthPlugin
-{
- public $host=null;
- public $port=null;
- public $version=null;
- public $starttls=null;
- public $binddn=null;
- public $bindpw=null;
- public $basedn=null;
- public $options=null;
- public $filter=null;
- public $scope=null;
- public $attributes=array();
-
- function __construct()
- {
- parent::__construct();
- }
-
- //---interface implementation---//
-
- function checkPassword($nickname, $password)
- {
- $ldap = $this->ldap_get_connection();
- if(!$ldap){
- return false;
- }
- $entry = $this->ldap_get_user($nickname);
- if(!$entry){
- return false;
- }else{
- $config = $this->ldap_get_config();
- $config['binddn']=$entry->dn();
- $config['bindpw']=$password;
- if($this->ldap_get_connection($config)){
- return true;
- }else{
- return false;
- }
- }
- }
-
- function autoRegister($nickname)
- {
- $attributes=array();
- $config_attributes = array('nickname','email','fullname','homepage','location');
- foreach($config_attributes as $config_attribute){
- $value = common_config('ldap', $config_attribute.'_attribute');
- if($value!==false){
- array_push($attributes,$value);
- }
- }
- $entry = $this->ldap_get_user($nickname,$attributes);
- if($entry){
- $registration_data = array();
- foreach($config_attributes as $config_attribute){
- $value = common_config('ldap', $config_attribute.'_attribute');
- if($value!==false){
- if($config_attribute=='email'){
- $registration_data[$config_attribute]=common_canonical_email($entry->getValue($value,'single'));
- }else if($config_attribute=='nickname'){
- $registration_data[$config_attribute]=common_canonical_nickname($entry->getValue($value,'single'));
- }else{
- $registration_data[$config_attribute]=$entry->getValue($value,'single');
- }
- }
- }
- //set the database saved password to a random string.
- $registration_data['password']=common_good_rand(16);
- $user = User::register($registration_data);
- return true;
- }else{
- //user isn't in ldap, so we cannot register him
- return null;
- }
- }
-
- function changePassword($nickname,$oldpassword,$newpassword)
- {
- //TODO implement this
- throw new Exception(_('Sorry, changing LDAP passwords is not supported at this time'));
-
- return false;
- }
-
- function canUserChangeField($nickname, $field)
- {
- switch($field)
- {
- case 'password':
- case 'nickname':
- case 'email':
- return false;
- }
- }
-
- //---utility functions---//
- function ldap_get_config(){
- $config = array();
- $keys = array('host','port','version','starttls','binddn','bindpw','basedn','options','filter','scope');
- foreach($keys as $key){
- $value = $this->$key;
- if($value!==null){
- $config[$key]=$value;
- }
- }
- return $config;
- }
-
- function ldap_get_connection($config = null){
- if($config == null){
- $config = $this->ldap_get_config();
- }
-
- //cannot use Net_LDAP2::connect() as StatusNet uses
- //PEAR::setErrorHandling(PEAR_ERROR_CALLBACK, 'handleError');
- //PEAR handling can be overridden on instance objects, so we do that.
- $ldap = new Net_LDAP2($config);
- $ldap->setErrorHandling(PEAR_ERROR_RETURN);
- $err=$ldap->bind();
- if (Net_LDAP2::isError($err)) {
- common_log(LOG_WARNING, 'Could not connect to LDAP server: '.$err->getMessage());
- return false;
- }
- return $ldap;
- }
-
- /**
- * get an LDAP entry for a user with a given username
- *
- * @param string $username
- * $param array $attributes LDAP attributes to retrieve
- * @return string DN
- */
- function ldap_get_user($username,$attributes=array()){
- $ldap = $this->ldap_get_connection();
- $filter = Net_LDAP2_Filter::create(common_config('ldap','nickname_attribute'), 'equals', $username);
- $options = array(
- 'scope' => 'sub',
- 'attributes' => $attributes
- );
- $search = $ldap->search(null,$filter,$options);
-
- if (PEAR::isError($search)) {
- common_log(LOG_WARNING, 'Error while getting DN for user: '.$search->getMessage());
- return false;
- }
-
- if($search->count()==0){
- return false;
- }else if($search->count()==1){
- $entry = $search->shiftEntry();
- return $entry;
- }else{
- common_log(LOG_WARNING, 'Found ' . $search->count() . ' ldap user with the username: ' . $username);
- return false;
- }
- }
-}
+++ /dev/null
-The LDAP plugin allows for StatusNet to handle authentication, authorization, and user information through LDAP.
-
-Installation
-============
-add "addPlugin('ldap', array('setting'=>'value', 'setting2'=>'value2', ...);" to the bottom of your config.php
-
-Settings
-========
-authn_authoritative (false): Set to true if LDAP's responses are authoritative (meaning if LDAP fails, do check the any other plugins or the internal password database).
-autoregistration (false): Set to true if users should be automatically created when they attempt to login.
-email_changeable (true): Are users allowed to change their email address? (true or false)
-password_changeable (true): Are users allowed to change their passwords? (true or false)
-
-host*: LDAP server name to connect to. You can provide several hosts in an array in which case the hosts are tried from left to right.. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-port: Port on the server. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-version: LDAP version. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-starttls: TLS is started after connecting. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-binddn: The distinguished name to bind as (username). See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-bindpw: Password for the binddn. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-basedn*: LDAP base name (root directory). See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-options: See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-filter: Default search filter. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-scope: Default search scope. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
-
-attributes: an array with the key being the StatusNet user attribute name, and the value the LDAP attribute name
- nickname*
- email
- fullname
- homepage
- location
-
-* required
-default values are in (parenthesis)
-
-Example
-=======
-Here's an example of an LDAP plugin configuration that connects to Microsoft Active Directory.
-
-addPlugin('ldap', array(
- 'authn_authoritative'=>true,
- 'autoregistration'=>true,
- 'binddn'=>'username',
- 'bindpw'=>'password',
- 'basedn'=>'OU=Users,OU=StatusNet,OU=US,DC=americas,DC=global,DC=loc',
- 'host'=>array('server1', 'server2'),
- 'attributes'=>array(
- 'nickname'=>'sAMAccountName',
- 'email'=>'mail',
- 'fullname'=>'displayName')
-));
--- /dev/null
+<?php
+/**
+ * StatusNet, the distributed open-source microblogging tool
+ *
+ * Plugin to enable LDAP Authentication and Authorization
+ *
+ * PHP version 5
+ *
+ * LICENCE: This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * @category Plugin
+ * @package StatusNet
+ * @author Craig Andrews <candrews@integralblue.com>
+ * @copyright 2009 Craig Andrews http://candrews.integralblue.com
+ * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
+ * @link http://status.net/
+ */
+
+if (!defined('STATUSNET') && !defined('LACONICA')) {
+ exit(1);
+}
+
+require_once INSTALLDIR.'/plugins/Authentication/AuthenticationPlugin.php';
+require_once 'Net/LDAP2.php';
+
+class LdapAuthenticatonPlugin extends AuthenticationPlugin
+{
+ public $host=null;
+ public $port=null;
+ public $version=null;
+ public $starttls=null;
+ public $binddn=null;
+ public $bindpw=null;
+ public $basedn=null;
+ public $options=null;
+ public $filter=null;
+ public $scope=null;
+ public $attributes=array();
+
+ function __construct()
+ {
+ parent::__construct();
+ }
+
+ //---interface implementation---//
+
+ function checkPassword($nickname, $password)
+ {
+ $ldap = $this->ldap_get_connection();
+ if(!$ldap){
+ return false;
+ }
+ $entry = $this->ldap_get_user($nickname);
+ if(!$entry){
+ return false;
+ }else{
+ $config = $this->ldap_get_config();
+ $config['binddn']=$entry->dn();
+ $config['bindpw']=$password;
+ if($this->ldap_get_connection($config)){
+ return true;
+ }else{
+ return false;
+ }
+ }
+ }
+
+ function autoRegister($nickname)
+ {
+ $attributes=array();
+ $config_attributes = array('nickname','email','fullname','homepage','location');
+ foreach($config_attributes as $config_attribute){
+ $value = common_config('ldap', $config_attribute.'_attribute');
+ if($value!==false){
+ array_push($attributes,$value);
+ }
+ }
+ $entry = $this->ldap_get_user($nickname,$attributes);
+ if($entry){
+ $registration_data = array();
+ foreach($config_attributes as $config_attribute){
+ $value = common_config('ldap', $config_attribute.'_attribute');
+ if($value!==false){
+ if($config_attribute=='email'){
+ $registration_data[$config_attribute]=common_canonical_email($entry->getValue($value,'single'));
+ }else if($config_attribute=='nickname'){
+ $registration_data[$config_attribute]=common_canonical_nickname($entry->getValue($value,'single'));
+ }else{
+ $registration_data[$config_attribute]=$entry->getValue($value,'single');
+ }
+ }
+ }
+ //set the database saved password to a random string.
+ $registration_data['password']=common_good_rand(16);
+ $user = User::register($registration_data);
+ return true;
+ }else{
+ //user isn't in ldap, so we cannot register him
+ return null;
+ }
+ }
+
+ function changePassword($nickname,$oldpassword,$newpassword)
+ {
+ //TODO implement this
+ throw new Exception(_('Sorry, changing LDAP passwords is not supported at this time'));
+
+ return false;
+ }
+
+ function canUserChangeField($nickname, $field)
+ {
+ switch($field)
+ {
+ case 'password':
+ case 'nickname':
+ case 'email':
+ return false;
+ }
+ }
+
+ //---utility functions---//
+ function ldap_get_config(){
+ $config = array();
+ $keys = array('host','port','version','starttls','binddn','bindpw','basedn','options','filter','scope');
+ foreach($keys as $key){
+ $value = $this->$key;
+ if($value!==null){
+ $config[$key]=$value;
+ }
+ }
+ return $config;
+ }
+
+ function ldap_get_connection($config = null){
+ if($config == null){
+ $config = $this->ldap_get_config();
+ }
+
+ //cannot use Net_LDAP2::connect() as StatusNet uses
+ //PEAR::setErrorHandling(PEAR_ERROR_CALLBACK, 'handleError');
+ //PEAR handling can be overridden on instance objects, so we do that.
+ $ldap = new Net_LDAP2($config);
+ $ldap->setErrorHandling(PEAR_ERROR_RETURN);
+ $err=$ldap->bind();
+ if (Net_LDAP2::isError($err)) {
+ common_log(LOG_WARNING, 'Could not connect to LDAP server: '.$err->getMessage());
+ return false;
+ }
+ return $ldap;
+ }
+
+ /**
+ * get an LDAP entry for a user with a given username
+ *
+ * @param string $username
+ * $param array $attributes LDAP attributes to retrieve
+ * @return string DN
+ */
+ function ldap_get_user($username,$attributes=array()){
+ $ldap = $this->ldap_get_connection();
+ $filter = Net_LDAP2_Filter::create(common_config('ldap','nickname_attribute'), 'equals', $username);
+ $options = array(
+ 'scope' => 'sub',
+ 'attributes' => $attributes
+ );
+ $search = $ldap->search(null,$filter,$options);
+
+ if (PEAR::isError($search)) {
+ common_log(LOG_WARNING, 'Error while getting DN for user: '.$search->getMessage());
+ return false;
+ }
+
+ if($search->count()==0){
+ return false;
+ }else if($search->count()==1){
+ $entry = $search->shiftEntry();
+ return $entry;
+ }else{
+ common_log(LOG_WARNING, 'Found ' . $search->count() . ' ldap user with the username: ' . $username);
+ return false;
+ }
+ }
+}
--- /dev/null
+The LDAP Authentication plugin allows for StatusNet to handle authentication through LDAP.
+
+Installation
+============
+add "addPlugin('ldapAuthentication', array('setting'=>'value', 'setting2'=>'value2', ...);" to the bottom of your config.php
+
+Settings
+========
+authoritative (false): Set to true if LDAP's responses are authoritative (meaning if LDAP fails, do check the any other plugins or the internal password database).
+autoregistration (false): Set to true if users should be automatically created when they attempt to login.
+email_changeable (true): Are users allowed to change their email address? (true or false)
+password_changeable (true): Are users allowed to change their passwords? (true or false)
+
+host*: LDAP server name to connect to. You can provide several hosts in an array in which case the hosts are tried from left to right.. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+port: Port on the server. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+version: LDAP version. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+starttls: TLS is started after connecting. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+binddn: The distinguished name to bind as (username). See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+bindpw: Password for the binddn. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+basedn*: LDAP base name (root directory). See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+options: See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+filter: Default search filter. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+scope: Default search scope. See http://pear.php.net/manual/en/package.networking.net-ldap2.connecting.php
+
+attributes: an array with the key being the StatusNet user attribute name, and the value the LDAP attribute name
+ nickname*
+ email
+ fullname
+ homepage
+ location
+
+* required
+default values are in (parenthesis)
+
+Example
+=======
+Here's an example of an LDAP plugin configuration that connects to Microsoft Active Directory.
+
+addPlugin('ldapAuthentication', array(
+ 'authoritative'=>true,
+ 'autoregistration'=>true,
+ 'binddn'=>'username',
+ 'bindpw'=>'password',
+ 'basedn'=>'OU=Users,OU=StatusNet,OU=US,DC=americas,DC=global,DC=loc',
+ 'host'=>array('server1', 'server2'),
+ 'attributes'=>array(
+ 'nickname'=>'sAMAccountName',
+ 'email'=>'mail',
+ 'fullname'=>'displayName')
+));