11

When the user register on the site , and I look in the database joomla_users in the password table, there are password stored in the following formats:

  • $P$Do8QrURFT1r0NlWf0X/grdF/aMqwqK/

  • $P$DH38Lch9z508gJiop3A6u0whTity390

  • ........

But not in the form as described in the documentation (MD5 + ":" + SALT):

  • 1802ebc64051d5b4f4d1b408babb5020:0PHJDbnsyX05YpKbAuLYnw2VCzFMW2VK

I need to have this clarified for me, because I'm using outside script that checks for user credentials to check for password match.

In my PHP script I have code that seperates SALT from password from database:

$parts   = explode( ':', $password_database );
$crypt   = $parts[0];
$salt   = $parts[1];

But I can't do that if there is no dobule knot (:)

manlio
  • 18,345
  • 14
  • 76
  • 126
Gregor
  • 275
  • 1
  • 7
  • 19

3 Answers3

15

Try this,

The following piece of code is creating Joomla standard password (Older Version 1.5,1.7 etc).

 jimport('joomla.user.helper');
 $salt = JUserHelper::genRandomPassword(32);
 $crypt = JUserHelper::getCryptedPassword($password_choose, $salt);
 $password = $crypt.':'.$salt;

Joomla 3.2+ introduced PHP's password algorithm bcrypt but it required a minimum PHP 5.3+ If you plan to use bcrypt make sure your server PHP version is capable for this, read more here.

The other Version of Joomla Using the following methods (Joomla 3.x)

 jimport('joomla.user.helper');
 $yourpass = JUserHelper::hashPassword($password_choose);

The older algorithm also works fine in latest version too , only difference is older version creates a 65 character password and new one creates 34 character string. always go with updated version

Also if you are using external script should include Joomla framework like below. This should at very top of your external php file

define( '_JEXEC', 1 );
define('JPATH_BASE', dirname(__FILE__) );//this is when we are in the root
define( 'DS', DIRECTORY_SEPARATOR );

require_once ( JPATH_BASE .DS.'includes'.DS.'defines.php' );
require_once ( JPATH_BASE .DS.'includes'.DS.'framework.php' );

$mainframe =& JFactory::getApplication('site');
$mainframe->initialise();

Also you mentioned you have to check users credential then no need to check password format and all thing just use below codes after framework loads.

   $credentials['username'] = $data['username']; //user entered name
   $credentials['password'] = $data['password']; //users entered password
   $app = JFactory::getApplication();
   $error = $app->login($credentials, $options);
   if (!JError::isError($error)) {
    // login success
    }
  else{
    //Failed attempt
   }

hope it helps..

Jobin
  • 8,238
  • 1
  • 33
  • 52
  • Hi. With this trying 'test' as password I am getting a 65 character string: $P$D6qfmWHlMjUFNUxiYnt5qawXZ1bOTP. But changing the password of an user to test in BD I get a 34 character string: $P$D6qfmWHlMjUFNUxiYnt5qawXZ1bOTP. Why? – Mikel Apr 09 '14 at 12:14
  • @OceanicSix How you change the password from admin side ? its uses default joomla script or your own custom codes.It always create the password with length of 65char. – Jobin Apr 10 '14 at 02:48
  • What I mean is that using what Jobin said in his first part code I got a 65 character password. Changing to a user its password (in backend / administrator view) and then cheking in DB what have been stored, the string has 34 characters. So it is the how joomla store passwords. I finally get to do a 34 character encrypted password with David Fritsch code. – Mikel Apr 10 '14 at 11:13
  • Both are working right ? It depends on the Version too. – Jobin Apr 10 '14 at 11:35
  • I am using Joomla 3.2.1 and generate a encrypted password with that PHP code (which will have 34 character) and paste it in password column in 'XXX_user' table DB works. – Mikel Apr 10 '14 at 15:15
  • @JobinJose What if my external script is not in the same project? I have 2 different projects. – Amol Chakane Jun 21 '14 at 15:35
  • @AmolChakane you mean two Joomla installation ? The you have to use External script with loading framework options. – Jobin Jun 23 '14 at 03:06
  • @JobinJose My external script is in another project, which is developed in core php. – Amol Chakane Jun 23 '14 at 15:41
  • @AmolChakane ok, both are in same public_html right ? then even your core php project can load the Joomla framework using above script. If it is in two different space you can't solve it. – Jobin Jun 24 '14 at 02:45
  • @JobinJose My badluck :( Projects are in two different spaces. But I got one Joomla component which allows remote login using curl. – Amol Chakane Jun 25 '14 at 09:16
  • Very nice. But suppose you have to decrypt it (or encrypt it) using something other than PHP, like Java? – nemesys May 09 '15 at 18:45
  • @nemesys you can't decrypt Joomla Password! – Jobin May 11 '15 at 06:55
  • 2
    Recent versions of Joomla use the built-in PHP [password_hash](http://php.net/manual/it/function.password-hash.php) function when available (PHP >= 5.5). That hashing function uses the "standard" bcrypt algorithm, which is available in many languages. – Augusto Destrero Mar 10 '16 at 15:45
10

Joomla's default user class no longer uses salted MD5 to hash the password. The bind function of the JUser class now calls JUserHelper::hashPassword($array['password']) to encrypt the password.

That function is currently this:

public static function hashPassword($password)
    {
            // Use PHPass's portable hashes with a cost of 10.
            $phpass = new PasswordHash(10, true);

            return $phpass->HashPassword($password);
    }

And that means that it now relies on PHPass which you can read more about here: http://www.openwall.com/phpass/. Based on reading just the intro of this site, I'm guessing that the encryption is now bcrypt instead of MD5, but Joomla may have overriden the default encryption.

David Fritsch
  • 3,711
  • 2
  • 16
  • 25
5

With David Fritsch answer I get to do a encrypted password as Joomla does:

<?php
    define( '_JEXEC', 1 );
    define('JPATH_BASE', dirname(__FILE__) );//this is when we are in the root
    define( 'DS', DIRECTORY_SEPARATOR );

    require_once( JPATH_BASE .DS.'includes'.DS.'defines.php' );
    require_once( JPATH_BASE .DS.'includes'.DS.'framework.php' );

    $mainframe =& JFactory::getApplication('site');
    $mainframe->initialise();

    jimport('joomla.user.helper');
    $password = "test";     
    echo "<strong>Password: </strong>" . JUserHelper::hashPassword($password);
?>

Note that you have to store the file in joomla root directory, or change JPATH_BASE.

Mikel
  • 5,902
  • 5
  • 34
  • 49
  • 1
    For future visitors - this code outputs (Joomla 3.4.4): Password:$2y$10$upX58HulZWgBwKps2DaB9eoi2jI90H3i.JP3aSJQ.QwJWDo62l/Cy – Krzysiek Oct 14 '15 at 08:29
  • For future visitors, I found that actually (with Joomla! 3.5.1) the hash will be always different, even with the very same password being inserted. – diegov May 09 '16 at 11:58