Unintentional duplication of Set::Scalar requirement.
[koha.git] / Install.pm
1 package Install; #assumes Install.pm
2
3 use strict;
4 require Exporter;
5
6 use vars qw($VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS);
7
8 # set the version for version checking
9 $VERSION = 0.01;
10
11 @ISA = qw(Exporter);
12 @EXPORT = qw(   &checkperlmodules
13                 &getmessage
14                 &showmessage
15                 &releasecandidatewarning
16                 &getinstallationdirectories
17                 &getdatabaseinfo
18                 &getapacheinfo
19                 &getapachevhostinfo
20                 &updateapacheconf
21                 &basicauthentication
22                 &installfiles
23                 &databasesetup
24                 &restartapache
25                 &loadconfigfile
26                 );
27
28
29 my $messages;
30 $messages->{'continuing'}->{en}="Great!  Continuing setup.\n\n";
31 $messages->{'WelcomeToKohaInstaller'}->{en}=qq|
32 =================================
33 = Welcome to the Koha Installer =
34 =================================
35
36 Welcome to the Koha install script!  This script will prompt you for some
37 basic information about your desired setup, then install Koha according to
38 your specifications.  To accept the default value for any question, simply hit
39 Enter at the prompt.
40
41 Please be sure to read the documentation, or visit the Koha website at 
42 http://www.koha.org for more information.
43
44 Are you ready to begin the installation? (Y/[N]): |;
45 $messages->{'ReleaseCandidateWarning'}->{en}=qq|
46 =====================
47 = RELEASE CANDIDATE =
48 =====================
49
50 WARNING WARNING WARNING WARNING WARNING
51
52 You are about to install Koha version %s.  This version of Koha is a
53 release candidate.  It is not intended to be installed on production systems.
54 It is being released so that users can test it before we release a final
55 version.
56
57 Are you sure you want to install Koha %s? (Y/[N]): |;
58 $messages->{'WatchForReleaseAnnouncements'}->{en}=qq|
59
60 Watch for announcements of Koha releases on the Koha mailing list or the Koha
61 web site (http://www.koha.org/).
62
63 |;
64
65 $messages->{'NETZ3950Missing'}->{en}=qq|
66
67 The Net::Z3950 module is missing.  This module is necessary if you want to use
68 Koha's Z39.50 client to download bibliographic records from other libraries.
69 To install this module, you will need the yaz client installed from
70 http://www.indexdata.dk/yaz/ and then you can install the perl module with the
71 command:
72
73 perl -MCPAN -e 'install Net::Z3950'
74
75 Press the <ENTER> key to continue: |;
76
77 $messages->{'CheckingPerlModules'}->{en}=qq|
78
79 ==================
80 = PERL & MODULES =
81 ==================
82
83 Checking perl modules ...
84 |;
85
86 $messages->{'PerlVersionFailure'}->{en}="Sorry, you need at least Perl %s\n";
87
88 $messages->{'MissingPerlModules'}->{en}=qq|
89
90 ========================
91 = MISSING PERL MODULES =
92 ========================
93
94 You are missing some Perl modules which are required by Koha.
95 Once these modules have been installed, rerun this installer.
96 They can be installed by running (as root) the following:
97
98 %s
99 |;
100 $messages->{'AllPerlModulesInstalled'}->{en}=qq|
101
102 ==============================
103 = ALL PERL MODULES INSTALLED =
104 ==============================
105
106 All mandatory perl modules are installed.
107
108 Press <ENTER> to continue: |;
109 $messages->{'KohaVersionInstalled'}->{en}="You currently have Koha %s on your system.";
110 $messages->{'KohaUnknownVersionInstalled'}->{en}="I am not able to determine what version of Koha is installed now.";
111 $messages->{'KohaAlreadyInstalled'}->{en}=qq|
112 ==========================
113 = Koha already installed =
114 ==========================
115
116 It looks like Koha is already installed on your system (/etc/koha.conf exists
117 already).  If you would like to upgrade your system to %s, please use
118 the koha.upgrade script in this directory.
119
120 %s
121
122 |;
123 $messages->{'GetOpacDir'}->{en}=qq|
124 ==================
125 = OPAC DIRECTORY =
126 ==================
127
128 Please supply the directory you want Koha to store its OPAC files in.  This
129 directory will be auto-created for you if it doesn't exist.
130
131 OPAC Directory [%s]: |;
132
133 $messages->{'GetIntranetDir'}->{en}=qq|
134 =================================
135 = INTRANET/LIBRARIANS DIRECTORY =
136 =================================
137
138 Please supply the directory you want Koha to store its Intranet/Librarians
139 files in.  This directory will be auto-created for you if it doesn't exist.
140
141 Intranet Directory [%s]: |;
142
143 $messages->{'GetKohaLogDir'}->{en}=qq|
144 ======================
145 = KOHA LOG DIRECTORY =
146 ======================
147
148 Specify a log directory where any Koha daemons can create log files.
149
150 Koha Log Directory [%s]: |;
151
152 $messages->{'AuthenticationWarning'}->{en}=qq|
153 ==================
154 = Authentication =
155 ==================
156
157 This release of Koha has a new authentication module.  If you are not already
158 using basic authentication on your intranet, you will be required to log in to
159 access some of the features of the intranet.  You can log in using the userid
160 and password from the /etc/koha.conf configuration file at any time.  Use the
161 "Members" module to add passwords for other accounts and set their permissions.
162
163 [NOTE PERMISSIONS ARE NOT COMPLETED AS OF THIS RELEASE.  Do not give passwords
164 to any patrons unless you want them to have full access to your intranet.]
165
166 Press the <ENTER> key to continue: |;
167
168 $messages->{'Completed'}->{en}=qq|
169 ==============================
170 = KOHA INSTALLATION COMPLETE =
171 ==============================
172
173 Congratulations ... your Koha installation is complete!
174
175 You will be able to connect to your Librarian interface at:
176
177    http://%s\:%s/
178
179 and the OPAC interface at :
180
181    http://%s\:%s/
182
183
184 Be sure to read the INSTALL, and Hints files. 
185
186 For more information visit http://www.koha.org
187
188 Press <ENTER> to exit the installer: |;
189
190 sub releasecandidatewarning {
191     my $message=getmessage('ReleaseCandidateWarning', [$::kohaversion, $::kohaversion]);
192     my $answer=showmessage($message, 'yn', 'n');
193
194     if ($answer =~ /y/i) {
195         print getmessage('continuing');
196     } else {
197         my $message=getmessage('WatchForReleaseAnnouncements');
198         print $message;
199         exit;
200     };
201 }
202
203
204 #
205 # Test for Perl and Modules
206 #
207 #
208 sub checkperlmodules {
209     my $message = getmessage('CheckingPerlModules');
210     showmessage($message, 'none');
211     
212     unless (eval "require 5.6.0") {
213         die getmessage('PerlVersionFailure', ['5.6.0']);
214     }
215
216     my @missing = ();
217     unless (eval {require DBI})               { push @missing,"DBI" };
218     unless (eval {require Date::Manip})       { push @missing,"Date::Manip" };
219     unless (eval {require DBD::mysql})        { push @missing,"DBD::mysql" };
220     unless (eval {require Set::Scalar})       { push @missing,"Set::Scalar" };
221     unless (eval {require Digest::MD5})       { push @missing,"Digest::MD5" };
222     unless (eval {require Net::Z3950})        { 
223         my $message = getmessage('NETZ3950Missing');
224         showmessage($message, 'PressEnter', '', 1);
225         if ($#missing>=0) {
226             push @missing, "Net::Z3950";
227         }
228     }
229
230 #
231 # Print out a list of any missing modules
232 #
233
234     if (@missing > 0) {
235         my $missing='';
236         foreach my $module (@missing) {
237             $missing.="   perl -MCPAN -e 'install \"$module\"'\n";
238         }
239         my $message=getmessage('MissingPerlModules', [$missing]);
240         showmessage($message, 'none');
241         exit;
242     } else {
243         showmessage(getmessage('AllPerlModulesInstalled'), 'PressEnter', '', 1);
244     }
245
246
247 }
248
249
250 sub getmessage {
251     my $messagename=shift;
252     my $variables=shift;
253     my $message=$messages->{$messagename}->{$::language} || $messages->{$messagename}->{en} || "Error: No message named $messagename in Install.pm\n";
254     if (defined($variables)) {
255         $message=sprintf $message, @$variables;
256     }
257     return $message;
258 }
259
260
261 sub showmessage {
262     my $message=shift;
263     my $responsetype=shift;
264     my $defaultresponse=shift;
265     my $noclear=shift;
266     ($noclear) || (system('clear'));
267     if ($responsetype =~ /^yn$/) {
268         $responsetype='restrictchar yn';
269     }
270     print $message;
271     SWITCH: {
272         if ($responsetype =~/^restrictchar (.*)/i) {
273             my $response='\0';
274             my $options=$1;
275             until ($options=~/$response/) {
276                 ($defaultresponse) || ($defaultresponse=substr($options,0,1));
277                 $response=<STDIN>;
278                 chomp $response;
279                 (length($response)) || ($response=$defaultresponse);
280                 unless ($options=~/$response/) {
281                     ($noclear) || (system('clear'));
282                     print "Invalid Response.  Choose from [$options].\n\n";
283                     print $message;
284                 }
285             }
286             return $response;
287         }
288         if ($responsetype =~/^free$/i) {
289             (defined($defaultresponse)) || ($defaultresponse='');
290             my $response=<STDIN>;
291             chomp $response;
292             ($response) || ($response=$defaultresponse);
293             return $response;
294         }
295         if ($responsetype =~/^numerical$/i) {
296             (defined($defaultresponse)) || ($defaultresponse='');
297             my $response='';
298             until ($response=~/^\d+$/) {
299                 $response=<STDIN>;
300                 chomp $response;
301                 ($response) || ($response=$defaultresponse);
302                 unless ($response=~/^\d+$/) {
303                     ($noclear) || (system('clear'));
304                     print "Invalid Response ($response).  Response must be a number.\n\n";
305                     print $message;
306                 }
307             }
308             return $response;
309         }
310         if ($responsetype =~/^email$/i) {
311             (defined($defaultresponse)) || ($defaultresponse='');
312             my $response='';
313             until ($response=~/.*\@.*\..*/) {
314                 $response=<STDIN>;
315                 chomp $response;
316                 ($response) || ($response=$defaultresponse);
317                 unless ($response=~/.*\@.*\..*/) {
318                     ($noclear) || (system('clear'));
319                     print "Invalid Response ($response).  Response must be a valid email address.\n\n";
320                     print $message;
321                 }
322             }
323             return $response;
324         }
325         if ($responsetype =~/^PressEnter$/i) {
326             <STDIN>;
327             return;
328         }
329         if ($responsetype =~/^none$/i) {
330             return;
331         }
332     }
333 }
334
335 sub getinstallationdirectories {
336     $::opacdir = '/usr/local/koha/opac';
337     $::intranetdir = '/usr/local/koha/intranet';
338     my $getdirinfo=1;
339     while ($getdirinfo) {
340         # Loop until opac directory and koha directory are different
341         my $message=getmessage('GetOpacDir', [$::opacdir]);
342         $::opacdir=showmessage($message, 'free', $::opacdir);
343
344         $message=getmessage('GetIntranetDir', [$::intranetdir]);
345         $::intranetdir=showmessage($message, 'free', $::intranetdir);
346
347         if ($::intranetdir eq $::opacdir) {
348             print qq|
349
350 You must specify different directories for the OPAC and INTRANET files!
351  :: $::intranetdir :: $::opacdir ::
352 |;
353 <STDIN>
354         } else {
355             $getdirinfo=0;
356         }
357     }
358     $::kohalogdir='/var/log/koha';
359     my $message=getmessage('GetKohaLogDir', [$::kohalogdir]);
360     $::kohalogdir=showmessage($message, 'free', $::kohalogdir);
361
362
363     unless ( -d $::intranetdir ) {
364        my $result=mkdir ($::intranetdir, oct(770));
365        if ($result==0) {
366            my @dirs = split(m#/#, $::intranetdir);
367             my $checkdir='';
368             foreach (@dirs) {
369                 $checkdir.="$_/";
370                 unless (-e "$checkdir") {
371                     mkdir($checkdir, 0775);
372                 }
373             }
374        }
375        chown (oct(0), (getgrnam($::httpduser))[2], "$::intranetdir");
376        chmod (oct(770), "$::intranetdir");
377     }
378     unless ( -d "$::intranetdir/htdocs" ) {
379        mkdir ("$::intranetdir/htdocs", oct(750));
380     }
381     unless ( -d "$::intranetdir/cgi-bin" ) {
382        mkdir ("$::intranetdir/cgi-bin", oct(750));
383     }
384     unless ( -d "$::intranetdir/modules" ) {
385        mkdir ("$::intranetdir/modules", oct(750));
386     }
387     unless ( -d "$::intranetdir/scripts" ) {
388        mkdir ("$::intranetdir/scripts", oct(750));
389     }
390     unless ( -d $::opacdir ) {
391        my $result=mkdir ($::opacdir, oct(770));
392        if ($result==0) {
393            my @dirs = split(m#/#, $::opacdir);
394             my $checkdir='';
395             foreach (@dirs) {
396                 $checkdir.="$_/";
397                 unless (-e "$checkdir") {
398                     mkdir($checkdir, 0775);
399                 }
400             }
401        }
402        chown (oct(0), (getgrnam($::httpduser))[2], "$::opacdir");
403        chmod (oct(770), "$::opacdir");
404     }
405     unless ( -d "$::opacdir/htdocs" ) {
406        mkdir ("$::opacdir/htdocs", oct(750));
407     }
408     unless ( -d "$::opacdir/cgi-bin" ) {
409        mkdir ("$::opacdir/cgi-bin", oct(750));
410     }
411
412
413     unless ( -d $::kohalogdir ) {
414        my $result=mkdir ($::kohalogdir, oct(770));
415        if ($result==0) {
416            my @dirs = split(m#/#, $::kohalogdir);
417             my $checkdir='';
418             foreach (@dirs) {
419                 $checkdir.="$_/";
420                 unless (-e "$checkdir") {
421                     mkdir($checkdir, 0775);
422                 }
423             }
424        }
425
426        chown (oct(0), (getgrnam($::httpduser))[2,3], "$::kohalogdir");
427        chmod (oct(770), "$::kohalogdir");
428     }
429 }
430
431
432
433 $messages->{'DatabaseName'}->{en}=qq|
434 ==========================
435 = Name of MySQL database =
436 ==========================
437
438 Please provide the name of the mysql database for your koha installation.
439
440 Database name [%s]: |;
441
442 $messages->{'DatabaseHost'}->{en}=qq|
443 =================
444 = Database Host =
445 =================
446
447 Please provide the hostname for mysql.  Unless the database is located on
448 another machine this will be "localhost".
449
450 Database host [%s]: |;
451
452 $messages->{'DatabaseUser'}->{en}=qq|
453 =================
454 = Database User =
455 =================
456
457 Please provide the name of the user, who will have full administrative rights
458 to the %s database, when authenticating from %s.
459
460 Database user [%s]: |;
461
462 $messages->{'DatabasePassword'}->{en}=qq|
463 =====================
464 = Database Password =
465 =====================
466
467 Please provide a good password for the user %s.
468
469 Database Password: |;
470
471 $messages->{'BlankPassword'}->{en}=qq|
472 ==================
473 = BLANK PASSWORD =
474 ==================
475
476 You must not use a blank password for your MySQL user!
477
478 Press <ENTER> to try again: 
479 |;
480
481 sub getdatabaseinfo {
482
483     $::dbname = 'Koha';
484     $::hostname = 'localhost';
485     $::user = 'kohaadmin';
486     $::pass = '';
487
488 #Get the database name
489
490     my $message=getmessage('DatabaseName', [$::dbname]);
491     $::dbname=showmessage($message, 'free', $::dbname);
492
493 #Get the hostname for the database
494     
495     $message=getmessage('DatabaseHost', [$::hostname]);
496     $::hostname=showmessage($message, 'free', $::hostname);
497
498 #Get the username for the database
499
500     $message=getmessage('DatabaseUser', [$::dbname, $::hostname, $::user]);
501     $::user=showmessage($message, 'free', $::user);
502
503 #Get the password for the database user
504
505     while ($::pass eq '') {
506         my $message=getmessage('DatabasePassword', [$::user]);
507         $::pass=showmessage($message, 'free', $::pass);
508         if ($::pass eq '') {
509             my $message=getmessage('BlankPassword');
510             showmessage($message,'PressEnter');
511         }
512     }
513 }
514
515
516
517 $messages->{'FoundMultipleApacheConfFiles'}->{en}=qq|
518 ================================
519 = MULTIPLE APACHE CONFIG FILES =
520 ================================
521
522 I found more than one possible Apache configuration file:
523
524 %s
525
526 Choose the correct file [1]: |;
527
528 $messages->{'NoApacheConfFiles'}->{en}=qq|
529 ===============================
530 = NO APACHE CONFIG FILE FOUND =
531 ===============================
532
533 I was not able to find your Apache configuration file.
534
535 The file is usually called httpd.conf or apache.conf.
536
537 Please specify the location of your config file: |;
538
539 $messages->{'NotAFile'}->{en}=qq|
540 =======================
541 = FILE DOES NOT EXIST =
542 =======================
543
544 The file %s does not exist.
545
546 Please press <ENTER> to continue: |;
547
548 $messages->{'EnterApacheUser'}->{en}=qq|
549 ====================
550 = NEED APACHE USER =
551 ====================
552
553 I was not able to determine the user that Apache is running as.  This
554 information is necessary in order to set the access privileges correctly on
555 /etc/koha.conf.  This user should be set in one of the Apache configuration
556 files using the "User" directive.
557
558 Enter the Apache userid: |;
559
560 $messages->{'InvalidUserid'}->{en}=qq|
561 ==================
562 = INVALID USERID =
563 ==================
564
565 The userid %s is not a valid userid on this system.
566
567 Press <ENTER> to continue: |;
568
569 sub getapacheinfo {
570     my @confpossibilities;
571
572     foreach my $httpdconf (qw(/usr/local/apache/conf/httpd.conf
573                           /usr/local/etc/apache/httpd.conf
574                           /usr/local/etc/apache/apache.conf
575                           /var/www/conf/httpd.conf
576                           /etc/apache/conf/httpd.conf
577                           /etc/apache/conf/apache.conf
578                           /etc/apache-ssl/conf/apache.conf
579                           /etc/httpd/conf/httpd.conf
580                           /etc/httpd/httpd.conf)) {
581         if ( -f $httpdconf ) {
582             push @confpossibilities, $httpdconf;
583         }
584     }
585
586     if ($#confpossibilities==-1) {
587         my $message=getmessage('NoApacheConfFiles');
588         my $choice='';
589         until (-f $choice) {
590             $choice=showmessage($message, "free", 1);
591             unless (-f $choice) {
592                 showmessage(getmessage('NotAFile', [$choice]),'PressEnter', '', 1);
593             }
594         }
595     } elsif ($#confpossibilities>0) {
596         my $conffiles='';
597         my $counter=1;
598         my $options='';
599         foreach (@confpossibilities) {
600             $conffiles.="   $counter: $_\n";
601             $options.="$counter";
602             $counter++;
603         }
604         my $message=getmessage('FoundMultipleApacheConfFiles', [$conffiles]);
605         my $choice=showmessage($message, "restrictchar $options", 1);
606         $::realhttpdconf=$confpossibilities[$choice-1];
607     } else {
608         $::realhttpdconf=$confpossibilities[0];
609     }
610     open (HTTPDCONF, $::realhttpdconf) or warn "Insufficient privileges to open $::realhttpdconf for reading.\n";
611     while (<HTTPDCONF>) {
612         if (/^\s*User\s+"?([-\w]+)"?\s*$/) {
613             $::httpduser = $1;
614         }
615     }
616     close(HTTPDCONF);
617
618
619
620
621     unless ($::httpduser) {
622         my $message=getmessage('EnterApacheUser');
623         until (length($::httpduser) && getpwnam($::httpduser)) {
624             $::httpduser=showmessage($message, "free", '');
625             if (length($::httpduser)>0) {
626                 unless (getpwnam($::httpduser)) {
627                     my $message=getmessage('InvalidUserid', [$::httpduser]);
628                     showmessage($message,'PressEnter');
629                 }
630             } else {
631             }
632         }
633         print "AU: $::httpduser\n";
634     }
635 }
636
637
638 $messages->{'ApacheConfigIntroduction'}->{en}=qq|
639 ========================
640 = APACHE CONFIGURATION =
641 ========================
642
643 Koha needs to setup your Apache configuration file for the
644 OPAC and LIBRARIAN virtual hosts.  By default this installer
645 will do this by using one ip address and two different ports
646 for the virtual hosts.  There are other ways to set this up,
647 and the installer will leave comments in httpd.conf detailing
648 what these other options are.
649
650
651 Press <ENTER> to continue: |;
652
653 $messages->{'GetVirtualHostEmail'}->{en}=qq|
654 =============================
655 = WEB SERVER E-MAIL CONTACT =
656 =============================
657
658 Enter the e-mail address to be used as a contact for the virtual hosts (this
659 address is displayed if any errors are encountered).
660
661 E-mail contact [%s]: |;
662
663 $messages->{'GetServerName'}->{en}=qq|
664 ======================================
665 = WEB SERVER HOST NAME OR IP ADDRESS =
666 ======================================
667
668 Please enter the domain name or ip address of your computer.
669
670 Host name or IP Address [%s]: |;
671
672 $messages->{'GetOpacPort'}->{en}=qq|
673 ==========================
674 = OPAC VIRTUAL HOST PORT =
675 ==========================
676
677 Please enter the port for your OPAC interface.  This defaults to port 80, but
678 if you are already serving web content from this server, you should change it
679 to a different port (8000 might be a good choice).
680
681 Enter the OPAC Port [%s]: |;
682
683 $messages->{'GetIntranetPort'}->{en}=qq|
684 ==============================
685 = INTRANET VIRTUAL HOST PORT =
686 ==============================
687
688 Please enter the port for your Intranet interface.  This must be different from
689 the OPAC port (%s).
690
691 Enter the Intranet Port [%s]: |;
692
693
694 sub getapachevhostinfo {
695
696     $::svr_admin = "webmaster\@$::domainname";
697     $::servername=`hostname -f`;
698     chomp $::servername;
699     $::opacport=80;
700     $::intranetport=8080;
701
702     showmessage(getmessage('ApacheConfigIntroduction'), 'PressEnter');
703
704     $::svr_admin=showmessage(getmessage('GetVirtualHostEmail', [$::svr_admin]), 'email', $::svr_admin);
705     $::servername=showmessage(getmessage('GetServerName', [$::servername]), 'free', $::servername);
706
707
708     $::opacport=showmessage(getmessage('GetOpacPort', [$::opacport]), 'numerical', $::opacport);
709     $::intranetport=showmessage(getmessage('GetIntranetPort', [$::opacport, $::intranetport]), 'numerical', $::intranetport);
710
711 }
712
713 $messages->{'StartUpdateApache'}->{en}=qq|
714 =================================
715 = UPDATING APACHE CONFIGURATION =
716 =================================
717
718 Checking for modules that need to be loaded...
719 |;
720
721 $messages->{'LoadingApacheModuleModEnv'}->{en}="Loading SetEnv Apache module.\n";
722
723 $messages->{'LoadingApacheModuleModInc'}->{en}="Loading Includes Apache module.\n";
724
725 $messages->{'ApacheConfigBackupFailed'}->{en}=qq|
726 ======================================
727 = APACHE CONFIGURATION BACKUP FAILED =
728 ======================================
729
730 An error occurred while trying to make a backup copy of %s.
731
732   %s
733
734 No changes will be made to the apache configuration file at this time.
735
736 Press <ENTER> to continue: |;
737
738
739 $messages->{'ApacheAlreadyConfigured'}->{en}=qq|
740 =============================
741 = APACHE ALREADY CONFIGURED =
742 =============================
743
744 %s appears to already have an entry for Koha
745 Virtual Hosts.  You may need to edit %s
746 f anything has changed since it was last set up.  This
747 script will not attempt to modify an existing Koha apache
748 configuration.
749
750 Press <ENTER> to continue: |;
751
752 sub updateapacheconf {
753     my $logfiledir=`grep ^ErrorLog $::realhttpdconf`;
754     chomp $logfiledir;
755
756     if ($logfiledir) {
757         $logfiledir=~m#ErrorLog (.*)/[^/]*$#;
758         $logfiledir=$1;
759     }
760
761     unless ($logfiledir) {
762         $logfiledir='logs';
763     }
764
765     showmessage(getmessage('StartUpdateApache'), 'none');
766
767     my $httpdconf;
768     my $envmodule=0;
769     my $includesmodule=0;
770     open HC, $::realhttpdconf;
771     while (<HC>) {
772         if (/^\s*#\s*LoadModule env_module /) {
773             s/^\s*#\s*//;
774             showmessage(getmessage('LoadingApacheModuleModEnv'));
775             $envmodule=1;
776         }
777         if (/^\s*#\s*LoadModule includes_module /) {
778             s/^\s*#\s*//;
779             showmessage(getmessage('LoadingApacheModuleModInc'));
780         }
781         if (/\s*LoadModule includes_module / ) {
782             $includesmodule=1;
783         }
784         $httpdconf.=$_;
785     }
786
787     my $backupfailed=0;
788     $backupfailed=`cp -f $::realhttpdconf $::realhttpdconf\.prekoha`;
789     if ($backupfailed) {
790         showmessage(getmessage('ApacheConfigBackupFailed', [$::realhttpdconf,$backupfailed ]), 'PressEnter');
791         return;
792     }
793
794     if ($envmodule || $includesmodule) {
795         open HC, ">$::realhttpdconf";
796         print HC $httpdconf;
797         close HC;
798     }
799
800
801     
802     if (`grep 'VirtualHost $::servername' $::realhttpdconf`) {
803         showmessage(getmessage('ApacheAlreadyConfigured', [$::realhttpdconf, $::realhttpdconf]), 'PressEnter');
804         return;
805     } else {
806         my $includesdirectives='';
807         if ($includesmodule) {
808             $includesdirectives.="Options +Includes\n";
809             $includesdirectives.="   AddHandler server-parsed .html\n";
810         }
811         open(SITE,">>$::realhttpdconf") or warn "Insufficient priveleges to open $::realhttpdconf for writing.\n";
812         my $opaclisten = '';
813         if ($::opacport != 80) {
814             $opaclisten="Listen $::opacport";
815         }
816         my $intranetlisten = '';
817         if ($::intranetport != 80) {
818             $intranetlisten="Listen $::intranetport";
819         }
820         print SITE <<EOP
821
822 # Ports to listen to for Koha
823 $opaclisten
824 $intranetlisten
825
826 # NameVirtualHost is used by one of the optional configurations detailed below
827
828 #NameVirtualHost 11.22.33.44
829
830 # KOHA's OPAC Configuration
831 <VirtualHost $::servername\:$::opacport>
832    ServerAdmin $::svr_admin
833    DocumentRoot $::opacdir/htdocs
834    ServerName $::servername
835    ScriptAlias /cgi-bin/koha/ $::opacdir/cgi-bin/
836    ErrorLog $logfiledir/opac-error_log
837    TransferLog $logfiledir/opac-access_log
838    SetEnv PERL5LIB "$::intranetdir/modules"
839    $includesdirectives
840 </VirtualHost>
841
842 # KOHA's INTRANET Configuration
843 <VirtualHost $::servername\:$::intranetport>
844    ServerAdmin $::svr_admin
845    DocumentRoot $::intranetdir/htdocs
846    ServerName $::servername
847    ScriptAlias /cgi-bin/koha/ "$::intranetdir/cgi-bin/"
848    ErrorLog $logfiledir/koha-error_log
849    TransferLog $logfiledir/koha-access_log
850    SetEnv PERL5LIB "$::intranetdir/modules"
851    $includesdirectives
852 </VirtualHost>
853
854 # If you want to use name based Virtual Hosting:
855 #   1. remove the two Listen lines
856 #   2. replace $::servername\:$::opacport wih your.opac.domain.name
857 #   3. replace ServerName $::servername wih ServerName your.opac.domain.name
858 #   4. replace $::servername\:$::intranetport wih your intranet domain name
859 #   5. replace ServerName $::servername wih ServerName your.intranet.domain.name
860 #
861 # If you want to use NameVirtualHost'ing (using two names on one ip address):
862 #   1.  Follow steps 1-5 above
863 #   2.  Uncomment the NameVirtualHost line and set the correct ip address
864
865 EOP
866
867
868     }
869 }
870
871 $messages->{'IntranetAuthenticationQuestion'}->{en}=qq|
872 ===========================
873 = INTRANET AUTHENTICATION =
874 ===========================
875
876 I can set it up so that the Intranet/Librarian site is password protected using
877 Apache's Basic Authorization.
878
879 Would you like to do this ([Y]/N): |;
880
881 $messages->{'BasicAuthUsername'}->{en}="Please enter a userid for intranet access [%s]: ";
882 $messages->{'BasicAuthPassword'}->{en}="Please enter a password for %s: ";
883 $messages->{'BasicAuthPasswordWasBlank'}->{en}="\nYou cannot use a blank password!\n\n";
884
885 sub basicauthentication {
886     my $message=getmessage('IntranetAuthenticationQuestion');
887     my $answer=showmessage($message, 'yn', 'y');
888
889     my $apacheauthusername='librarian';
890     my $apacheauthpassword='';
891     if ($answer=~/^y/i) {
892         ($apacheauthusername) = showmessage(getmessage('BasicAuthUsername', [ $apacheauthusername]), 'free', $apacheauthusername, 1);
893         $apacheauthusername=~s/[^a-zA-Z0-9]//g;
894         while (! $apacheauthpassword) {
895             ($apacheauthpassword) = showmessage(getmessage('BasicAuthPassword', [ $apacheauthusername]), 'free', 1);
896             if (!$apacheauthpassword) {
897                 ($apacheauthpassword) = showmessage(getmessage('BasicAuthPasswordWasBlank'), 'none', '', 1);
898             }
899         }
900         open AUTH, ">/etc/kohaintranet.pass";
901         my $chars='ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
902         my $salt=substr($chars, int(rand(length($chars))),1);
903         $salt.=substr($chars, int(rand(length($chars))),1);
904         print AUTH $apacheauthusername.":".crypt($apacheauthpassword, $salt)."\n";
905         close AUTH;
906         open(SITE,">>$::realhttpdconf") or warn "Insufficient priveleges to open $::realhttpdconf for writing.\n";
907         print SITE <<EOP
908
909 <Directory $::intranetdir>
910     AuthUserFile /etc/kohaintranet.pass
911     AuthType Basic
912     AuthName "Koha Intranet (for librarians only)"
913     Require  valid-user
914 </Directory>
915 EOP
916     }
917     close(SITE);
918 }
919
920 $messages->{'InstallFiles'}->{en}=qq|
921 ====================
922 = INSTALLING FILES =
923 ====================
924
925 Copying files to installation directories:
926
927 |;
928
929
930 $messages->{'CopyingFiles'}->{en}="Copying %s to %s.\n";
931
932
933
934 sub installfiles {
935
936
937     showmessage(getmessage('InstallFiles'),'none');
938     print getmessage('CopyingFiles', ['internet-html', "$::intranetdir/htdocs" ]);
939     system("cp -R intranet-html/* $::intranetdir/htdocs/");
940     print getmessage('CopyingFiles', ['internet-cgi', "$::intranetdir/cgi-bin" ]);
941     system("cp -R intranet-cgi/* $::intranetdir/cgi-bin/");
942     print getmessage('CopyingFiles', ['stand-alone scripts', "$::intranetdir/scripts" ]);
943     system("cp -R scripts/* $::intranetdir/scripts/");
944     print getmessage('CopyingFiles', ['perl modules', "$::intranetdir/modules" ]);
945     system("cp -R modules/* $::intranetdir/modules/");
946     print getmessage('CopyingFiles', ['opac-html', "$::opacdir/htdocs" ]);
947     system("cp -R opac-html/* $::opacdir/htdocs/");
948     print getmessage('CopyingFiles', ['opac-cgi', "$::opacdir/cgi-bin" ]);
949     system("cp -R opac-cgi/* $::opacdir/cgi-bin/");
950     system("touch $::opacdir/cgi-bin/opac");
951
952     system("chown -R root.$::httpduser $::opacdir");
953     system("chown -R root.$::httpduser $::intranetdir");
954
955     # Create /etc/koha.conf
956
957     open(KC,">$::etcdir/koha.conf") or warn "Couldn't create file
958     at $::etcdir.  Must have write capability.\n";
959     print KC qq|
960 database=$::dbname
961 hostname=$::hostname
962 user=$::user
963 pass=$::pass
964 includes=$::intranetdir/htdocs/includes
965 intranetdir=$::intranetdir
966 opacdir=$::opacdir
967 kohalogdir=$::kohalogdir
968 kohaversion=$::kohaversion
969 httpduser=$::httpduser
970 |;
971     close(KC);
972
973     chown((getpwnam($::httpduser)) [2,3], "$::etcdir/koha.conf") or warn "can't chown koha.conf: $!";
974     chmod 0440, "$::etcdir/koha.conf";
975
976     chmod 0750, "$::intranetdir/scripts/z3950daemon/z3950-daemon-launch.sh";
977     chmod 0750, "$::intranetdir/scripts/z3950daemon/z3950-daemon-shell.sh";
978     chmod 0750, "$::intranetdir/scripts/z3950daemon/processz3950queue";
979     chown(0, (getpwnam($::httpduser)) [3], "$::intranetdir/scripts/z3950daemon/z3950-daemon-shell.sh") or warn "can't chown $::intranetdir/scripts/z3950daemon/z3950-daemon-shell.sh: $!";
980     chown(0, (getpwnam($::httpduser)) [3], "$::intranetdir/scripts/z3950daemon/processz3950queue") or warn "can't chown $::intranetdir/scripts/z3950daemon/processz3950queue: $!";
981
982 }
983
984 $messages->{'MysqlRootPassword'}->{en}=qq|
985 ============================
986 = MYSQL ROOT USER PASSWORD =
987 ============================
988
989 To allow us to create the koha database please supply your
990 mysql server's root user password:
991
992 Enter MySql root user password: |;
993
994 $messages->{'InvalidMysqlRootPassword'}->{en}="Invalid Password.  Please try again.";
995
996 $messages->{'CreatingDatabase'}->{en}=qq|
997 =====================
998 = CREATING DATABASE =
999 =====================
1000
1001 Creating the MySql database for Koha...
1002
1003 |;
1004
1005 $messages->{'CreatingDatabaseError'}->{en}=qq|
1006 ===========================
1007 = ERROR CREATING DATABASE =
1008 ===========================
1009
1010 Couldn't connect to the MySQL server for the reason given above.
1011 This is a serious problem, the database will not get installed.\a
1012
1013 Press <ENTER> to continue: |;
1014
1015 $messages->{'SampleData'}->{en}=qq|
1016 ===============
1017 = SAMPLE DATA =
1018 ===============
1019
1020 If you are installing Koha for evaluation purposes,  I have a batch of sample
1021 data that you can install now.
1022
1023 If you are installing Koha with the intention of populating it with your own
1024 data, you probably don't want this sample data installed.
1025
1026 Would you like to install the sample data? Y/[N]: |;
1027
1028 $messages->{'SampleDataInstalled'}->{en}=qq|
1029 =========================
1030 = SAMPLE DATA INSTALLED =
1031 =========================
1032
1033 Sample data has been installed.  For some suggestions on testing Koha, please
1034 read the file doc/HOWTO-Testing.  If you find any bugs, please submit them at
1035 http://bugs.koha.org/.  If you need help with testing Koha, you can post a
1036 question through the koha-devel mailing list, or you can check for a developer
1037 online at +irc.katipo.co.nz:6667 channel #koha.
1038
1039 You can find instructions for subscribing to the Koha mailing lists at:
1040
1041     http://www.koha.org
1042
1043
1044 Press <ENTER> to continue: |;
1045
1046 $messages->{'AddBranchPrinter'}->{en}=qq|
1047 ==========================
1048 = Add Branch and Printer =
1049 ==========================
1050
1051 Would you like to install an initial branch and printer? [Y]/N: |;
1052
1053 $messages->{'BranchName'}->{en}="Branch Name [%s]: ";
1054 $messages->{'BranchCode'}->{en}="Branch Code (4 letters or numbers) [%s]: ";
1055 $messages->{'PrinterQueue'}->{en}="Printer Queue [%s]: ";
1056 $messages->{'PrinterName'}->{en}="Printer Name [%s]: ";
1057
1058 sub databasesetup {
1059     my $mysqldir;
1060     $::mysqluser = 'root';
1061     $::mysqlpass = '';
1062
1063     foreach my $mysql (qw(/usr/local/mysql
1064                           /opt/mysql
1065                           )) {
1066        if ( -d $mysql ) {
1067                 $mysqldir=$mysql;
1068        }
1069     }
1070     if (!$mysqldir){
1071         $mysqldir='/usr';
1072     }
1073
1074
1075     my $needpassword=1;
1076     while ($needpassword) {
1077         $::mysqlpass=showmessage(getmessage('MysqlRootPassword'), 'free');
1078         my $result=system("$mysqldir/bin/mysqladmin -u$::mysqluser -p$::mysqlpass proc > /dev/null 2>&1");
1079         if ($result) {
1080             print getmessage('InvalidMysqlRootPassword');
1081         } else {
1082             $needpassword=0;
1083         }
1084     }
1085
1086     showmessage(getmessage('CreatingDatabase'),'none');
1087
1088     my $result=system("$mysqldir/bin/mysqladmin -u$::mysqluser -p$::mysqlpass create $::dbname");
1089     if ($result) {
1090         showmessage(getmessage('CreatingDatabaseError'),'PressEnter', '', 1);
1091     } else {
1092         system("$mysqldir/bin/mysql -u$::mysqluser -p$::mysqlpass $::dbname < koha.mysql");
1093         system("$mysqldir/bin/mysql -u$::mysqluser -p$::mysqlpass mysql -e \"insert into user (Host,User,Password) values ('$::hostname','$::user',password('$::pass'))\"\;");
1094         system("$mysqldir/bin/mysql -u$::mysqluser -p$::mysqlpass mysql -e \"insert into db (Host,Db,User,Select_priv,Insert_priv,Update_priv,Delete_priv,Create_priv,Drop_priv, index_priv, alter_priv) values ('%','$::dbname','$::user','Y','Y','Y','Y','Y','Y','Y','Y')\"");
1095         system("$mysqldir/bin/mysqladmin -u$::mysqluser -p$::mysqlpass reload");
1096
1097         system ("perl -I $::intranetdir/modules scripts/updater/updatedatabase");
1098
1099
1100         my $response=showmessage(getmessage('SampleData'), 'yn', 'n');
1101         if ($response =~/^y/i) {
1102             system("gunzip sampledata-1.2.gz");
1103             system("cat sampledata-1.2 | $mysqldir/bin/mysql -u$::mysqluser -p$::mysqlpass $::dbname");
1104             system("gzip -9 sampledata-1.2");
1105             system("$mysqldir/bin/mysql -u$::mysqluser -p$::mysqlpass $::dbname -e \"insert into branches (branchcode,branchname,issuing) values ('MAIN', 'Main Library', 1)\"");
1106             system("$mysqldir/bin/mysql -u$::mysqluser -p$::mysqlpass $::dbname -e \"insert into printers (printername,printqueue,printtype) values ('Circulation Desk Printer', 'lp', 'hp')\"");
1107             showmessage(getmessage('SampleDataInstalled'), 'PressEnter');
1108         } else {
1109             my $input;
1110             my $response=showmessage(getmessage('AddBranchPrinter'), 'yn', 'y');
1111
1112             unless ($response =~/^n/i) {
1113                 my $branch='Main Library';
1114                 print "Enter a name for the library branch [$branch]: ";
1115                 $branch=showmessage(getmessage('BranchName', [$branch]), 'free', $branch, 1);
1116                 $branch=~s/[^A-Za-z0-9\s]//g;
1117
1118                 my $branchcode=$branch;
1119                 $branchcode=~s/[^A-Za-z0-9]//g;
1120                 $branchcode=uc($branchcode);
1121                 $branchcode=substr($branchcode,0,4);
1122                 $branchcode=showmessage(getmessage('BranchCode', [$branchcode]), 'free', $branchcode, 1);
1123                 $branchcode=~s/[^A-Z]//g;
1124                 $branchcode=uc($branchcode);
1125                 $branchcode=substr($branchcode,0,4);
1126
1127                 system("$mysqldir/bin/mysql -u$::mysqluser -p$::mysqlpass $::dbname -e \"insert into branches (branchcode,branchname,issuing) values ('$branchcode', '$branch', 1)\"");
1128
1129                 my $printername='Library Printer';
1130                 $printername=showmessage(getmessage('PrinterName', [$printername]), 'free', $printername, 1);
1131                 $printername=~s/[^A-Za-z0-9\s]//g;
1132
1133                 my $printerqueue='lp';
1134                 $printerqueue=showmessage(getmessage('PrinterQueue', [$printerqueue]), 'free', $printerqueue, 1);
1135                 $printerqueue=~s/[^A-Za-z0-9]//g;
1136                 system("$mysqldir/bin/mysql -u$::mysqluser -p$::mysqlpass $::dbname -e \"insert into printers (printername,printqueue,printtype) values ('$printername', '$printerqueue', '')\"");
1137
1138             }
1139         }
1140
1141
1142     }
1143
1144 }
1145
1146 $messages->{'RestartApache'}->{en}=qq|
1147 ==================
1148 = RESTART APACHE =
1149 ==================
1150
1151 Apache needs to be restarted to load the new configuration for Koha.
1152
1153 Would you like to restart Apache now?  [Y]/N: |;
1154
1155 sub restartapache {
1156
1157     my $response=showmessage(getmessage('RestartApache'), 'yn', 'y');
1158
1159
1160
1161     unless ($response=~/^n/i) {
1162         # Need to support other init structures here?
1163         if (-e "/etc/rc.d/init.d/httpd") {
1164             system('/etc/rc.d/init.d/httpd restart');
1165         } elsif (-e "/etc/init.d/apache") {
1166             system('/etc//init.d/apache restart');
1167         } elsif (-e "/etc/init.d/apache-ssl") {
1168             system('/etc/init.d/apache-ssl restart');
1169         }
1170     }
1171
1172 }
1173
1174 sub loadconfigfile {
1175     my %configfile;
1176
1177     open (KC, "/etc/koha.conf");
1178     while (<KC>) {
1179      chomp;
1180      (next) if (/^\s*#/);
1181      if (/(.*)\s*=\s*(.*)/) {
1182        my $variable=$1;
1183        my $value=$2;
1184        # Clean up white space at beginning and end
1185        $variable=~s/^\s*//g;
1186        $variable=~s/\s*$//g;
1187        $value=~s/^\s*//g;
1188        $value=~s/\s*$//g;
1189        $configfile{$variable}=$value;
1190      }
1191     }
1192
1193     $::intranetdir=$configfile{'intranetdir'};
1194     $::opacdir=$configfile{'opacdir'};
1195     $::kohaversion=$configfile{'kohaversion'};
1196     $::kohalogdir=$configfile{'kohalogdir'};
1197     $::database=$configfile{'database'};
1198     $::hostname=$configfile{'hostname'};
1199     $::user=$configfile{'user'};
1200     $::pass=$configfile{'pass'};
1201 }
1202
1203 END { }       # module clean-up code here (global destructor)
1204