phpBB 3.1: How to create a password manager instance?

Discussion forum for Extension Writers regarding Extension Development.
Post Reply
CarstenF
Registered User
Posts: 33
Joined: Sat Jun 28, 2008 8:55 pm

phpBB 3.1: How to create a password manager instance?

Post by CarstenF »

Hi all,

with phpBB 3.0, I used phpBB as a login provider for another system (a DokuWiki instance). That is, in order to enable users to log into DokuWiki using their phpBB username and password, I used (in a DokuWiki plugin) code like this:

Code: Select all

    define('IN_PHPBB', true);
    $phpbb_root_path = $conf['auth']['phpbb']['root_path'];   // from DokuWiki config
    $phpEx = substr(strrchr(__FILE__, '.'), 1);

    include $phpbb_root_path . 'config.php';
    include $phpbb_root_path . 'includes/functions.php';

    // ...

    return phpbb_check_hash($provided_cleartext_password, $hash_from_database) ;
With phpBB 3.1, this no longer works: phpbb_check_hash() is now in includes/functions_compatibility.php, defined like this:

Code: Select all

function phpbb_check_hash($password, $hash)
{
	global $phpbb_container;
	$passwords_manager = $phpbb_container->get('passwords.manager');

	return $passwords_manager->check($password, $hash);
}
If I use this to update the above code, the problem is that $phpbb_container is not known, but we need it in order to obtain $passwords_manager. Therefore, I now include common.php, obtaining this result:

Code: Select all

    // ... as before

    include $phpbb_root_path . 'config.php';
    include $phpbb_root_path . 'common.php';    // for $phpbb_container

    // ...

    gobal $phpbb_container;

    $passwords_manager = $phpbb_container->get('passwords.manager');
    return $passwords_manager->check($provided_cleartext_password, $hash_from_database);
The problem is that common.php seems to define many global variables and functions that collide with DokuWiki.

Therefore, I would like to avoid including common.php, and instead include only the minimal amount of code that is necessary. For my purpose, at a minimum it is apparently necessary to create an instance of passwords manager, but unfortunately I'm not safe enough in phpBB code (and php in general) to see how I could achieve that.

Thus, can you please help me with this?
How can a passwords manager be instantiated with a minimum of include dependencies?

Best regards,
Carsten
Paul
Infrastructure Team Leader
Infrastructure Team Leader
Posts: 28654
Joined: Sat Dec 04, 2004 3:44 pm
Location: The netherlands.
Name: Paul Sohier
Contact:

Re: phpBB 3.1: How to create a password manager instance?

Post by Paul »

You will always need to include common.php.
CarstenF
Registered User
Posts: 33
Joined: Sat Jun 28, 2008 8:55 pm

Re: phpBB 3.1: How to create a password manager instance?

Post by CarstenF »

Hi Paul,
thanks for your reply.
Paul wrote:You will always need to include common.php.
Well, the manager class is defined in phpbb\passwords\manager.php.
Normally, I would just include that, then create an instance of the class.

Unfortunately, the constructor takes parameters that I don't know how to supply -- I had hoped that there was a reasonably simple way to come up with the proper parameters (possibly with more but still limited includes), then be able to use the result while having introduced only a minimal set of dependencies.

Do you see any chance to achieve that?
User avatar
javiexin
Code Contributor
Posts: 1157
Joined: Wed Oct 12, 2011 11:46 pm
Location: Madrid, Spain
Name: Javier
Contact:

Re: phpBB 3.1: How to create a password manager instance?

Post by javiexin »

If you use dependency injection, you might not need the "includes".
See how phpbb/passwords/manager.php defines its own dependencies in config/password.yml
https://github.com/phpbb/phpbb/blob/3.1 ... .yml#L3-L9

Also, you may have to take into consideration this: viewtopic.php?p=14083231#p14083231

Hope this helps.
-javiexin

EDIT: Never mind, I misunderstood your use case. This is not going to work in your case. Sorry.
Paul
Infrastructure Team Leader
Infrastructure Team Leader
Posts: 28654
Joined: Sat Dec 04, 2004 3:44 pm
Location: The netherlands.
Name: Paul Sohier
Contact:

Re: phpBB 3.1: How to create a password manager instance?

Post by Paul »

CarstenF wrote:Hi Paul,
thanks for your reply.
Paul wrote:You will always need to include common.php.
Well, the manager class is defined in phpbb\passwords\manager.php.
Normally, I would just include that, then create an instance of the class.

Unfortunately, the constructor takes parameters that I don't know how to supply -- I had hoped that there was a reasonably simple way to come up with the proper parameters (possibly with more but still limited includes), then be able to use the result while having introduced only a minimal set of dependencies.

Do you see any chance to achieve that?
sure, you need the password helper, password collection and config. Config depends on the dbal, which depends on a database connection which is setup in common.php.
CarstenF
Registered User
Posts: 33
Joined: Sat Jun 28, 2008 8:55 pm

Re: phpBB 3.1: How to create a password manager instance?

Post by CarstenF »

javiexin wrote:See how phpbb/passwords/manager.php defines its own dependencies in config/password.yml
https://github.com/phpbb/phpbb/blob/3.1 ... .yml#L3-L9
[...]
EDIT: Never mind, I misunderstood your use case. This is not going to work in your case. Sorry.
Thanks for your reply. I could indeed not make progress from this, but it helped my understanding a little. ;)
CarstenF
Registered User
Posts: 33
Joined: Sat Jun 28, 2008 8:55 pm

Re: phpBB 3.1: How to create a password manager instance?

Post by CarstenF »

Paul wrote:sure, you need the password helper, password collection and config. Config depends on the dbal, which depends on a database connection which is setup in common.php.
Well, this being circular is indeed not helpful...

In the meanwhile, I "solved" the problem by a work-around that is very simple, but also somewhat clumsy: I put the phpBB-based password-checking code into stand-alone PHP script that takes the username and password as command line arguments and indicates via its exit code whether the password is correct.
The DokuWiki auth plugin just calls this script via exec() and proceeds according to its exit code.

(For another subsystem that lives on a different host, I even have a variant of this technique that works remotely via plain HTTP / HTML web requests.)

Even though this works well, it doesn't solve the actual problem of phpBB and DokuWiki conflicting. The DokuWiki auth plugin queries the phpBB database with its own means in order to learn a user's email address, user groups, etc. This is possible and works because there is no need to exactly reproduce phpBB implementation details as is needed for password hashing.

Btw., as an alternative approach, I was briefly considering using the bare password drivers directly, without the manager class. This looks a lot more feasible, also because my only goal is to come up with a password-checking that needs no other features at all. However, as the above mentioned work-around was even simpler, I didn't pursue this any further.

So in summary, my original problem of making my DokuWiki auth plugin working with phpBB 3.1 again is solved via the above mentioned work-around. :D
rxu
Extensions Development Team
Posts: 3712
Joined: Wed Oct 25, 2006 12:46 pm
Location: Siberia, Russian Federation
Contact:

Re: phpBB 3.1: How to create a password manager instance?

Post by rxu »

CarstenF wrote:The DokuWiki auth plugin just calls this script via exec()
Using exec() is probably not a good practise, and it's not allowed by extensions writing policy (no idea if it makes any sense for you).

Anyway, although I don't know what exactly are you trying to achieve, you can build common.php-like file with the minimal code required to run container builder, and then get services you need, like that (PHPBB_ROOT_PATH should be set to the path you need, or dropped if you don't need it):

Code: Select all

define('IN_PHPBB', true);

define('PHPBB_ROOT_PATH', './phpBB/');

$phpbb_root_path = (defined('PHPBB_ROOT_PATH')) ? PHPBB_ROOT_PATH : './';
$phpEx = substr(strrchr(__FILE__, '.'), 1);

require($phpbb_root_path . 'includes/startup.' . $phpEx);
require($phpbb_root_path . 'phpbb/class_loader.' . $phpEx);

$phpbb_class_loader = new \phpbb\class_loader('phpbb\\', "{$phpbb_root_path}phpbb/", $phpEx);
$phpbb_class_loader->register();

$phpbb_config_php_file = new \phpbb\config_php_file($phpbb_root_path, $phpEx);
extract($phpbb_config_php_file->get_all());

require($phpbb_root_path . 'includes/functions.' . $phpEx);

// Set PHP error handler to ours
set_error_handler(defined('PHPBB_MSG_HANDLER') ? PHPBB_MSG_HANDLER : 'msg_handler');

$phpbb_class_loader_ext = new \phpbb\class_loader('\\', "{$phpbb_root_path}ext/", $phpEx);
$phpbb_class_loader_ext->register();

phpbb_load_extensions_autoloaders($phpbb_root_path);

// Set up container
$phpbb_container_builder = new \phpbb\di\container_builder($phpbb_config_php_file, $phpbb_root_path, $phpEx);
$phpbb_container = $phpbb_container_builder->get_container();

$phpbb_class_loader->set_cache($phpbb_container->get('cache.driver'));

$passwords_manager = $phpbb_container->get('passwords.manager');

var_dump($passwords_manager);
 
CarstenF
Registered User
Posts: 33
Joined: Sat Jun 28, 2008 8:55 pm

Re: phpBB 3.1: How to create a password manager instance?

Post by CarstenF »

Hi rxu,
rxu wrote:Using exec() is probably not a good practise, and it's not allowed by extensions writing policy (no idea if it makes any sense for you).
Yes, I'm aware of exec()'s inherent problems, and would certainly prefer to avoid it. At this time though, it allows me to cleanly and easily separate phpBB from DokuWiki code as described above, so I bite the bullet and use it for now.
Anyway, although I don't know what exactly are you trying to achieve, you can build common.php-like file with the minimal code required to run container builder, and then get services you need, like that (PHPBB_ROOT_PATH should be set to the path you need, or dropped if you don't need it):
Many thanks for posting this code! Unfortunately, while this already works much better than using common.php directly, I still cannot combine it with DokuWiki without getting conflicts, probably due to global variables such as $db (and possibly others). This is a good starting point for further test though. I'll continue trying to make it work, and will report here if successful.
nicofuma
3.2 Release Manager
3.2 Release Manager
Posts: 546
Joined: Sun Apr 13, 2014 1:47 am
Location: Grenoble - France

Re: phpBB 3.1: How to create a password manager instance?

Post by nicofuma »

You can also incapsulate the include of common within a function...
Member of phpBB Development-Team
No Support via PM
rxu
Extensions Development Team
Posts: 3712
Joined: Wed Oct 25, 2006 12:46 pm
Location: Siberia, Russian Federation
Contact:

Re: phpBB 3.1: How to create a password manager instance?

Post by rxu »

CarstenF wrote:I still cannot combine it with DokuWiki without getting conflicts, probably due to global variables such as $db (and possibly others).
Well, in the code given there're no global instances initialized excepting the container (neither $user nor $db and others), so you can do it manually naming them appropriately to avoid conflicts.
So it would be good to know what is actually conflicting.
CarstenF
Registered User
Posts: 33
Joined: Sat Jun 28, 2008 8:55 pm

Re: phpBB 3.1: How to create a password manager instance?

Post by CarstenF »

Thanks for the additional information!

I think I got a step further:
In my DokuWiki test system, I inserted a var_dump(debug_backtrace()); statement just before the trigger_error() that caused the premature end of DokuWiki. From the stack trace, it seems as if the DokuWiki code tries to access the global $_SERVER, whereupon phpBB's class deactivated_super_global becomes active and ends the script with a trigger_error() itself.

(The actual error message that phpBB uses (Illegal use of $_SERVER. You must use the request class or request_var() to access input data. [...]. This error message was generated by deactivated_super_global.) appears to be covered by yet something else in msg_handler(). I did not yet look into it, but likely something else goes wrong while it attempts to gather additional information for the debug output.)

Does that sound like a likely scenario? (I know too little about phpBB to judge for myself, maybe I'm totally off track.)

If so, what would be reasonable next steps?
Post Reply

Return to “Extension Writers Discussion”