summaryrefslogtreecommitdiff
path: root/rt/bin
diff options
context:
space:
mode:
Diffstat (limited to 'rt/bin')
-rw-r--r--rt/bin/mason_handler.fcgi.in15
-rw-r--r--rt/bin/mason_handler.scgi.in8
-rw-r--r--rt/bin/mason_handler.svc.in8
-rw-r--r--rt/bin/rt-crontool.in8
-rw-r--r--rt/bin/rt-mailgate.in407
-rw-r--r--rt/bin/rt.in14
-rwxr-xr-xrt/bin/standalone_httpd.in154
-rwxr-xr-xrt/bin/webmux.pl148
-rw-r--r--rt/bin/webmux.pl.in85
9 files changed, 594 insertions, 253 deletions
diff --git a/rt/bin/mason_handler.fcgi.in b/rt/bin/mason_handler.fcgi.in
index 193eaae57..4a1abd36b 100644
--- a/rt/bin/mason_handler.fcgi.in
+++ b/rt/bin/mason_handler.fcgi.in
@@ -1,9 +1,9 @@
#!@PERL@
-# BEGIN BPS TAGGED BLOCK {{{
+# {{{ BEGIN BPS TAGGED BLOCK
#
# COPYRIGHT:
#
-# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# This software is Copyright (c) 1996-2004 Best Practical Solutions, LLC
# <jesse@bestpractical.com>
#
# (Except where explicitly superseded by other copyright notices)
@@ -43,7 +43,7 @@
# works based on those contributions, and sublicense and distribute
# those contributions and any derivatives thereof.
#
-# END BPS TAGGED BLOCK }}}
+# }}} END BPS TAGGED BLOCK
package RT::Mason;
use strict;
@@ -65,7 +65,6 @@ while ( my $cgi = CGI::Fast->new ) {
$ENV{'ENV'} = '' if defined $ENV{'ENV'};
$ENV{'IFS'} = '' if defined $ENV{'IFS'};
- Module::Refresh->refresh if $RT::DevelMode;
RT::ConnectToDatabase();
if ( ( !$Handler->interp->comp_exists( $cgi->path_info ) )
@@ -77,7 +76,13 @@ while ( my $cgi = CGI::Fast->new ) {
if ($@) {
$RT::Logger->crit($@);
}
- RT::Interface::Web::Handler->CleanupRequest();
+
+
+ if ($RT::Handle->TransactionDepth) {
+ $RT::Handle->ForceRollback;
+ $RT::Logger->crit("Transaction not committed. Usually indicates a software fault. Data loss may have occurred") ;
+ }
+
}
diff --git a/rt/bin/mason_handler.scgi.in b/rt/bin/mason_handler.scgi.in
index 2b38c9340..177ff00fd 100644
--- a/rt/bin/mason_handler.scgi.in
+++ b/rt/bin/mason_handler.scgi.in
@@ -1,9 +1,9 @@
#!@SPEEDY_BIN@
-# BEGIN BPS TAGGED BLOCK {{{
+# {{{ BEGIN BPS TAGGED BLOCK
#
# COPYRIGHT:
#
-# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# This software is Copyright (c) 1996-2004 Best Practical Solutions, LLC
# <jesse@bestpractical.com>
#
# (Except where explicitly superseded by other copyright notices)
@@ -43,7 +43,7 @@
# works based on those contributions, and sublicense and distribute
# those contributions and any derivatives thereof.
#
-# END BPS TAGGED BLOCK }}}
+# }}} END BPS TAGGED BLOCK
package RT::Mason;
use strict;
@@ -61,5 +61,5 @@ if ( ( !$Handler->interp->comp_exists( $cgi->path_info ) )
}
$Handler->handle_cgi_object($cgi);
-RT::Interface::Web::Handler->CleanupRequest();
+
1;
diff --git a/rt/bin/mason_handler.svc.in b/rt/bin/mason_handler.svc.in
index 7be566deb..d82f3c120 100644
--- a/rt/bin/mason_handler.svc.in
+++ b/rt/bin/mason_handler.svc.in
@@ -1,9 +1,9 @@
#!@PERL@
-# BEGIN BPS TAGGED BLOCK {{{
+# {{{ BEGIN BPS TAGGED BLOCK
#
# COPYRIGHT:
#
-# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# This software is Copyright (c) 1996-2004 Best Practical Solutions, LLC
# <jesse@bestpractical.com>
#
# (Except where explicitly superseded by other copyright notices)
@@ -43,8 +43,7 @@
# works based on those contributions, and sublicense and distribute
# those contributions and any derivatives thereof.
#
-# END BPS TAGGED BLOCK }}}
-
+# }}} END BPS TAGGED BLOCK
=head1 NAME
mason_handler.svc - Win32 IIS Service handler for RT
@@ -237,7 +236,6 @@ while( my $cgi = CGI::Fast->new ) {
warn "Serving $comp\n";
$Handler->handle_cgi($comp);
- RT::Interface::Web::Handler->CleanupRequest();
# _should_ always be tied
}
diff --git a/rt/bin/rt-crontool.in b/rt/bin/rt-crontool.in
index 76b08c344..6b95d8dc5 100644
--- a/rt/bin/rt-crontool.in
+++ b/rt/bin/rt-crontool.in
@@ -1,9 +1,9 @@
#!@PERL@
-# BEGIN BPS TAGGED BLOCK {{{
+# {{{ BEGIN BPS TAGGED BLOCK
#
# COPYRIGHT:
#
-# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# This software is Copyright (c) 1996-2004 Best Practical Solutions, LLC
# <jesse@bestpractical.com>
#
# (Except where explicitly superseded by other copyright notices)
@@ -43,11 +43,11 @@
# works based on those contributions, and sublicense and distribute
# those contributions and any derivatives thereof.
#
-# END BPS TAGGED BLOCK }}}
+# }}} END BPS TAGGED BLOCK
use strict;
use Carp;
-use lib ("@LOCAL_LIB_PATH@", "@RT_LIB_PATH@");
+use lib ("@RT_LIB_PATH@", "@LOCAL_LIB_PATH@");
package RT;
diff --git a/rt/bin/rt-mailgate.in b/rt/bin/rt-mailgate.in
index 5ac9469d8..a37364ffb 100644
--- a/rt/bin/rt-mailgate.in
+++ b/rt/bin/rt-mailgate.in
@@ -1,9 +1,9 @@
#!@PERL@ -w
-# BEGIN BPS TAGGED BLOCK {{{
+# {{{ BEGIN BPS TAGGED BLOCK
#
# COPYRIGHT:
#
-# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# This software is Copyright (c) 1996-2004 Best Practical Solutions, LLC
# <jesse@bestpractical.com>
#
# (Except where explicitly superseded by other copyright notices)
@@ -43,12 +43,385 @@
# works based on those contributions, and sublicense and distribute
# those contributions and any derivatives thereof.
#
-# END BPS TAGGED BLOCK }}}
+# }}} END BPS TAGGED BLOCK
=head1 NAME
rt-mailgate - Mail interface to RT3.
+=begin testing
+
+use RT::I18N;
+
+# Make sure that when we call the mailgate wrong, it tempfails
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://bad.address"), "Opened the mailgate - The error below is expected - $@");
+print MAIL <<EOF;
+From: root\@localhost
+To: rt\@example.com
+Subject: This is a test of new ticket creation
+
+Foob!
+EOF
+close (MAIL);
+
+# Check the return value
+is ( $? >> 8, 75, "The error message above is expected The mail gateway exited with a failure. yay");
+
+
+# {{{ Test new ticket creation by root who is privileged and superuser
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --debug --url http://localhost".$RT::WebPath."/ --queue general --action correspond"), "Opened the mailgate - $@");
+print MAIL <<EOF;
+From: root\@localhost
+To: rt\@example.com
+Subject: This is a test of new ticket creation
+
+Blah!
+Foob!
+EOF
+close (MAIL);
+
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+use RT::Tickets;
+my $tickets = RT::Tickets->new($RT::SystemUser);
+$tickets->OrderBy(FIELD => 'id', ORDER => 'DESC');
+$tickets->Limit(FIELD => 'id', OPERATOR => '>', VALUE => '0');
+my $tick = $tickets->First();
+ok (UNIVERSAL::isa($tick,'RT::Ticket'));
+ok ($tick->Id, "found ticket ".$tick->Id);
+ok ($tick->Subject eq 'This is a test of new ticket creation', "Created the ticket");
+
+# }}}
+
+
+# {{{This is a test of new ticket creation as an unknown user
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action correspond"), "Opened the mailgate - $@");
+print MAIL <<EOF;
+From: doesnotexist\@example.com
+To: rt\@example.com
+Subject: This is a test of new ticket creation as an unknown user
+
+Blah!
+Foob!
+EOF
+close (MAIL);
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+$tickets = RT::Tickets->new($RT::SystemUser);
+$tickets->OrderBy(FIELD => 'id', ORDER => 'DESC');
+$tickets->Limit(FIELD => 'id' ,OPERATOR => '>', VALUE => '0');
+$tick = $tickets->First();
+ok ($tick->Id, "found ticket ".$tick->Id);
+ok ($tick->Subject ne 'This is a test of new ticket creation as an unknown user', "failed to create the new ticket from an unprivileged account");
+my $u = RT::User->new($RT::SystemUser);
+$u->Load('doesnotexist@example.com');
+ok( $u->Id == 0, " user does not exist and was not created by failed ticket submission");
+
+
+# }}}
+
+# {{{ now everybody can create tickets. can a random unkown user create tickets?
+
+my $g = RT::Group->new($RT::SystemUser);
+$g->LoadSystemInternalGroup('Everyone');
+ok( $g->Id, "Found 'everybody'");
+
+my ($val,$msg) = $g->PrincipalObj->GrantRight(Right => 'CreateTicket');
+ok ($val, "Granted everybody the right to create tickets - $msg");
+
+sleep(60); # gotta sleep so the remote process' ACL cache times out
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action correspond"), "Opened the mailgate - $@");
+print MAIL <<EOF;
+From: doesnotexist\@example.com
+To: rt\@example.com
+Subject: This is a test of new ticket creation as an unknown user
+
+Blah!
+Foob!
+EOF
+close (MAIL);
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+
+$tickets = RT::Tickets->new($RT::SystemUser);
+$tickets->OrderBy(FIELD => 'id', ORDER => 'DESC');
+$tickets->Limit(FIELD => 'id' ,OPERATOR => '>', VALUE => '0');
+$tick = $tickets->First();
+ok ($tick->Id, "found ticket ".$tick->Id);
+ok ($tick->Subject eq 'This is a test of new ticket creation as an unknown user', "failed to create the new ticket from an unprivileged account");
+my $u = RT::User->new($RT::SystemUser);
+$u->Load('doesnotexist@example.com');
+ok( $u->Id != 0, " user does not exist and was created by ticket submission");
+
+# }}}
+
+
+# {{{ can another random reply to a ticket without being granted privs? answer should be no.
+
+
+#($val,$msg) = $g->PrincipalObj->GrantRight(Right => 'CreateTicket');
+#ok ($val, "Granted everybody the right to create tickets - $msg");
+#sleep(60); # gotta sleep so the remote process' ACL cache times out
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action correspond"), "Opened the mailgate - $@");
+print MAIL <<EOF;
+From: doesnotexist-2\@example.com
+To: rt\@example.com
+Subject: [example.com #@{[$tick->Id]}] This is a test of a reply as an unknown user
+
+Blah!
+Foob!
+EOF
+close (MAIL);
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+$u = RT::User->new($RT::SystemUser);
+$u->Load('doesnotexist-2@example.com');
+ok( $u->Id == 0, " user does not exist and was not created by ticket correspondence submission");
+# }}}
+
+
+# {{{ can another random reply to a ticket after being granted privs? answer should be yes
+
+
+($val,$msg) = $g->PrincipalObj->GrantRight(Right => 'ReplyToTicket');
+ok ($val, "Granted everybody the right to reply to tickets - $msg");
+sleep(60); # gotta sleep so the remote process' ACL cache times out
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action correspond"), "Opened the mailgate - $@");
+print MAIL <<EOF;
+From: doesnotexist-2\@example.com
+To: rt\@example.com
+Subject: [example.com #@{[$tick->Id]}] This is a test of a reply as an unknown user
+
+Blah!
+Foob!
+EOF
+close (MAIL);
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+
+$u = RT::User->new($RT::SystemUser);
+$u->Load('doesnotexist-2@example.com');
+ok( $u->Id != 0, " user exists and was created by ticket correspondence submission");
+
+# }}}
+
+# {{{ can another random comment on a ticket without being granted privs? answer should be no.
+
+
+#($val,$msg) = $g->PrincipalObj->GrantRight(Right => 'CreateTicket');
+#ok ($val, "Granted everybody the right to create tickets - $msg");
+#sleep(60); # gotta sleep so the remote process' ACL cache times out
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action comment"), "Opened the mailgate - $@");
+print MAIL <<EOF;
+From: doesnotexist-3\@example.com
+To: rt\@example.com
+Subject: [example.com #@{[$tick->Id]}] This is a test of a comment as an unknown user
+
+Blah!
+Foob!
+EOF
+close (MAIL);
+
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+$u = RT::User->new($RT::SystemUser);
+$u->Load('doesnotexist-3@example.com');
+ok( $u->Id == 0, " user does not exist and was not created by ticket comment submission");
+
+# }}}
+# {{{ can another random reply to a ticket after being granted privs? answer should be yes
+
+
+($val,$msg) = $g->PrincipalObj->GrantRight(Right => 'CommentOnTicket');
+ok ($val, "Granted everybody the right to reply to tickets - $msg");
+sleep(60); # gotta sleep so the remote process' ACL cache times out
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action comment"), "Opened the mailgate - $@");
+print MAIL <<EOF;
+From: doesnotexist-3\@example.com
+To: rt\@example.com
+Subject: [example.com #@{[$tick->Id]}] This is a test of a comment as an unknown user
+
+Blah!
+Foob!
+EOF
+close (MAIL);
+
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+$u = RT::User->new($RT::SystemUser);
+$u->Load('doesnotexist-3@example.com');
+ok( $u->Id != 0, " user exists and was created by ticket comment submission");
+
+# }}}
+
+# {{{ Testing preservation of binary attachments
+
+# Get a binary blob (Best Practical logo)
+
+# Create a mime entity with an attachment
+
+use MIME::Entity;
+my $entity = MIME::Entity->build( From => 'root@localhost',
+ To => 'rt@localhost',
+ Subject => 'binary attachment test',
+ Data => ['This is a test of a binary attachment']);
+
+# currently in lib/t/autogen
+$entity->attach(Path => '@MASON_HTML_PATH@/NoAuth/images/spacer.gif',
+ Type => 'image/gif',
+ Encoding => 'base64');
+
+# Create a ticket with a binary attachment
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action correspond"), "Opened the mailgate - $@");
+
+$entity->print(\*MAIL);
+
+close (MAIL);
+
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+my $tickets = RT::Tickets->new($RT::SystemUser);
+$tickets->OrderBy(FIELD => 'id', ORDER => 'DESC');
+$tickets->Limit(FIELD => 'id', OPERATOR => '>', VALUE => '0');
+ $tick = $tickets->First();
+ok (UNIVERSAL::isa($tick,'RT::Ticket'));
+ok ($tick->Id, "found ticket ".$tick->Id);
+ok ($tick->Subject eq 'binary attachment test', "Created the ticket - ".$tick->Id);
+
+my $file = `cat ../../../html/NoAuth/images/spacer.gif`;
+ok ($file, "Read in the logo image");
+
+
+ use Digest::MD5;
+warn "for the raw file the content is ".Digest::MD5::md5_base64($file);
+
+
+
+# Verify that the binary attachment is valid in the database
+my $attachments = RT::Attachments->new($RT::SystemUser);
+$attachments->Limit(FIELD => 'ContentType', VALUE => 'image/gif');
+ok ($attachments->Count == 1, 'Found only one gif in the database');
+my $attachment = $attachments->First;
+ok($attachment->Id);
+my $acontent = $attachment->Content;
+
+ warn "coming from the database, the content is ".Digest::MD5::md5_base64($acontent);
+
+is( $acontent, $file, 'The attachment isn\'t screwed up in the database.');
+# Log in as root
+use Getopt::Long;
+use LWP::UserAgent;
+
+
+# Grab the binary attachment via the web ui
+my $ua = LWP::UserAgent->new();
+
+my $full_url = "http://localhost".$RT::WebPath."/Ticket/Attachment/".$attachment->TransactionId."/".$attachment->id."/spacer.gif?&user=root&pass=password";
+my $r = $ua->get( $full_url);
+
+
+# Verify that the downloaded attachment is the same as what we uploaded.
+is($file, $r->content, 'The attachment isn\'t screwed up in download');
+
+
+
+# }}}
+
+# {{{ Simple I18N testing
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action correspond"), "Opened the mailgate - $@");
+
+print MAIL <<EOF;
+From: root\@localhost
+To: rtemail\@example.com
+Subject: This is a test of I18N ticket creation
+Content-Type: text/plain; charset="utf-8"
+
+2 accented lines
+\303\242\303\252\303\256\303\264\303\273
+\303\241\303\251\303\255\303\263\303\272
+bye
+EOF
+close (MAIL);
+
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+my $unitickets = RT::Tickets->new($RT::SystemUser);
+$unitickets->OrderBy(FIELD => 'id', ORDER => 'DESC');
+$unitickets->Limit(FIELD => 'id', OPERATOR => '>', VALUE => '0');
+my $unitick = $unitickets->First();
+ok (UNIVERSAL::isa($unitick,'RT::Ticket'));
+ok ($unitick->Id, "found ticket ".$unitick->Id);
+ok ($unitick->Subject eq 'This is a test of I18N ticket creation', "Created the ticket - ". $unitick->Subject);
+
+
+
+my $unistring = "\303\241\303\251\303\255\303\263\303\272";
+Encode::_utf8_on($unistring);
+is ($unitick->Transactions->First->Content, $unitick->Transactions->First->Attachments->First->Content, "Content is ". $unitick->Transactions->First->Attachments->First->Content);
+ok($unitick->Transactions->First->Attachments->First->Content =~ /$unistring/i, $unitick->Id." appears to be unicode ". $unitick->Transactions->First->Attachments->First->Id);
+# supposedly I18N fails on the second message sent in.
+
+ok(open(MAIL, "|@RT_BIN_PATH@/rt-mailgate --url http://localhost".$RT::WebPath."/ --queue general --action correspond"), "Opened the mailgate - $@");
+
+print MAIL <<EOF;
+From: root\@localhost
+To: rtemail\@example.com
+Subject: This is a test of I18N ticket creation
+Content-Type: text/plain; charset="utf-8"
+
+2 accented lines
+\303\242\303\252\303\256\303\264\303\273
+\303\241\303\251\303\255\303\263\303\272
+bye
+EOF
+close (MAIL);
+
+#Check the return value
+is ($? >> 8, 0, "The mail gateway exited normally. yay");
+
+my $tickets2 = RT::Tickets->new($RT::SystemUser);
+$tickets2->OrderBy(FIELD => 'id', ORDER => 'DESC');
+$tickets2->Limit(FIELD => 'id', OPERATOR => '>', VALUE => '0');
+my $tick2 = $tickets2->First();
+ok (UNIVERSAL::isa($tick2,'RT::Ticket'));
+ok ($tick2->Id, "found ticket ".$tick2->Id);
+ok ($tick2->Subject eq 'This is a test of I18N ticket creation', "Created the ticket");
+
+
+
+my $unistring = "\303\241\303\251\303\255\303\263\303\272";
+Encode::_utf8_on($unistring);
+
+ok ($tick2->Transactions->First->Content =~ $unistring, "It appears to be unicode - ".$tick2->Transactions->First->Content);
+
+# }}}
+
+
+($val,$msg) = $g->PrincipalObj->RevokeRight(Right => 'CreateTicket');
+ok ($val, $msg);
+
+
+
+=end testing
+
=cut
@@ -72,6 +445,7 @@ for (qw(url)) {
die "$0 invoked improperly\n\nNo $_ provided to mail gateway!\n" unless $opts{$_};
}
+undef $/;
my $ua = LWP::UserAgent->new();
$ua->cookie_jar( { file => $opts{jar} } );
@@ -82,7 +456,7 @@ my %args = (
);
# Read the message in from STDIN
-$args{'message'} = do { local (@ARGV, $/); <> };
+$args{'message'} = <>;
unless ( $args{message} =~ /\S/ ) {
print STDERR "$0: no message passed on STDIN!\n";
@@ -155,7 +529,7 @@ sub check_failure {
Usual invocation (from MTA):
- rt-mailgate --action (correspond|comment|...) --queue queuename
+ rt-mailgate --action (correspond|comment) --queue queuename
--url http://your.rt.server/
[ --debug ]
[ --extension (queue|action|ticket) ]
@@ -171,31 +545,15 @@ See C<man rt-mailgate> for more.
=item C<--action>
-Specifies what happens to email sent to this alias. The avaliable
-basic actions are: C<correspond>, C<comment>.
-
-
-If you've set the RT configuration variable B<$RT::UnsafeEmailCommands>,
-C<take> and C<resolve> are also available. You can execute two or more
-actions on a single message using a C<-> separated list. RT will execute
-the actions in the listed order. For example you can use C<take-comment>,
-C<correspond-resolve> or C<take-comment-resolve> as actions.
-
-Note that C<take> and C<resolve> actions ignore message text if used
-alone. Include a C<comment> or C<correspond> action if you want RT
-to record the incoming message.
-
-The default action is C<correspond>.
+Specifies whether this is a correspondence or comment address.
=item C<--queue>
-This flag determines which queue this alias should create a ticket in if no ticket identifier
-is found.
+Reflects which queue this address handles.
=item C<--url>
-This flag tells the mail gateway where it can find your RT server. You should
-probably use the same URL that users use to log into RT.
+The location of the web server for your RT instance.
=item C<--extension> OPTIONAL
@@ -286,7 +644,6 @@ several parameters:
=item Message
A C<MIME::Entity> object representing the email
-
=item CurrentUser
An C<RT::CurrentUser> object
diff --git a/rt/bin/rt.in b/rt/bin/rt.in
index d12460b06..86c83ca50 100644
--- a/rt/bin/rt.in
+++ b/rt/bin/rt.in
@@ -1,9 +1,9 @@
#!@PERL@ -w
-# BEGIN BPS TAGGED BLOCK {{{
+# {{{ BEGIN BPS TAGGED BLOCK
#
# COPYRIGHT:
#
-# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# This software is Copyright (c) 1996-2004 Best Practical Solutions, LLC
# <jesse@bestpractical.com>
#
# (Except where explicitly superseded by other copyright notices)
@@ -43,11 +43,7 @@
# works based on those contributions, and sublicense and distribute
# those contributions and any derivatives thereof.
#
-# END BPS TAGGED BLOCK }}}
-
-# Designed and implemented for Best Practical Solutions, LLC by
-# Abhijit Menon-Sen <ams@wiw.org>
-
+# }}} END BPS TAGGED BLOCK
use strict;
# This program is intentionally written to have as few non-core module
@@ -1259,7 +1255,7 @@ sub vsplit {
my @values = ref $val eq 'ARRAY' ? @$val : $val;
foreach my $line (map {split /\n/} @values) {
- # XXX: This should become a real parser, à la Text::ParseWords.
+ # XXX: This should become a real parser, à la Text::ParseWords.
$line =~ s/^\s+//;
$line =~ s/\s+$//;
push @words, split /\s*,\s*/, $line;
@@ -1775,7 +1771,7 @@ Text:
Examples:
- rt comment -m 'Not worth fixing.' -a stddisclaimer.h 23
+ rt comment -t 'Not worth fixing.' -a stddisclaimer.h 23
--
diff --git a/rt/bin/standalone_httpd.in b/rt/bin/standalone_httpd.in
index 6ba799833..bf449455c 100755
--- a/rt/bin/standalone_httpd.in
+++ b/rt/bin/standalone_httpd.in
@@ -1,9 +1,9 @@
#!@PERL@ -w
-# BEGIN BPS TAGGED BLOCK {{{
+# {{{ BEGIN BPS TAGGED BLOCK
#
# COPYRIGHT:
#
-# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# This software is Copyright (c) 1996-2004 Best Practical Solutions, LLC
# <jesse@bestpractical.com>
#
# (Except where explicitly superseded by other copyright notices)
@@ -43,24 +43,150 @@
# works based on those contributions, and sublicense and distribute
# those contributions and any derivatives thereof.
#
-# END BPS TAGGED BLOCK }}}
+# }}} END BPS TAGGED BLOCK
+package RT::Mason;
-use warnings;
use strict;
+use vars '$Handler';
-BEGIN {
- use lib( "@LOCAL_LIB_PATH@", "@RT_LIB_PATH@");
- use RT;
- RT::LoadConfig();
- if ($RT::DevelMode) { require Module::Refresh; }
-}
+require ('@RT_BIN_PATH@/webmux.pl');
+
+use lib( "@LOCAL_LIB_PATH@", "@RT_LIB_PATH@");
+
+use Socket;
RT::Init();
-use RT::Interface::Web::Standalone;
+my $port = shift || '8080';
+
+main_loop($port);
+
+sub main_loop {
+ my $port = shift;
+ my $tcp = getprotobyname('tcp');
+
+ socket( HTTPDaemon, PF_INET, SOCK_STREAM, $tcp ) or die "socket: $!";
+ setsockopt( HTTPDaemon, SOL_SOCKET, SO_REUSEADDR, pack( "l", 1 ) )
+ or warn "setsockopt: $!";
+ bind( HTTPDaemon, sockaddr_in( $port, INADDR_ANY ) ) or die "bind: $!";
+ listen( HTTPDaemon, SOMAXCONN ) or die "listen: $!";
+
+ print("You can connect to your RT server at http://localhost:$port/\n");
+
+ while (1) {
+
+ for ( ; accept( Remote, HTTPDaemon ); close Remote ) {
+
+ *STDIN = *Remote;
+ *STDOUT = *Remote;
+
+ my $remote_sockaddr = getpeername(STDIN);
+ my ( undef, $iaddr ) = sockaddr_in($remote_sockaddr);
+ my $peername = gethostbyaddr( $iaddr, AF_INET ) || "localhost";
+ my $peeraddr = inet_ntoa($iaddr) || "127.0.0.1";
+
+ my $local_sockaddr = getsockname(STDIN);
+ my ( undef, $localiaddr ) = sockaddr_in($local_sockaddr);
+ my $localname = gethostbyaddr( $localiaddr, AF_INET )
+ || "localhost";
+ my $localaddr = inet_ntoa($localiaddr) || "127.0.0.1";
+
+ chomp( $_ = <STDIN> );
+ my ( $method, $request_uri, $proto, undef ) = split;
+
+ #$request_uri =~ s#\\#/#g;
+ $RT::Logger->info("<- $peername: $_");
+ my ( $file, undef, $query_string ) =
+ ( $request_uri =~ /([^?]*)(\?(.*))?/ ); # split at ?
+ #$file =~ s/%([\dA-Fa-f]{2})/chr(hex($1))/eg; # decode url-escaped entities
+
+ last if ( $method !~ /^(GET|POST|HEAD)$/ );
+
+ build_cgi_env( method => $method,
+ query_string => $query_string,
+ path => $file,
+ method => $method,
+ port => $port,
+ peername => $peername,
+ peeraddr => $peeraddr,
+ localname => $localname,
+ request_uri => $request_uri );
+
+ RT::ConnectToDatabase();
+ my $cgi = CGI->new();
+
+ print "HTTP/1.0 200 OK\n"; # probably OK by now
+
+ if ( ( !$Handler->interp->comp_exists( $cgi->path_info ) )
+ && ($Handler->interp->comp_exists( $cgi->path_info . "/index.html" ) )
+ ) {
+ $cgi->path_info( $cgi->path_info . "/index.html" );
+ }
+
+ eval { $Handler->handle_cgi_object($cgi); };
+ $RT::Logger->crit($@) if ($@);
+
+ if ( $RT::Handle->TransactionDepth ) {
+ $RT::Handle->ForceRollback;
+ $RT::Logger->crit( "Transaction not committed. Usually indicates a software fault. Data loss may have occurred");
+ }
+
+ }
+
+ }
+
+}
+
+
+
+sub build_cgi_env {
+ my %args = ( query_string => '',
+ path => '',
+ port => undef,
+ protocol => undef,
+ localname => undef,
+ method => undef,
+ remote_name => undef,
+
+
+ @_);
+
+ foreach my $var qw(USER_AGENT CONTENT_LENGTH CONTENT_TYPE
+ COOKIE SERVER_PORT SERVER_PROTOCOL SERVER_NAME
+ PATH_INFO REQUEST_URI REQUEST_METHOD REMOTE_ADDR
+ REMOTE_HOST QUERY_STRING SERVER_SOFTWARE) {
+ delete $ENV{$var};
+ }
+ while (<STDIN>) {
+ s/[\r\l\n\s]+$//;
+ if( /^([\w\-]+): (.+)/i) {
+ my $tag = uc($1);
+ $tag =~ s/^COOKIES$/COOKIE/;
+ my $val = $2;
+ $tag =~ s/-/_/g;
+ $tag = "HTTP_".$tag unless (grep /^$tag$/, qw(CONTENT_LENGTH CONTENT_TYPE COOKIE));
+ if ($ENV{$tag}) {
+ $ENV{$tag} .= "; $val";
+ }
+ else {
+ $ENV{$tag} = $val;
+ }
+ }
+ last if (/^$/);
+ }
-my $server = RT::Interface::Web::Standalone->new;
-$server->port(shift @ARGV) if ($ARGV[0]);
-$server->run();
+ $ENV{SERVER_PROTOCOL} = $args{protocol};
+ $ENV{SERVER_PORT} = $args{port};
+ $ENV{SERVER_NAME} = $args{'localname'};
+ $ENV{SERVER_URL} = "http://".$args{'localname'}.":".$args{'port'}."/";
+ $ENV{PATH_INFO} = $args{'path'};
+ $ENV{REQUEST_URI} = $args{'request_uri'};
+ $ENV{REQUEST_METHOD} = $args{method};
+ $ENV{REMOTE_ADDR} = $args{'peeraddr'};
+ $ENV{REMOTE_HOST} = $args{'peername'};
+ $ENV{QUERY_STRING} = $args{'query_string'};
+ $ENV{SERVER_SOFTWARE} = "rt-standalone/$RT::VERSION";
+ CGI::initialize_globals();
+}
diff --git a/rt/bin/webmux.pl b/rt/bin/webmux.pl
deleted file mode 100755
index 96e7ebf8d..000000000
--- a/rt/bin/webmux.pl
+++ /dev/null
@@ -1,148 +0,0 @@
-#!/usr/bin/perl
-# BEGIN LICENSE BLOCK
-#
-# Copyright (c) 1996-2003 Jesse Vincent <jesse@bestpractical.com>
-#
-# (Except where explictly superceded by other copyright notices)
-#
-# This work is made available to you under the terms of Version 2 of
-# the GNU General Public License. A copy of that license should have
-# been provided with this software, but in any event can be snarfed
-# from www.gnu.org.
-#
-# This work is distributed in the hope that it will be useful, but
-# WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-# General Public License for more details.
-#
-# Unless otherwise specified, all modifications, corrections or
-# extensions to this work which alter its source code become the
-# property of Best Practical Solutions, LLC when submitted for
-# inclusion in the work.
-#
-#
-# END LICENSE BLOCK
-
-use strict;
-
-BEGIN {
- $ENV{'PATH'} = '/bin:/usr/bin'; # or whatever you need
- $ENV{'CDPATH'} = '' if defined $ENV{'CDPATH'};
- $ENV{'SHELL'} = '/bin/sh' if defined $ENV{'SHELL'};
- $ENV{'ENV'} = '' if defined $ENV{'ENV'};
- $ENV{'IFS'} = '' if defined $ENV{'IFS'};
-
-}
-
-use lib ("/opt/rt3/local/lib", "/opt/rt3/lib");
-use RT;
-
-package RT::Mason;
-
-use CGI qw(-private_tempfiles); #bring this in before mason, to make sure we
- #set private_tempfiles
-
-BEGIN {
- if ($mod_perl::VERSION >= 1.9908) {
- require Apache::RequestUtil;
- no warnings 'redefine';
- my $sub = *Apache::request{CODE};
- *Apache::request = sub {
- my $r;
- eval { $r = $sub->('Apache'); };
- # warn $@ if $@;
- return $r;
- };
- }
- if ($CGI::MOD_PERL) {
- require HTML::Mason::ApacheHandler;
- }
- else {
- require HTML::Mason::CGIHandler;
- }
-}
-
-use HTML::Mason; # brings in subpackages: Parser, Interp, etc.
-
-use vars qw($Nobody $SystemUser $r);
-
-#This drags in RT's config.pm
-RT::LoadConfig();
-
-use Carp;
-
-{
- package HTML::Mason::Commands;
- use vars qw(%session);
-
- use RT::Tickets;
- use RT::Transactions;
- use RT::Users;
- use RT::CurrentUser;
- use RT::Templates;
- use RT::Queues;
- use RT::ScripActions;
- use RT::ScripConditions;
- use RT::Scrips;
- use RT::Groups;
- use RT::GroupMembers;
- use RT::CustomFields;
- use RT::CustomFieldValues;
- use RT::TicketCustomFieldValues;
-
- use RT::Interface::Web;
- use MIME::Entity;
- use Text::Wrapper;
- use CGI::Cookie;
- use Time::ParseDate;
- use HTML::Entities;
-}
-
-
-# Activate the following if running httpd as root (the normal case).
-# Resets ownership of all files created by Mason at startup.
-# Note that mysql uses DB for sessions, so there's no need to do this.
-unless ($RT::DatabaseType =~ /(mysql|Pg)/) {
- # Clean up our umask to protect session files
- umask(0077);
-
-if ( $CGI::MOD_PERL) {
- chown( Apache->server->uid, Apache->server->gid, [$RT::MasonSessionDir] )
- if Apache->server->can('uid');
- }
- # Die if WebSessionDir doesn't exist or we can't write to it
- stat($RT::MasonSessionDir);
- die "Can't read and write $RT::MasonSessionDir"
- unless ( ( -d _ ) and ( -r _ ) and ( -w _ ) );
-}
-
-my $ah = &RT::Interface::Web::NewApacheHandler(@RT::MasonParameters) if $CGI::MOD_PERL;
-
-sub handler {
- ($r) = @_;
-
- local $SIG{__WARN__};
- local $SIG{__DIE__};
-
- RT::Init();
-
- # We don't need to handle non-text items
- return -1 if defined( $r->content_type ) && $r->content_type !~ m|^text/|io;
-
- my %session;
- my $status;
- eval { $status = $ah->handle_request($r) };
- if ($@) {
- $RT::Logger->crit($@);
- }
-
- undef (%session);
-
- if ($RT::Handle->TransactionDepth) {
- $RT::Handle->ForceRollback;
- $RT::Logger->crit("Transaction not committed. Usually indicates a software fault. Data loss may have occurred") ;
- }
- return $status;
-}
-
-1;
diff --git a/rt/bin/webmux.pl.in b/rt/bin/webmux.pl.in
index 73b10143d..877948960 100644
--- a/rt/bin/webmux.pl.in
+++ b/rt/bin/webmux.pl.in
@@ -1,9 +1,9 @@
#!@PERL@
-# BEGIN BPS TAGGED BLOCK {{{
+# {{{ BEGIN BPS TAGGED BLOCK
#
# COPYRIGHT:
#
-# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# This software is Copyright (c) 1996-2004 Best Practical Solutions, LLC
# <jesse@bestpractical.com>
#
# (Except where explicitly superseded by other copyright notices)
@@ -43,7 +43,7 @@
# works based on those contributions, and sublicense and distribute
# those contributions and any derivatives thereof.
#
-# END BPS TAGGED BLOCK }}}
+# }}} END BPS TAGGED BLOCK
use strict;
BEGIN {
@@ -53,12 +53,10 @@ BEGIN {
$ENV{'ENV'} = '' if defined $ENV{'ENV'};
$ENV{'IFS'} = '' if defined $ENV{'IFS'};
- use CGI qw(-private_tempfiles); #bring this in before mason, to make sure we
- #set private_tempfiles
-
- die "RT does not support mod_perl 1.99. Please upgrade to mod_perl 2.0"
+ eval { require Apache2; require APR::Table; require MasonX::Apache2Handler; 1 } or
+ eval { require Apache2; require Apache::compat; 1 } or die $@
if $ENV{'MOD_PERL'}
- and $ENV{'MOD_PERL'} =~ m{mod_perl/(?:1\.9)};
+ and $ENV{'MOD_PERL'} =~ m{mod_perl/(?:2|1\.9)};
}
@@ -67,57 +65,62 @@ use RT;
package RT::Mason;
+use CGI qw(-private_tempfiles); #bring this in before mason, to make sure we
+ #set private_tempfiles
+
+use HTML::Mason; # brings in subpackages: Parser, Interp, etc.
+
use vars qw($Nobody $SystemUser $Handler $r);
#This drags in RT's config.pm
-BEGIN {
- RT::LoadConfig();
- if ($RT::DevelMode) { require Module::Refresh; }
-}
+RT::LoadConfig();
+use Carp;
{
package HTML::Mason::Commands;
use vars qw(%session);
+
+ use RT::Tickets;
+ use RT::Transactions;
+ use RT::Users;
+ use RT::CurrentUser;
+ use RT::Templates;
+ use RT::Queues;
+ use RT::ScripActions;
+ use RT::ScripConditions;
+ use RT::Scrips;
+ use RT::Groups;
+ use RT::GroupMembers;
+ use RT::CustomFields;
+ use RT::CustomFieldValues;
+ use RT::TicketCustomFieldValues;
+
+ use RT::Interface::Web;
+ use MIME::Entity;
+ use Text::Wrapper;
+ use CGI::Cookie;
+ use Time::ParseDate;
+ use HTML::Entities;
+ use HTML::Scrubber;
+ use Text::Quoted;
}
-use RT::Interface::Web;
use RT::Interface::Web::Handler;
$Handler = RT::Interface::Web::Handler->new(@RT::MasonParameters);
-if ($ENV{'MOD_PERL'} && !$RT::DevelMode) {
- # Under static_source, we need to purge the component cache
- # each time we restart, so newer components may be reloaded.
- #
- # We can't do this in FastCGI or we'll blow away the component root _every_ time a new server starts
- # which happens every few hits.
-
- use File::Path qw( rmtree );
- use File::Glob qw( bsd_glob );
- rmtree([ bsd_glob("$RT::MasonDataDir/obj/*") ], 0, 1);
-}
-
sub handler {
($r) = @_;
local $SIG{__WARN__};
local $SIG{__DIE__};
- # We don't need to handle non-text, non-xml items
- if ($r->content_type =~ m/^httpd\b.*\bdirectory/i) {
- use File::Spec::Unix;
- # Our DirectoryIndex is always index.html, regardless of httpd settings
- $r->filename( File::Spec::Unix->catfile( $r->filename, 'index.html' ) );
- }
- elsif (defined( $r->content_type )) {
- $r->content_type =~ m!(^text/|\bxml\b)!i or return -1;
- }
-
- Module::Refresh->refresh if $RT::DevelMode;
-
RT::Init();
+ # We don't need to handle non-text, non-xml items
+ return -1 if defined( $r->content_type ) && $r->content_type !~ m!(^text/|\bxml\b)!io;
+
my %session;
my $status;
eval { $status = $Handler->handle_request($r) };
@@ -127,8 +130,12 @@ sub handler {
undef(%session);
- RT::Interface::Web::Handler->CleanupRequest();
-
+ if ( $RT::Handle->TransactionDepth ) {
+ $RT::Handle->ForceRollback;
+ $RT::Logger->crit(
+"Transaction not committed. Usually indicates a software fault. Data loss may have occurred"
+ );
+ }
return $status;
}