Re: Config files in CPAN modules?
by blue_cowdawg (Monsignor) on Jul 21, 2006 at 14:51 UTC
|
So what's a good way to deal with this?
One way I've solved this for some modules for general
use that I've authored for my job is to use
XML::Simple
to store my configs. If I have a program that is
invoking a module that needs to get to a config file
named "foo.pl" I simply create a file in
the directory the script lives in called "foo.xml"
and put the configuration information in there.
For instance I have some database access modules
that I use a lot and I store the information as such:
<disco_database>
<host>database-host.foo.com</host>
<dbname>disco</dbname>
<user>disco</dbname>
<password>duck</password>
</disco_database>
in my xml file. The module s written to invoke
XML::Simple
thusly:
package my_package;
use Class::DBI::Loader;
use XML::Simple;
| much handwaving...
sub new {
| more handwaving...
my $config = new XMLIn();
$self->{loader} =
Class::DBI::Loader -> new (
dsn => sprintf("dbi:%s:dbname=%s;host=%s",
$config->{disco_database}->{driver},
$config->{disco_database]->{dbname},
$config->{disco_database}->{host}),
user=>$config->{disco_database}->{user},
password=>$config->{disco_database}->{password}
| and so forth...
This has the added bonus that if I have change any of the
parameters that the script and its associated modules
need to live on change I don't have to search through
all the source code of the modules and script to change
variables.
In other cases (and actually, the project I call
"disco" is a good example of this) I put a config
file that is central for that module. If I ever have to
override it I make that a potential parameter for
instantiating the module. For instance:
| blah blah...
use IBM::Disco::HostEntry;
|
}
| blah
|
|
my $he = IBM::Disco::HostEntry->new{ config_file =>
qq(/path/to/file) );
|
When the module is instantiated it uses a default normally
but when the parameter config_file is
passed to the constructor I use that value instead.
Peter L. Berghold -- Unix Professional
Peter -at- Berghold -dot- Net; AOL IM redcowdawg Yahoo IM: blue_cowdawg
| [reply] [d/l] [select] |
Re: Config files in CPAN modules?
by eric256 (Parson) on Jul 21, 2006 at 15:30 UTC
|
Allow the user to sub-class your module and specify there configuration there (either as a reference to a file or the actual configuration
package My::Whatever;
use base Whatever;
sub config_file { "/usr/home/whatever" };
Seems like this gives the most power to everyone involved, even means that i could have several configurations and easy access to each.
| [reply] [d/l] |
Re: Config files in CPAN modules?
by philcrow (Priest) on Jul 21, 2006 at 14:37 UTC
|
Using Module::Build you can easily implement option 3. <shameless_plug> You could consider Gantry::Conf which gives considerable control to you and the user. </shameless_plug>
Phil | [reply] |
Re: Config files in CPAN modules?
by eXile (Priest) on Jul 21, 2006 at 18:31 UTC
|
Lots of software looks at several places for configfiles. Ie. a systemwide config and a user-specific config. Usually the user-specific config can override the systemwide config (exception is security-type options for instance). User-specific configs usually live in a users home directory (on UNIX as .<appname>rc files, like .cvsrc ).
My advice would be to consider using a 2 configfile type of approach, make it work in all three situations ( system-config + user-config, system-config + no user-config, no system-config + user-config ) and document what overrides what. | [reply] |
|
| [reply] |
|
I like the opposite -- save the original as 'config.orig' or 'config.old', or perhaps 'config.2006-07-21' for example. Then, save the new one as 'config'. It's pretty common, and it gives me a point of reference when I go to customize the new one.
What's really best, though, is when a package recognizes an obsolete config file and saves a 'config.old', a 'config.defaults', and a 'config' that has all the options from 'config.old' updated to match the new format and adds any settings from 'config.defaults' that used to be hardcoded and now aren't. Preferably, the new config file will be set up with things specified as much like the old version worked even if the default behaviors have changed, and with notes in the config file's comments stating what's changed and why. I can't name a CPAN module that does this currently, but I've used a few server and desktop applications that do this. That's one of the biggest things I like about the CMS I recommend for my clients, actually. When they upgrade it (or hopefully when they pay me to upgrade it), the upgrade is almost seamless.
| [reply] |
|
I think it's important to adhere to the system philosophy of placing config files. Some systems use /etc/, some systems use /usr/share, some systems use C:\USER_SETTINGS.
Unfortunately, there is no CPAN module that makes this transparent.
| [reply] |
Re: Config files in CPAN modules?
by kwaping (Priest) on Jul 21, 2006 at 14:59 UTC
|
| [reply] |
Re: Config files in CPAN modules?
by fmerges (Chaplain) on Jul 22, 2006 at 10:50 UTC
|
Hi,
Normally what I do is asking the user to provide the configuration, could be the config itself, or the path to the configuration file:
MyModule->new({ config_file => 'file.conf'}); # or
MyModule->new({ config => \%Config }); # or
MyModule->load_config($file); # etc...
This way it's up to the users script to decide which method he uses to provide the modules with the configuration settings.
Or going for well known places where the config files should be (linux -> /etc or /usr/local/etc) could be with subdir for the application itself or so; or the other way is to create a hierarchy for the application itself:
MyApp
|
+-- bin/
+-- etc/
+-- lib/
+-- docs/
But the most important thing of all is to DOCUMENT it. So that the user know how he must do instead of figuring it out. ;-)
Regards,
fmerges at irc.freenode.net
| [reply] [d/l] [select] |
Re: Config files in CPAN modules?
by adamk (Chaplain) on Jul 22, 2006 at 12:57 UTC
|
File::UserConfig might be one way to at least handle the initial case.
It installs to the module's "auto" share directory a default copy of the configuration file/directory.
When the program runs the first time for a new user, it copies it to the appropriate place.
For the upgrade case, perhaps what Ruby on Rails does for SQL schema. You have the config in a format you can manipulate, then write a series of classes that upgrade or downgrade from one version to the next.
Upgrading over a number of releases just means running each upgrade sequentially (with a backup first).
| [reply] |
Re: Config files in CPAN modules?
by Anonymous Monk on Jul 24, 2006 at 08:14 UTC
|
| [reply] |
Re: Config files in CPAN modules?
by hobbs (Monk) on Jul 24, 2006 at 18:49 UTC
|
Here's a "Clever" solution ;)
- Define a config format that begins with "1;\n__END__\n", and continues with whatever sort of config data you like.
- Have your users put "myapp.conf" anywhere in @INC. Optionally recognize a special environment var (say, MYAPP_HOME) to temporarily push onto @INC, just in case they don't feel like fooling around with PERL5LIB :)
- In your code:
{
local @INC = @INC;
unshift @INC, $ENV{MYAPP_HOME} if defined $ENV{MYAPP_HOME};
require 'myapp.conf';
}
open my $conf, '<', $INC{'myapp.conf'} or die 'Flaming death';
1 while <$conf> ne "__END__\n";
enjoy($conf);
| [reply] [d/l] |
Re: Config files in CPAN modules?
by pemungkah (Priest) on Jul 25, 2006 at 22:52 UTC
|
I don't know if you'd consider it "slick" or not, but CPAN.pm does something like this.
It installs a basic set of config data in CPAN/Config.pm, which can be overridden by data stored by the user in .cpan (which CPAN.pm silently creates and manages).
Whether this is sufficiently cross-platform enough for you I don't know, but it's certainly an alternative.
I'd be tempted to suggest Config::Std for config files, except for the fact that it doesn't handle a dynamic choice of config file well (you can always eval a 'use', though). | [reply] |
Re: Config files in CPAN modules?
by Anonymous Monk on Jul 25, 2006 at 08:55 UTC
|
Use option 2. And define an include-statement in your format. And your default config should be "include /etc/config" ;-)
All bases covered. | [reply] |