Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 7 years ago.
Improve this question
Is there any preferred naming convention for perl modules?
For example, what is more common practice in perl world - SomeModule or Some::Module? Maybe there are some cases when one style is better than another?
If you take a look at CPAN you will see that, by and large, module names are organised into top-level categories for the first segment of the name, and a distinctive name within that category for each module. For instance, the top ten categories (by distribution count) are
Net
App
WWW
Test
Data
Catalyst
Acme
Text
Dist
HTML
The second part of the name is usually either to identify it within all other modules of that category (such as HTML::TreeBuilder), or as a subdivision of a large category (like Net::FTP::* modules)
There may be a third section to the name, which represents either a component module of an overall set (for example DBIx::Class::Relationship and DBIx::Class::ResultSet ) or a separate module that has been subclassed from another (like HTML::TreeBuilder::XPath)
For too long there has been no control over the names of the modules uploaded to CPAN, and some parts of it can be a bit of a mess. However it does represent a defined and growing set of names that you should try to avoid with your own package identifiers. Your example isn't very realistic, but I would probably go with just SomeModule, as just inserting a pair of colons between every pair of words is definitely not the way to go
If you have multiple modules you can start gathering them together into categories, and it would help if you used a top-level category (like Site or Company) that avoided clashes with any CPAN modules that you could use. Examples could be Site::Utils::Matrices and Site::Utils::StringProcessing
The one major rule is that your package names should be in CamelCase, as all lower-case names are reserved for Perl pragmas
Since stevieb's solution has been deleted, it's worth me reposting a link to brian d foy's excellent On The Naming of Modules which makes many salient points
It depends whether or not you intend to put your module on CPAN. If you are putting it on CPAN, you should be reading perldoc perlmodstyle anyway. If however you are just using the modules privately, the most relevant point is that the :: is used to signify a directory hierarchy. Ex:
use lib 'my_module';
use Some::Module;
This loads a module named "Module.pm" in a folder called "Some", in the directory "my_module".
This is not to be confused with package names, which often also use ::. With package names, :: is usually used to designate conceptual hierarchies or relationships between packages, such as classes and sub-classes.
Related
I have checked
On the Naming of Modules,
perldoc perlvar and
perldoc perlmod
but can not find best practices for naming modules whose name is an acronym: SMTP, ORM.
At once on CPAN both variants names are seen: SMTP and Smtp
If my new module name is an acronymthen
what would be the better name for it: My::Module::Abcd or My::Module::ABCD?
In naming convention for Perl, aside from reserved you get to choose a naming convention that can be understood among those you work with. No module that starts with keywords or reserved prefix will be accepted to CPAN or the core.
So you can either choose to adopt My::Module::Abcd or My::Module::ABCD as long as you chose to adopt one that will helping people find your module.
Alternatively, you can use an underscore in the top-level name (like My_Corp::Session or just My_Session). All categories with an underscore have also been reserved. (This is mentioned in perlmodlib, under "Select a name for the module".)
Note that both those reservations apply only to the top-level name. For example, there are CPAN modules named Time::Local and Text::CSV_XS. But Local::Time and Text_CSV::XS are reserved names and would not be accepted on CPAN.
Naming modules after your company is fine too. (Well, unless you work for some really generic sounding company.) Using the reverse domain name is probably overkill, unless you intend to distribute your modules to others. (But in that case, you should probably register a normal module name.)
You might want to take a long at How do I choose a package name for a custom Perl module that does not collide with builtin or CPAN packages names?
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 5 years ago.
Improve this question
How to write PowerShell script for attached screenshots? I am trying to run and configure installer via PowrShell.
There is no guarantee that this will be possible, as it's possible to (incorrectly) author a Windows Installer package in a way that rejects this. But in many cases, it suffices to find the feature names, property names, and property values involved in the settings you wish to control.
Note that to approach 100% correctness, you will have to consider all properties that get set during the normal UI sequence, or consult documentation provided by the author of the package.
Feature Selection
You can specify which features will be installed by listing their names in the special properties: ADDLOCAL, REMOVE, ADDSOURCE, etc. To find their names, consult documentation, or examine the Feature table of the .msi file.
Note that doing this can evade attempts the author might have made to ensure proper selection of features (for some meaning of proper), and it will also set the property Preselected, which offers the author a way to tweak the behavior in this situation.
Configuration
Windows Installer dialog boxes are all defined in the Dialog table and Control table, but the results can also be augmented by the ControlEvent table and custom actions. In the common case you can look at the Control table to identify the Property name associated with the values you wish to set. For example, an Edit control with Property value TESTPROP will set the property TESTPROP to whatever you type into its associated edit box. Check boxes cross reference the CheckBox table for the value they will set or clear (often simply 1), etc. Radio button groups cross reference the RadioButton table for their values.
Sometimes intermediate values may be set by the controls, and their eventual target properties are then adjusted by a custom action invoked by a Control Event or a sequenced Custom Action.
Alternatives
Instead of poking into the inner bowels of the installation package you are trying to automate, documentation from its author is often much safer. When that's missing, you can find a tool that helps you generate a response transform (much easier to use, but fallible), a tool that helps you explore the tables I described above (harder, but gives as complete an understanding as you can get), or you can create and examine a verbose log file created while installing the package with the settings you desire (middle of the road).
The log file will include all the properties and feature names you need to set on a command line, but probably will include several you do not need to set. Figuring out which is which can still be difficult.
End Result
In the end, you will end up with a command line including some of the following parts. I'm using italics to indicate the parts whose names or values I do not know; those should be substituted with correct values. I've also added parentheticals to explain what each part does; those should be omitted. I've broken the command line across multiple screen lines for clarity.
msiexec /i the.msi /qn (install the.msi silently)
ADDLOCAL="desired,features,here" (select these features)
REMOVE="undesired,features,here" (optional; explicilty unselect these features)
SOMEPROP1="some value1" (specify the value of one or more properties)
SOMEPROP2="some value2"
SOMEPROP3="some value3" (specify more properties as necessary)
Note that property names are almost always going to be upper case and may include underscores. Feature names can be mixed case but will not include spaces. Property values can be anything, and must be quoted if they include spaces or other special characters.
If you plan to use this across multiple systems, note that differences in the target system can affect the correct command lines to use. This is relatively rare; when it happens, it's likely to be due to differing versions of Windows or differing availability of optional dependencies.
I want to separate all the common subroutines in another file to save up some space and to tidy up each files. Then just use require() to call a subroutine.
for ex.
sub greet{
print "Hi there\n";
}
which I added and called in Script1.pl, Script2.pl and Script3.pl.
What are the pro's and con's on separating subroutines to another file?
I'm sorry for my grammar. Hope you'd help me understand.
Whenever you have code that is used by more than one script, it generally ought to be split into a library, as you have described. There are many ways to do this, and each has its own advantages and disadvantages which are beyond the scope of your specific question.
So to address your specific question as to pros and cons of moving functionality into a library, lets start with
Pros
Because you have less duplicate code it is easier to
Debug your code (fewer places for bugs to exist)
Update your code (you don't have to edit the same functionality in 10 places)
It makes it easier to share your library functions with other people, or just other projects
It encourages better design, by making you think modularly
Saves space (a pretty minor point, with modern storage media)
Cons
It's harder to distribute your code--you must make sure you distribute all required files as well.
It's not as easy to see your entire code at once--only an issue for small projects, where you even have the option of fitting the entire project on the screen (or in your head) at once
General rule of thumb: Except for very small and/or self-contained projects, use libraries.
I have read the perldoc on modules, but I don't see a recommendation on naming a package so it won't collide with builtin or CPAN module/package names.
In the past, to develop a local Session.pm module, I have created a local directory using my company's name, such as:
package Company::Session;
... and Session.pm would be found in directory Company/.
But I'm just not a fan of this naming convention. I would rather name the package hierarchy closer to the functionality of the code. But that's how it's done on CPAN generally...
I feel like I am missing something fundamental. I also looked in Damian's Perl Best Practices but I may not have been looking in the right place...
Any recommendations on avoiding package namespace collisions the right way?
Update w/ Related Question: if there is a package name conflict, how does Perl choose which one to use? Thanks everyone.
The namespace Local:: has been reserved for just this purpose. No module that starts with that prefix will be accepted to CPAN or the core. Alternatively, you can use an underscore in the top-level name (like My_Corp::Session or just My_Session). All categories with an underscore have also been reserved. (This is mentioned in perlmodlib, under "Select a name for the module".)
Note that both those reservations apply only to the top-level name. For example, there are CPAN modules named Time::Local and Text::CSV_XS. But Local::Time and Text_CSV::XS are reserved names and would not be accepted on CPAN.
Naming modules after your company is fine too. (Well, unless you work for some really generic sounding company.) Using the reverse domain name is probably overkill, unless you intend to distribute your modules to others. (But in that case, you should probably register a normal module name.)
How Perl resolves a conflict:
Perl searches the directories in #INC for a module with the specified name. The first module found is the one used. So the order of directories in #INC determines which module would be used (if you have modules with the same name installed in different locations).
perl -V will report the contents of #INC (the highest-priority directories are listed first). But there are lots of ways to manipulate #INC at runtime, too.
BTW, Raku can handle multiple modules with the same name by different authors, and even use more than one in a single program. That's a different solution.
There is nothing wrong with naming your internal modules after your company; I always do this. 90% of my code ends up on CPAN, so it has "normal" names, but the internal stuff is always starts with ClientName::.
I'm sure everyone else does this too.
What's wrong with just picking a name for your package that you like and then googling "perl the-name-you-picked"?
The #INC variable contains a list of directories to in which to look for modules. It starts with the first entry and then moves on to next if it doesn't find the request module. #INC has a default value that created when perl is compiled, but you can can change it with the PERL5LIB environment variable, the lib pragma, and directly manipulating the #INC array in a BEGIN block:
#!/usr/bin/perl
BEGIN {
#INC = (); #no modules can be found
}
use strict; #error: Can't locate strict.pm in #INC (#INC contains:)
If you need the maximum level of certainty that your module name will not conflict with someone else's you can take a page from Java's book: name the module with the name of the companies domain. So if you work for Example, Inc. and their domain name is example.com, you would name your HTML parser module Com::Example::HTML::Parser or Example::Com::HTML::Parser. The benefit of the first is that if you have multiple subunits they can all have their own name space, but the modules will still sort together:
Com::Example::Biz::FindCustomers
Com::Example::IT::ParseLogs
Com::Example::QA::TestServer
but it does look odd at first.
(I know this post is old, but as I've had to sort this out in the past few months, I thought I'd weigh in)
At work we decided that 'Local::' felt too geographic. CompanyName:: had some problems for us too that aren't development related, I'll skip those, though I will say that CompanyName is long when you have to type it dozens of times.
So we settled on 'Our::'. Sure, we're not 'CPAN Safe' as there could be the day when we want to use a CPAN module with the Our:: prefix. But it feels nice.
Our::Data is our Class::DBI module
Our::App is our generic app framework that does config handling and Getopt stuff
Nice to read and nice to type.
I have read the perldoc on modules, but I don't see a recommendation on naming a package so it won't collide with builtin or CPAN module/package names.
In the past, to develop a local Session.pm module, I have created a local directory using my company's name, such as:
package Company::Session;
... and Session.pm would be found in directory Company/.
But I'm just not a fan of this naming convention. I would rather name the package hierarchy closer to the functionality of the code. But that's how it's done on CPAN generally...
I feel like I am missing something fundamental. I also looked in Damian's Perl Best Practices but I may not have been looking in the right place...
Any recommendations on avoiding package namespace collisions the right way?
Update w/ Related Question: if there is a package name conflict, how does Perl choose which one to use? Thanks everyone.
The namespace Local:: has been reserved for just this purpose. No module that starts with that prefix will be accepted to CPAN or the core. Alternatively, you can use an underscore in the top-level name (like My_Corp::Session or just My_Session). All categories with an underscore have also been reserved. (This is mentioned in perlmodlib, under "Select a name for the module".)
Note that both those reservations apply only to the top-level name. For example, there are CPAN modules named Time::Local and Text::CSV_XS. But Local::Time and Text_CSV::XS are reserved names and would not be accepted on CPAN.
Naming modules after your company is fine too. (Well, unless you work for some really generic sounding company.) Using the reverse domain name is probably overkill, unless you intend to distribute your modules to others. (But in that case, you should probably register a normal module name.)
How Perl resolves a conflict:
Perl searches the directories in #INC for a module with the specified name. The first module found is the one used. So the order of directories in #INC determines which module would be used (if you have modules with the same name installed in different locations).
perl -V will report the contents of #INC (the highest-priority directories are listed first). But there are lots of ways to manipulate #INC at runtime, too.
BTW, Raku can handle multiple modules with the same name by different authors, and even use more than one in a single program. That's a different solution.
There is nothing wrong with naming your internal modules after your company; I always do this. 90% of my code ends up on CPAN, so it has "normal" names, but the internal stuff is always starts with ClientName::.
I'm sure everyone else does this too.
What's wrong with just picking a name for your package that you like and then googling "perl the-name-you-picked"?
The #INC variable contains a list of directories to in which to look for modules. It starts with the first entry and then moves on to next if it doesn't find the request module. #INC has a default value that created when perl is compiled, but you can can change it with the PERL5LIB environment variable, the lib pragma, and directly manipulating the #INC array in a BEGIN block:
#!/usr/bin/perl
BEGIN {
#INC = (); #no modules can be found
}
use strict; #error: Can't locate strict.pm in #INC (#INC contains:)
If you need the maximum level of certainty that your module name will not conflict with someone else's you can take a page from Java's book: name the module with the name of the companies domain. So if you work for Example, Inc. and their domain name is example.com, you would name your HTML parser module Com::Example::HTML::Parser or Example::Com::HTML::Parser. The benefit of the first is that if you have multiple subunits they can all have their own name space, but the modules will still sort together:
Com::Example::Biz::FindCustomers
Com::Example::IT::ParseLogs
Com::Example::QA::TestServer
but it does look odd at first.
(I know this post is old, but as I've had to sort this out in the past few months, I thought I'd weigh in)
At work we decided that 'Local::' felt too geographic. CompanyName:: had some problems for us too that aren't development related, I'll skip those, though I will say that CompanyName is long when you have to type it dozens of times.
So we settled on 'Our::'. Sure, we're not 'CPAN Safe' as there could be the day when we want to use a CPAN module with the Our:: prefix. But it feels nice.
Our::Data is our Class::DBI module
Our::App is our generic app framework that does config handling and Getopt stuff
Nice to read and nice to type.