root/trunk/Build.PL

Revision 1279, 14.9 kB (checked in by dom, 3 weeks ago)

Add read_only config option to turn off edits on a guide completely (fixes #276)

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
Line 
1use strict;
2use lib "lib";
3use Getopt::Long;
4
5eval {
6    require Config::Tiny;
7    # OpenGuides::Build and OpenGuides::Config both use Config::Tiny.
8    require OpenGuides::Build;
9    require OpenGuides::Config;
10};
11
12die "Problem loading OpenGuides module or a missing module\n\n$@.\n" if $@;
13
14my $force;
15
16GetOptions('force' => \$force);
17
18unless ($force) {
19        print <<EOF;
20
21Beginning install process... if you already have an OpenGuides
22configuration file and you don't want to have to type in all your config
23parameters over again, abort this process now, copy that file to this
24directory, and start again.
25
26EOF
27
28my $continue = Module::Build->y_n("Continue with install?", "y");
29exit 0 unless $continue;
30}
31
32my $existing_config_file = 'wiki.conf';
33my $existing_config;
34
35if (-f $existing_config_file) {
36    $existing_config = OpenGuides::Config->new(file => $existing_config_file);
37} else {
38    print <<EOF;
39No existing configuration file found; assuming this is a new install.
40See the message above if this isn't correct.
41
42EOF
43    $existing_config = OpenGuides::Config->new();
44}
45
46my %yn_vars = map { $_ => 1 }
47   qw(use_plucene enable_page_deletion navbar_on_home_page backlinks_in_title
48      moderation_requires_password enable_node_image enable_common_categories
49      enable_common_locales recent_changes_on_home_page
50      random_page_omits_locales random_page_omits_categories
51      content_above_navbar_in_html show_gmap_in_node_display force_wgs84
52      send_moderation_notifications read_only);
53
54my $skip_config = $force ? 'y' : Module::Build->y_n("Skip OpenGuides configuration?", "n");
55if ( $skip_config ) {
56    print <<EOF;
57===========================================================================
58Skipping OpenGuides configuration - any configuration options previously
59saved will be used instead.  You may tweak your configuration now by
60editing the 'wiki.conf' file produced by this script.
61===========================================================================
62EOF
63}
64
65my @answers;
66
67# It is an ancient Configurer, and he chooseth one of three.
68my $dbtype;
69my $dbtype_qu = $existing_config->dbtype__qu;
70if ( $skip_config ) {
71    $dbtype = $existing_config->dbtype;
72} else {
73    until ( $dbtype ) {
74        my $def = $existing_config->dbtype;
75        $dbtype = Module::Build->prompt("\n$dbtype_qu", $def);
76        $dbtype = lc($dbtype);
77        $dbtype =~ s/^\s*//;
78        $dbtype =~ s/\s*$//;
79        unless ( $dbtype eq "postgres" or $dbtype eq "mysql"
80                 or $dbtype eq "sqlite" ) {
81            undef $dbtype;
82        }
83    }
84}
85
86# Check they have the relevant DBD driver installed.
87my %drivers = ( postgres => "DBD::Pg",
88                mysql    => "DBD::mysql",
89                sqlite   => "DBD::SQLite",
90              );
91eval "require $drivers{$dbtype}";
92warn "$drivers{$dbtype} is needed to run a $dbtype database" if $@;
93
94push @answers, { question => $dbtype_qu,
95                 variable => "dbtype",
96                 value    => $dbtype };
97
98my $install_directory; # used to suggest template paths
99my $use_plucene = 1; # keep track of this so we know what to put in prereqs
100my $centre_lat = ''; # contains centre lat derived from Google Maps URL
101foreach my $var ( qw(
102   dbname dbuser dbpass dbhost dbport script_name
103   install_directory template_path custom_template_path script_url
104   custom_lib_path use_plucene indexing_directory enable_page_deletion
105   admin_pass stylesheet_url site_name navbar_on_home_page
106   recent_changes_on_home_page random_page_omits_locales
107   random_page_omits_categories content_above_navbar_in_html home_name
108   site_desc default_city default_country contact_email default_language
109   formatting_rules_node backlinks_in_title gmaps_api_key centre_long
110   centre_lat show_gmap_in_node_display default_gmaps_zoom
111   default_gmaps_search_zoom force_wgs84 google_analytics_key
112   licence_name licence_url licence_info_url moderation_requires_password
113   enable_node_image enable_common_categories enable_common_locales
114   spam_detector_module host_checker_module static_path static_url
115   send_moderation_notifications read_only
116  ) ) {
117    my $q_method = $var . "__qu";
118    my $qu  = $existing_config->$q_method;
119    my $type = $yn_vars{$var} ? "y_n" : "";
120    my $def = $existing_config->$var;
121    my $val = $def;
122
123    # Override dbname question for SQLite only.
124    if ( $dbtype eq "sqlite" and $var eq "dbname" ) {
125        $qu = "what's the full filename of the SQLite database this site runs on?";
126    }
127
128    if ( $dbtype eq "sqlite" and
129         ( $var eq "dbuser" or $var eq "dbpass" or $var eq "dbhost" or
130           $var eq "dbport")
131       ) {
132        print "$var not relevant for SQLite... skipping...\n"
133            unless $skip_config;
134        push @answers, { question => $qu,
135                            variable => $var,
136                         value    => "not-used" };
137        next;
138    }
139
140    # We don't ask this for new installs as Search::InvertedIndex is
141    # deprecated
142    if ( $var eq "use_plucene" and $existing_config->$var == 1) {
143        print "Skipping question about plucene\n"
144            unless $skip_config;
145        push @answers, { question => $qu,
146                         variable => $var,
147                         value => 1 };
148        next;
149    }
150
151    # Make sensible suggestions for template paths if we don't already
152    # have them stored.  Not really a default, but a useful hint/shortcut.
153    if ( $var eq "template_path" && !defined $existing_config->$var ) {
154        $def = $install_directory;
155        $def .= "/" unless $def =~ m|/$|;
156        $def .= "templates";
157    }
158    if ( $var eq "custom_template_path" && !defined $existing_config->$var ) {
159        $def = $install_directory;
160        $def .= "/" unless $def =~ m|/$|;
161        $def .= "custom-templates";
162    }
163
164    # If a Google Maps URL was provided last time we know the centre_lat
165    if ( $var eq 'centre_lat' && $centre_lat ) {
166        $val = $centre_lat;
167        next;
168    }   
169
170    # Here is where we actually ask the questions.
171    unless ( $skip_config ) {
172        if ( $type eq "y_n" ) {
173            # may be stored as true/false integer value
174            if ( $def =~ /^\d+$/ ) {
175                $def = $def ? "y" : "n";
176            }
177            $val = Module::Build->y_n("\n$qu ", $def);
178        } else {
179            $val = Module::Build->prompt("\n$qu ", $def);
180        }
181    }
182
183    # Allow user to use a Google Maps URL rather than enter lat/long by hand.
184    # We assume centre_long is being asked for first; ensure so in big list above.
185    if ( $var eq 'centre_long' ) {
186        if ( $val =~ /ll=([-\d.]+),([-\d.]+)/ ) {
187            print "Got a Google Maps URL with centre long,lat: [$1, $2]\n";
188            $val = $1;
189            $centre_lat = $2;
190        }
191    }
192
193    # Store install_directory so we can use it to suggest template paths.
194    $install_directory = $val if $var eq "install_directory";
195
196    # Keep track of chosen search method so we know what to put in prereqs.
197    # From Module::Build docs: ->y_n returns a Perl boolean true or false.
198    $use_plucene = 1 if $var eq "use_plucene" and $val;
199
200    # Make sure that script_url ends in a /
201    if ( $var eq "script_url" and $val !~ /\/$/ ) {
202        $val .= "/";
203    }
204
205    push @answers, { question => $qu,
206                     variable => $var,
207                     value    => $val };
208}
209
210# Now deal with the geo stuff.
211my $geo_handler;
212my $geo_handler_qu = "Distance calculation methods available are:"
213                   . "\n  1) British National Grid"
214                   . "\n  2) Irish National Grid"
215                   . "\n  3) UTM ellipsoid"
216                   . "\nWhich would you like to use?";
217
218if ( $skip_config ) {
219    # We default to GB National Grid for historical reasons.
220    $geo_handler = $existing_config->geo_handler;
221} else {
222    my $choice;
223    until ( $choice ) {
224        my $def = $existing_config->geo_handler;
225        $choice = Module::Build->prompt("\n".$geo_handler_qu, $def);
226        $choice =~ s/^\s*//;
227        $choice =~ s/\s*$//;
228        unless ( $choice eq "1" or $choice eq "2" or $choice eq "3" ) {
229            undef $choice;
230        }
231    }
232    $geo_handler = $choice;
233}
234
235$geo_handler_qu =~ s/\n//gs;
236push @answers, {
237                 question => $geo_handler_qu,
238                 variable => "geo_handler",
239                 value    => $geo_handler,
240               };
241
242if ( $geo_handler eq "3" ) {
243    my $qu = $existing_config->ellipsoid__qu;
244    my $ellipsoid;
245    if ( $skip_config ) {
246        $ellipsoid = $existing_config->ellipsoid;
247    } else {
248        my $def = $existing_config->ellipsoid;
249        $ellipsoid = Module::Build->prompt("\n".$qu, $def);
250        $ellipsoid =~ s/^\s*//;
251        $ellipsoid =~ s/\s*$//;
252    }
253    push @answers, {
254                     question => $qu,
255                     variable => "ellipsoid",
256                     value    => $ellipsoid,
257                   };
258}
259
260# Create a user-friendly config file from answers to prompts.
261open FILE, ">wiki.conf" or die "Can't open wiki.conf for writing: $!";
262foreach my $ans (@answers) {
263    print FILE "# $ans->{question}\n";
264    print FILE "$ans->{variable} = $ans->{value}\n\n";
265}
266close FILE or die "Can't close wiki.conf: $!";
267
268# We currently only support Plucene for new installs, but may support
269# others in future
270my $search_module = $use_plucene ? "Plucene" : "Search::InvertedIndex";
271
272# Create the build object.
273my $build = OpenGuides::Build->new(
274    sign => 1,
275    dist_name => "OpenGuides",
276    dist_abstract => "A complete web application for managing a collaboratively-written guide to a city or town.",
277    module_name => "OpenGuides",
278    dist_version_from => "wiki.cgi",
279    license => "perl",
280    requires => {
281        'Algorithm::Diff'                     => '0.13'# for sdiff
282        'CGI'                                 => '2.92'# avoid escapeHTML bug
283        'CGI::Carp'                           => 0,
284        'CGI::Cookie'                         => 0,
285        'Wiki::Toolkit'                       => '0.77',
286        'Wiki::Toolkit::Feed::Atom'           => 0,
287        'Wiki::Toolkit::Feed::RSS'            => 0,
288        'Wiki::Toolkit::Formatter::UseMod'    => 0,
289        'Wiki::Toolkit::Plugin::Categoriser'  => 0,
290        'Wiki::Toolkit::Plugin::Diff'         => 0,
291        'Wiki::Toolkit::Plugin::JSON'         => 0,
292        'Wiki::Toolkit::Plugin::Locator::Grid'=> 0,
293        'Wiki::Toolkit::Plugin::RSS::Reader'  => 0,
294        'Class::Accessor'                     => 0,
295        'Config::Tiny'                        => 0,
296        'Data::Dumper'                        => 0,
297        $drivers{$dbtype}                     => 0,
298        'File::Spec::Functions'               => 0,
299        'File::Temp'                          => 0,
300                'Geo::Coordinates::UTM'               => 0,
301        'Geography::NationalGrid'             => 0,
302        'HTML::Entities'                      => 0,
303        'LWP::Simple'                         => 0,
304        'MIME::Lite'                          => 0,
305        'Parse::RecDescent'                   => 0,
306        $search_module                        => 0,
307        'POSIX'                               => 0,
308        'Template'                            => '2.15', # for hash.delete and string.remove vmethods
309        'Time::Piece'                         => 0,
310        'URI::Escape'                         => 0,
311        'XML::RSS'                            => 0,
312        'Data::Validate::URI'                 => 0,
313        'Net::Netmask'                        => 0,
314        'List::Util'                          => 0,
315        },
316    build_requires => {
317        'Module::Build' => '0.26', # API change for accessing config data
318        'Class::Accessor'                     => 0,
319        'Config::Tiny'                        => 0,
320        'Data::Dumper'                        => 0,
321        },
322    configure_requires => {
323        'Config::Tiny'                        => 0,
324        'Class::Accessor'                     => 0,
325        'Module::Build' => '0.26', # API change for accessing config data
326        },
327    recommends => {
328        'DBD::SQLite'                         => 0, # for testing
329        'Test::HTML::Content'                 => 0, # for testing, oddly enough
330        'Wiki::Toolkit::Plugin::Ping' => 0, # for pinging external services
331        'Geo::HelmertTransform'  => 0,      # for correct WGS84 lat/long
332        'Test::Pod'                           => 0,
333
334    },
335    dynamic_config => 1,
336    create_makefile_pl => "passthrough"
337);
338
339$build->add_to_cleanup( "t/indexes/" );
340$build->add_to_cleanup( "t/node.db" );
341$build->add_to_cleanup( "t/prefs.db" );
342$build->add_to_cleanup( "t/templates/tmp/" );
343
344# Tell OpenGuides::Build which additional scripts and templates to install.
345$build->config_data( __extra_scripts =>
346                      [ "wiki.conf", "preferences.cgi", "search.cgi",
347                        "newpage.cgi" ] );
348$build->config_data( __templates     => [
349                      "admin_home.tt",
350                      "admin_revert_user.tt",
351                      "backlink_results.tt",
352                      "banner.tt",
353                      "blacklisted_host.tt",
354                      "delete_confirm.tt",
355                      "delete_done.tt",
356                      "delete_password_wrong.tt",
357                      "differences.tt",
358                      "display_metadata.tt",
359                      "edit_form.tt",
360                      "edit_form_actions.tt",
361                      "error.tt",
362                      "footer.tt",
363                      "header.tt",
364                      "home_node.tt",
365                      "map_index.tt",
366                      "missing_metadata.tt",
367                      "moderate_confirm.tt",
368                      "moderate_password_wrong.tt",
369                      "navbar.tt",
370                      "navbar_categories.tt",
371                      "navbar_locales.tt",
372                      "navbar_help.tt",
373                      "navbar_admin.tt",
374                      "navbar_home_link.tt",
375                      "navbar_options.tt",
376                      "navbar_revision_info.tt",
377                      "navbar_search.tt",
378                      "navbar_this_page.tt",
379                      "navbar_tools.tt",
380                      "needing_moderation.tt",
381                      "newpage.tt",
382                      "node.tt",
383                      "node_history.tt",
384                      "node_image_fields.tt",
385                      "node_photo_notes.tt",
386                      "node_rdf.tt",
387                      "openguides_information_boxes.tt",
388                      "preferences.tt",
389                      "random_page_failure.tt",
390                      "rdf_index.tt",
391                      "read_only.tt",
392                      "recent_changes.tt",
393                      "search_results.tt",
394                      "site_index.tt",
395                      "search.tt",
396                      "spam_detected.tt",
397                      "userstats.tt",
398                      "wanted_pages.tt"
399    ] );
400
401$build->config_data( __static_files => [
402    # XXX to be supplied when we have some
403    ] );
404
405# Finally write the build script.
406$build->create_build_script;
Note: See TracBrowser for help on using the browser.