On 8/7/07, Fermín Galán Márquez <[EMAIL PROTECTED]> wrote: > Hi! > > I'm trying to introduce conditional module loading in a Perl program, > but I'm experiencing problems. For example: > > ... > if ($some_condition) { > use ModuleA; > (doing something using ModuleA) > } > else { > use ModuleB; > (doing something using ModuleB) > } > > That is, if $some_condition is true then load the ModuleA, if false load > ModuleB. However, it doesn't seem to work this way and I've observed > (counterintuitively :) that both modules are always loaded (ModuleA and > ModuleB), no matter the value of $some_condition. > > Is it possible to do such "conditional module loading" in Perl? What am > I doing wrong? Some workaround? snip
This is because a use statement is syntactic sugar for a BEGIN block and all BEGIN blocks run before your program starts (there are five phases BEGIN, INIT, CHECK, your code, and END). There are two ways to conditionally load a module: write the BEGIN block, require, and import statements yourself or use the string form of eval*. However, this is rarely a good idea. Most of the time people want to do this so they can use different versions of the same module (a test vs a prod version). This is better handled though the use of the PERL5LIB environmental variable to override which module is found than through runtime hacks. There are only two other reasons I can think of to conditionally load a module: factory classes and namespace pollution issues. If you want to create a factory class then I would take a good look at how the DBI module is handling things and emulate it (in particular the connect and install_driver methods). If you are having namespace pollution issues it is better to fix the modules in question than to add runtime hacks to your code. There is one last case, but it doesn't involve loading A or B, it involves loading A if it is available and setting a flag as to whether it is available or not. For example, I once wrote a Gtk based SQL Editor/Runner. It had the ability to save the result sets to Microsoft Excel files, but not everyone on the team had Spreadsheet::WriteExcel installed, so I had to add a hack** like this to the code our $can_write_xls = eval "use Spreadsheet::WriteExcel; 1"; Then later in the code sub save_file_xls { my ($name, $rs) = @_; unless ($can_write_xls) { error("Spreadsheet::WriteExcel is not installed, please choose another format"); return; } #save the result set } * this is one of the few valid uses of string eval, but only when the string is hard coded. ** a more elegant solution would have been to prevent the user from being able to choose xls as a format, but the type was inferred from the extension and I was too lazy to change that. -- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED] http://learn.perl.org/