# DESTDIR allows you to specify that RT be installed somewhere other than
# where it will eventually reside
-
DESTDIR =
+
RT_PATH = /opt/rt3
RT_ETC_PATH = /opt/rt3/etc
RT_BIN_PATH = /opt/rt3/bin
RT_DOC_PATH = /opt/rt3/share/doc
RT_LOCAL_PATH = /opt/rt3/local
LOCAL_ETC_PATH = /opt/rt3/local/etc
+LOCAL_LIB_PATH = /opt/rt3/local/lib
LOCAL_LEXICON_PATH = /opt/rt3/local/po
-MASON_HTML_PATH = /opt/rt3/share/html
+MASON_HTML_PATH = /var/www/freeside/rt
MASON_LOCAL_HTML_PATH = /opt/rt3/local/html
-MASON_DATA_PATH = /opt/rt3/var/mason_data
+MASON_DATA_PATH = /usr/local/etc/freeside/masondata
MASON_SESSION_PATH = /opt/rt3/var/session_data
-RT_LOG_PATH = /opt/rt3/var/log
+RT_LOG_PATH = /opt/rt3/var/log
# RT_READABLE_DIR_MODE is the mode of directories that are generally meant
# to be accessable
# set this to the name you want to give to the RT database in
# your database server. For Oracle, this should be the name of your sid
-DB_DATABASE = _DBC_DBNAME_
-DB_RT_USER = _DBC_DBUSER_
-DB_RT_PASS = _DBC_DBPASS_
+DB_DATABASE = freeside
+DB_RT_USER = freeside
+DB_RT_PASS =
# }}}
#!/usr/bin/perl
-# BEGIN LICENSE BLOCK
+# BEGIN BPS TAGGED BLOCK {{{
#
-# Copyright (c) 1996-2003 Jesse Vincent <jesse@bestpractical.com>
+# COPYRIGHT:
+#
+# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# <jesse@bestpractical.com>
#
-# (Except where explictly superceded by other copyright notices)
+# (Except where explicitly superseded by other copyright notices)
+#
+#
+# LICENSE:
#
# 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
# 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.
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+#
+#
+# CONTRIBUTION SUBMISSION POLICY:
+#
+# (The following paragraph is not intended to limit the rights granted
+# to you to modify and distribute this software under the terms of
+# the GNU General Public License and is only of importance to you if
+# you choose to contribute your changes and enhancements to the
+# community by submitting them to Best Practical Solutions, LLC.)
#
+# By intentionally submitting any modifications, corrections or
+# derivatives to this work, or any other work intended for use with
+# Request Tracker, to Best Practical Solutions, LLC, you confirm that
+# you are the copyright holder for those contributions and you grant
+# Best Practical Solutions, LLC a nonexclusive, worldwide, irrevocable,
+# royalty-free, perpetual, license to use, copy, create derivative
+# works based on those contributions, and sublicense and distribute
+# those contributions and any derivatives thereof.
#
-# END LICENSE BLOCK
+# END BPS TAGGED BLOCK }}}
+package RT::Mason;
use strict;
+use vars '$Handler';
use File::Basename;
require ('/opt/rt3/bin/webmux.pl');
-my $h = &RT::Interface::Web::NewCGIHandler(@RT::MasonParameters);
-
# Enter CGI::Fast mode, which should also work as a vanilla CGI script.
require CGI::Fast;
RT::Init();
-# Response loop
while ( my $cgi = CGI::Fast->new ) {
# the whole point of fastcgi requires the env to get reset here..
# So we must squash it again
$ENV{'ENV'} = '' if defined $ENV{'ENV'};
$ENV{'IFS'} = '' if defined $ENV{'IFS'};
+ Module::Refresh->refresh if $RT::DevelMode;
RT::ConnectToDatabase();
- if ( ( !$h->interp->comp_exists( $cgi->path_info ) )
- && ( $h->interp->comp_exists( $cgi->path_info . "/index.html" ) ) ) {
+ 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 { $h->handle_cgi_object($cgi); };
+ eval { $Handler->handle_cgi_object($cgi); };
if ($@) {
$RT::Logger->crit($@);
}
-
-
- if ($RT::Handle->TransactionDepth) {
- $RT::Handle->ForceRollback;
- $RT::Logger->crit("Transaction not committed. Usually indicates a software fault. Data loss may have occurred") ;
- }
-
+ RT::Interface::Web::Handler->CleanupRequest();
}
#!/usr/local/bin/speedy
-# BEGIN LICENSE BLOCK
+# BEGIN BPS TAGGED BLOCK {{{
#
-# Copyright (c) 1996-2003 Jesse Vincent <jesse@bestpractical.com>
+# COPYRIGHT:
+#
+# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# <jesse@bestpractical.com>
#
-# (Except where explictly superceded by other copyright notices)
+# (Except where explicitly superseded by other copyright notices)
+#
+#
+# LICENSE:
#
# 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
# 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.
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+#
+#
+# CONTRIBUTION SUBMISSION POLICY:
#
+# (The following paragraph is not intended to limit the rights granted
+# to you to modify and distribute this software under the terms of
+# the GNU General Public License and is only of importance to you if
+# you choose to contribute your changes and enhancements to the
+# community by submitting them to Best Practical Solutions, LLC.)
#
-# END LICENSE BLOCK
+# By intentionally submitting any modifications, corrections or
+# derivatives to this work, or any other work intended for use with
+# Request Tracker, to Best Practical Solutions, LLC, you confirm that
+# you are the copyright holder for those contributions and you grant
+# Best Practical Solutions, LLC a nonexclusive, worldwide, irrevocable,
+# royalty-free, perpetual, license to use, copy, create derivative
+# works based on those contributions, and sublicense and distribute
+# those contributions and any derivatives thereof.
+#
+# END BPS TAGGED BLOCK }}}
+package RT::Mason;
use strict;
+use vars '$Handler';
require ('/opt/rt3/bin/webmux.pl');
-my $h = &RT::Interface::Web::NewCGIHandler(@RT::MasonParameters);
-
require CGI;
RT::Init();
my $cgi = CGI->new;
-if ( ( !$h->interp->comp_exists( $cgi->path_info ) )
- && ( $h->interp->comp_exists( $cgi->path_info . "/index.html" ) ) ) {
+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" );
}
-$h->handle_cgi_object($cgi);
-
+$Handler->handle_cgi_object($cgi);
+RT::Interface::Web::Handler->CleanupRequest();
1;
#!/usr/bin/perl
-# BEGIN LICENSE BLOCK
+# BEGIN BPS TAGGED BLOCK {{{
#
-# Copyright (c) 1996-2003 Jesse Vincent <jesse@bestpractical.com>
+# COPYRIGHT:
+#
+# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# <jesse@bestpractical.com>
#
-# (Except where explictly superceded by other copyright notices)
+# (Except where explicitly superseded by other copyright notices)
+#
+#
+# LICENSE:
#
# 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
# 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.
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+#
#
+# CONTRIBUTION SUBMISSION POLICY:
#
-# END LICENSE BLOCK
+# (The following paragraph is not intended to limit the rights granted
+# to you to modify and distribute this software under the terms of
+# the GNU General Public License and is only of importance to you if
+# you choose to contribute your changes and enhancements to the
+# community by submitting them to Best Practical Solutions, LLC.)
+#
+# By intentionally submitting any modifications, corrections or
+# derivatives to this work, or any other work intended for use with
+# Request Tracker, to Best Practical Solutions, LLC, you confirm that
+# you are the copyright holder for those contributions and you grant
+# Best Practical Solutions, LLC a nonexclusive, worldwide, irrevocable,
+# royalty-free, perpetual, license to use, copy, create derivative
+# works based on those contributions, and sublicense and distribute
+# those contributions and any derivatives thereof.
+#
+# END BPS TAGGED BLOCK }}}
=head1 NAME
=cut
+package RT::Mason;
+
use strict;
use File::Basename;
+use vars '$Handler';
require (dirname(__FILE__) . '/webmux.pl');
use Cwd;
warn "Begin listening on $ENV{'FCGI_SOCKET_PATH'}\n";
require CGI::Fast;
-my $h = &RT::Interface::Web::NewCGIHandler(@RT::MasonParameters);
RT::Init();
warn "Serving $comp\n";
- $h->handle_cgi($comp);
+ $Handler->handle_cgi($comp);
+ RT::Interface::Web::Handler->CleanupRequest();
# _should_ always be tied
}
#!/usr/bin/perl
-# BEGIN LICENSE BLOCK
+# BEGIN BPS TAGGED BLOCK {{{
#
-# Copyright (c) 1996-2003 Jesse Vincent <jesse@bestpractical.com>
+# COPYRIGHT:
+#
+# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# <jesse@bestpractical.com>
#
-# (Except where explictly superceded by other copyright notices)
+# (Except where explicitly superseded by other copyright notices)
+#
+#
+# LICENSE:
#
# 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
# 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.
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
#
#
-# END LICENSE BLOCK
-
+# CONTRIBUTION SUBMISSION POLICY:
+#
+# (The following paragraph is not intended to limit the rights granted
+# to you to modify and distribute this software under the terms of
+# the GNU General Public License and is only of importance to you if
+# you choose to contribute your changes and enhancements to the
+# community by submitting them to Best Practical Solutions, LLC.)
+#
+# By intentionally submitting any modifications, corrections or
+# derivatives to this work, or any other work intended for use with
+# Request Tracker, to Best Practical Solutions, LLC, you confirm that
+# you are the copyright holder for those contributions and you grant
+# Best Practical Solutions, LLC a nonexclusive, worldwide, irrevocable,
+# royalty-free, perpetual, license to use, copy, create derivative
+# works based on those contributions, and sublicense and distribute
+# those contributions and any derivatives thereof.
+#
+# END BPS TAGGED BLOCK }}}
use strict;
use Carp;
-use lib ("/opt/rt3/lib", "/opt/rt3/local/lib");
+use lib ("/opt/rt3/local/lib", "/opt/rt3/lib");
package RT;
#Connect to the database and get RT::SystemUser and RT::Nobody loaded
RT::Init();
-#Drop setgid permissions
-RT::DropSetGIDPermissions();
-
#Get the current user all loaded
my $CurrentUser = GetCurrentUser();
}
my ( $search, $condition, $action, $search_arg, $condition_arg, $action_arg,
- $template_id, $help, $verbose );
-GetOptions( "search=s" => \$search,
- "search-arg=s" => \$search_arg,
- "condition=s" => \$condition,
- "condition-arg=s" => \$condition_arg,
- "action-arg=s" => \$action_arg,
- "action=s" => \$action,
- "template-id=s" => \$template_id,
- "help" => \$help,
- "verbose|v" => \$verbose );
-
-help() if $help;
+ $template_id, $transaction, $transaction_type, $help, $verbose );
+GetOptions( "search=s" => \$search,
+ "search-arg=s" => \$search_arg,
+ "condition=s" => \$condition,
+ "condition-arg=s" => \$condition_arg,
+ "action-arg=s" => \$action_arg,
+ "action=s" => \$action,
+ "template-id=s" => \$template_id,
+ "transaction=s" => \$transaction,
+ "transaction-type=s" => \$transaction_type,
+ "help" => \$help,
+ "verbose|v" => \$verbose );
+
+help() if $help or not $search or not $action;
+
+$transaction ||= 'first';
+unless ( $transaction =~ /^(first|last)$/i ) {
+ print STDERR loc("--transaction argument could be only 'first' or 'last'");
+ exit 1;
+}
+$transaction = lc($transaction) eq 'first'? 'ASC': 'DESC';
# We _must_ have a search object
load_module($search);
# load template if specified
my $template_obj;
if ($template_id) {
- $template_obj = RT::Template->new($RT::Nobody);
- $template_obj->LoadById($template_id);
+ $template_obj = RT::Template->new($CurrentUser);
+ $template_obj->Load($template_id);
}
+my $void_scrip = RT::Scrip->new( $CurrentUser );
+my $void_scrip_action = RT::ScripAction->new( $CurrentUser );
#At the appointed time:
#find a bunch of tickets
my $tickets = RT::Tickets->new($CurrentUser);
-my $search = $search->new( TicketsObj => $tickets, Argument => $search_arg );
+my $search = $search->new(
+ TicketsObj => $tickets,
+ Argument => $search_arg,
+ CurrentUser => $CurrentUser
+);
$search->Prepare();
#for each ticket we've found
while ( my $ticket = $tickets->Next() ) {
- print "\n" . $ticket->Id() . ": " if ($verbose);
+ print $ticket->Id() . ": " if ($verbose);
+
+ my $transaction = get_transaction($ticket);
+ print loc("Using transaction #[_1]...", $transaction->id)
+ if $verbose && $transaction;
# perform some more advanced check
if ($condition) {
- my $condition_obj = $condition->new( TicketObj => $ticket,
- Argument => $condition_arg );
+ my $condition_obj = $condition->new(
+ TransactionObj => $transaction,
+ TicketObj => $ticket,
+ ScripObj => $void_scrip,
+ TemplateObj => $template_obj,
+ Argument => $condition_arg,
+ CurrentUser => $CurrentUser,
+ );
# if the condition doesn't apply, get out of here
}
#prepare our action
- my $action_obj = $action->new( TicketObj => $ticket,
- TemplateObj => $template_obj,
- Argument => $action_arg );
+ my $action_obj = $action->new(
+ TicketObj => $ticket,
+ TransactionObj => $transaction,
+ TemplateObj => $template_obj,
+ Argument => $action_arg,
+ ScripObj => $void_scrip,
+ ScripActionObj => $void_scrip_action,
+ CurrentUser => $CurrentUser,
+ );
#if our preparation, move onto the next ticket
next unless ( $action_obj->Prepare );
#commit our action.
next unless ( $action_obj->Commit );
- print loc("Action committed.") if ($verbose);
+ print loc("Action committed.\n") if ($verbose);
+}
+
+=head2 get_transaction
+
+Takes ticket and returns its transaction acording to command
+line arguments C<--transaction> and <--transaction-type>.
+
+=cut
+
+sub get_transaction {
+ my $ticket = shift;
+ my $txns = $ticket->Transactions;
+ $txns->OrderByCols(
+ { FIELD => 'Created', ORDER => $transaction },
+ { FIELD => 'id', ORDER => $transaction },
+ );
+ $txns->Limit( FIELD => 'Type', VALUE => $transaction_type )
+ if $transaction_type;
+ $txns->RowsPerPage(1);
+ return $txns->First;
}
# {{{ load_module
. loc( "[_1] - An argument to pass to [_2]", "--action-argument", "--action" )
. "\n";
print " "
+ . loc( "[_1] - Specify id of the template you want to use", "--template-id" )
+ . "\n";
+ print " "
+ . loc( "[_1] - Specify if you want to use either 'first' or 'last' tarnsaction", "--transaction" )
+ . "\n";
+ print " "
+ . loc( "[_1] - Specify the type of a transaction you want to use", "--transaction-type" )
+ . "\n";
+ print " "
. loc( "[_1] - Output status updates to STDOUT", "--verbose" ) . "\n";
print "\n";
print "\n";
)
. "\n\n";
- print " bin/rt-cron-tool \\\n";
- print
- " --search RT::Search::ActiveTicketsInQueue --search-arg general \\\n";
- print
- " --condition RT::Condition::UntouchedInHours --condition-arg 4 \\\n";
+ print " bin/rt-crontool \\\n";
+ print " --search RT::Search::ActiveTicketsInQueue --search-arg general \\\n";
+ print " --condition RT::Condition::UntouchedInHours --condition-arg 4 \\\n";
print " --action RT::Action::SetPriority --action-arg 99 \\\n";
print " --verbose\n";
print "\n";
- print loc("Escalate tickets");
- print "rt-crontool \\\n";
- print " --search RT::Search::ActiveTicketsInQueue --search-arg thequeuename \\\n";
- print " --action RT::Action::EscalatePriority \\\n";
+ print loc("Escalate tickets"). "\n";
+ print " bin/rt-crontool \\\n";
+ print " --search RT::Search::ActiveTicketsInQueue --search-arg general \\\n";
+ print " --action RT::Action::EscalatePriority\n";
#!/usr/bin/perl -w
-# BEGIN LICENSE BLOCK
+# BEGIN BPS TAGGED BLOCK {{{
#
-# Copyright (c) 1996-2003 Jesse Vincent <jesse@bestpractical.com>
+# COPYRIGHT:
+#
+# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# <jesse@bestpractical.com>
#
-# (Except where explictly superceded by other copyright notices)
+# (Except where explicitly superseded by other copyright notices)
+#
+#
+# LICENSE:
#
# 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
# 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.
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+#
+#
+# CONTRIBUTION SUBMISSION POLICY:
#
+# (The following paragraph is not intended to limit the rights granted
+# to you to modify and distribute this software under the terms of
+# the GNU General Public License and is only of importance to you if
+# you choose to contribute your changes and enhancements to the
+# community by submitting them to Best Practical Solutions, LLC.)
#
-# END LICENSE BLOCK
+# By intentionally submitting any modifications, corrections or
+# derivatives to this work, or any other work intended for use with
+# Request Tracker, to Best Practical Solutions, LLC, you confirm that
+# you are the copyright holder for those contributions and you grant
+# Best Practical Solutions, LLC a nonexclusive, worldwide, irrevocable,
+# royalty-free, perpetual, license to use, copy, create derivative
+# works based on those contributions, and sublicense and distribute
+# those contributions and any derivatives thereof.
+#
+# 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, "|/opt/rt3/bin/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, "|/opt/rt3/bin/rt-mailgate --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, "|/opt/rt3/bin/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, "|/opt/rt3/bin/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, "|/opt/rt3/bin/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, "|/opt/rt3/bin/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, "|/opt/rt3/bin/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, "|/opt/rt3/bin/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 => '/opt/rt3/share/html/NoAuth/images/spacer.gif',
- Type => 'image/gif',
- Encoding => 'base64');
-
-# Create a ticket with a binary attachment
-ok(open(MAIL, "|/opt/rt3/bin/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;
-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, "|/opt/rt3/bin/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, "|/opt/rt3/bin/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
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} } );
);
# Read the message in from STDIN
-$args{'message'} = <>;
+$args{'message'} = do { local (@ARGV, $/); <> };
+unless ( $args{message} =~ /\S/ ) {
+ print STDERR "$0: no message passed on STDIN!\n";
+ exit 0;
+}
if ($opts{'extension'}) {
$args{$opts{'extension'}} = $ENV{'EXTENSION'};
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) ]
=item C<--action>
-Specifies whether this is a correspondence or comment address.
+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>.
=item C<--queue>
-Reflects which queue this address handles.
+This flag determines which queue this alias should create a ticket in if no ticket identifier
+is found.
=item C<--url>
-The location of the web server for your RT instance.
+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.
=item C<--extension> OPTIONAL
=item Message
A C<MIME::Entity> object representing the email
+
=item CurrentUser
An C<RT::CurrentUser> object
# {{{ Base Configuration
-# $rtname the string that RT will look for in mail messages to
+# $rtname is the string that RT will look for in mail messages to
# figure out what ticket a new piece of mail belongs to
# Your domain name is recommended, so as not to pollute the namespace.
Set($rtname , "example.com");
+
+# This regexp controls what subject tags RT recognizes as its own.
+# If you're not dealing with historical $rtname values, you'll likely
+# never have to enable this feature.
+#
+# Be VERY CAREFUL with it. Note that it overrides $rtname for subject
+# token matching and that you should use only "non-capturing" parenthesis
+# grouping. For example:
+#
+# Set($EmailSubjectTagRegex, qr/(?:example.com|example.org)/i );
+#
+# and NOT
+#
+# Set($EmailSubjectTagRegex, qr/(example.com|example.org)/i );
+#
+# This setting would make RT behave exactly as it does without the
+# setting enabled.
+#
+# Set($EmailSubjectTagRegex, qr/\Q$rtname\E/i );
+
+
+
# You should set this to your organization's DNS domain. For example,
# fsck.com or asylum.arkham.ma.us. It's used by the linking interface to
# guarantee that ticket URIs are unique and easy to construct.
# }}}
-# }}}
-
# {{{ Database Configuration
# Database driver beeing used. Case matters
# Valid types are "mysql", "Oracle" and "Pg"
-Set($DatabaseType , 'mysql');
+Set($DatabaseType , 'Pg');
# The domain name of your database server
# If you're running mysql and it's on localhost,
Set($DatabasePort , '');
#The name of the database user (inside the database)
-Set($DatabaseUser , 'rt_user');
+Set($DatabaseUser , 'freeside');
# Password the DatabaseUser should use to access the database
-Set($DatabasePassword , 'rt_pass');
+Set($DatabasePassword , '');
# The name of the RT's database on your database server
-Set($DatabaseName , 'rt3');
+Set($DatabaseName , 'freeside');
# If you're using Postgres and have compiled in SSL support,
# set DatabaseRequireSSL to 1 to turn on SSL communication
Set($LoopsToRTOwner , 1);
-# If $StoreLoopss is defined, RT will record messages that it believes
+# If $StoreLoops is defined, RT will record messages that it believes
# to be part of mail loops.
# As it does this, it will try to be careful not to send mail to the
# sender of these messages
Set($MaxAttachmentSize , 10000000);
# $TruncateLongAttachments: if this is set to a non-undef value,
-# RT will truncate attachments longer than MaxAttachmentLength.
+# RT will truncate attachments longer than MaxAttachmentSize.
Set($TruncateLongAttachments , undef);
# $DropLongAttachments: if this is set to a non-undef value,
-# RT will silently drop attachments longer than MaxAttachmentLength.
+# RT will silently drop attachments longer than MaxAttachmentSize.
Set($DropLongAttachments , undef);
# (These values are passed to the CanonicalizeEmailAddress subroutine in RT/User.pm)
# By default, that routine performs a s/$Match/$Replace/gi on any address passed to it
-Set($CanonicalizeEmailAddressMatch , 'subdomain.example.com$');
-Set($CanonicalizeEmailAddressReplace , 'example.com');
+#Set($CanonicalizeEmailAddressMatch , '@subdomain\.example\.com$');
+#Set($CanonicalizeEmailAddressReplace , '@example.com');
+
+# set this to true and the create new user page will use the values that you
+# enter in the form but use the function CanonicalizeUserInfo in User_Local.pm
+Set($CanonicalizeOnCreate , 0);
# If $SenderMustExistInExternalDatabase is true, RT will refuse to
# create non-privileged accounts for unknown users if you are using
# If 'sendmailpipe' doesn't work well for you, try 'sendmail'
#
# Note that you should remove the '-t' from $SendmailArguments
-# if you use 'sendmail rather than 'sendmailpipe'
+# if you use 'sendmail' rather than 'sendmailpipe'
Set($MailCommand , 'sendmailpipe');
# These options are good for most sendmail wrappers and workalikes
Set($SendmailArguments , "-oi -t");
+# $SendmailBounceArguments defines what flags to pass to $Sendmail
+# assuming RT needs to send an error (ie. bounce).
+
+Set($SendmailBounceArguments , '-f "<>"');
+
# These arguments are good for sendmail brand sendmail 8 and newer
#Set($SendmailArguments,"-oi -t -ODeliveryMode=b -OErrorMode=m");
# are WatcherType and TicketId.
Set($FriendlyToLineFormat, "\"%s of $RT::rtname Ticket #%s\":;");
-# By default RT doesn't notify the person who performs an update, as they
+# By default, RT doesn't notify the person who performs an update, as they
# already know what they've done. If you'd like to change this behaviour,
# Set $NotifyActor to 1
Set($NotifyActor, 0);
+# By default, RT records each message it sends out to its own internal database.# To change this behaviour, set $RecordOutgoingEmail to 0
+
+Set($RecordOutgoingEmail, 1);
# }}}
Set($LogDir, '/opt/rt3/var/log');
Set($LogToFileNamed , "rt.log"); #log to rt.log
+# On Solaris or UnixWare, set to ( socket => 'inet' ). Options here
+# override any other options RT passes to Log::Dispatch::Syslog.
+# Other interesting flags include facility and logopt. (See the
+# Log::Dispatch::Syslog documentation for more information.) (Maybe
+# ident too, if you have multiple RT installations.)
+
+@LogToSyslogConf = () unless (@LogToSyslogConf);
+
# }}}
# {{{ Web interface configuration
# This is the Scheme, server and port for constructing urls to webrt
# $WebBaseURL doesn't need a trailing /
-Set($WebBaseURL , "http://RT::WebBaseURL.not.configured:80");
+Set($WebBaseURL , "http://localhost");
Set($WebURL , $WebBaseURL . $WebPath . "/");
# $WebImagesURL points to the base URL where RT can find its images.
-Set($WebImagesURL , $WebURL . "NoAuth/images/");
+Set($WebImagesURL , $WebPath . "/NoAuth/images/");
+
+# $LogoURL points to the URL of the RT logo displayed in the web UI
-# $RTLogoURL points to the URL of the RT logo displayed in the web UI
+Set($LogoURL , $WebImagesURL . "bplogo.gif");
-Set($LogoURL , $WebImagesURL . "rt.jpg");
+# WebNoAuthRegex - What portion of RT's URLspace should not require
+# authentication.
+Set($WebNoAuthRegex, qr!^(?:/+NoAuth/|
+ /+REST/\d+\.\d+/NoAuth/)!x );
# For message boxes, set the entry box width and what type of wrapping
# to use.
# sent in a request (although there is probably more to it than that)
Set($TrustHTMLAttachments , undef);
+# Should RT redistribute correspondence that it identifies as
+# machine generated? A true value (the default) will do so, setting
+# this to '0' will cause no such messages to be redistributed.
+# You can also use 'privileged', which will redistribute only to
+# privileged users. This is seful if you get malformed bounces caused by
+# autocreated requestors with bogus addresses.
+Set($RedistributeAutoGeneratedMessages, 1);
+
+# If PreferRichText is set to a true value, RT will show HTML/Rich text
+# messages in preference to their plaintext alternatives. RT "scrubs" the
+# html to show only a minimal subset of HTML to avoid possible contamination
+# by cross-site-scripting attacks.
+Set($PreferRichText, undef);
+
# If $WebExternalAuth is defined, RT will defer to the environment's
# REMOTE_USER variable.
# Set($WebSessionClass , 'Apache::Session::File');
+# By default, RT clears its database cache after every page view.
+# This ensures that you've always got the most current information
+# when working in a multi-process (mod_perl or FastCGI) Environment
+# Setting $WebFlushDbCacheEveryRequest to '0' will turn this off,
+# which will speed RT up a bit, at the expense of a tiny bit of data
+# accuracy
+
+Set($WebFlushDbCacheEveryRequest, '1');
+
+
# $MaxInlineBody is the maximum attachment size that we want to see
# inline when viewing a transaction. 13456 is a random sane-sounding
# default.
Set($MaxInlineBody, 13456);
-# $MyTicketsLength is the length of the table on the front page.
-# For some people, the default of 10 isn't big enough to get a feel for
-# how much work needs to be done before you get some time off.
+# By default, RT shows newest transactions at the bottom of the ticket
+# history page, if you want see them at the top set this to '0'.
+
+Set($OldestTransactionsFirst, '1');
+
+# $MyTicketsLength is the length of the owned tickets table on the
+# front page. For some people, the default of 10 isn't big enough
+# to get a feel for how much work needs to be done before you get
+# some time off.
Set($MyTicketsLength, 10);
+# $MyRequestsLength is the length of the requested tickets table
+# on the front page.
+
+Set($MyRequestsLength, 10);
+
# @MasonParameters is the list of parameters for the constructor of
# HTML::Mason's Apache or CGI Handler. This is normally only useful
-# for debugging, eg. profiling individual components with
-# (preamble => 'my $p = MasonX::Profiler->new($m, $r);');
+# for debugging, eg. profiling individual components with:
+# use MasonX::Profiler; # available on CPAN
+# @MasonParameters = (preamble => 'my $p = MasonX::Profiler->new($m, $r);');
@MasonParameters = () unless (@MasonParameters);
+# $DefaultSearchResultFormat is the default format for RT search results
+Set ($DefaultSearchResultFormat, qq{
+ '<B><A HREF="$RT::WebPath/Ticket/Display.html?id=__id__">__id__</a></B>/TITLE:#',
+ '<B><A HREF="$RT::WebPath/Ticket/Display.html?id=__id__">__Subject__</a></B>/TITLE:Subject',
+ Status,
+ QueueName,
+ OwnerName,
+ Priority,
+ '__NEWLINE__',
+ '',
+ '<small>__Requestors__</small>',
+ '<small>__CreatedRelative__</small>',
+ '<small>__ToldRelative__</small>',
+ '<small>__LastUpdatedRelative__</small>',
+ '<small>__TimeLeft__</small>'});
+
+
# }}}
# {{{ RT UTF-8 Settings
# An array that contains languages supported by RT's internationalization
-# interface. Defaults to all *.po lexicons; set it to qw(en ja) will make
-# RT bilingual instead of multilingual, but will save same memory.
+# interface. Defaults to all *.po lexicons; setting it to qw(en ja) will make
+# RT bilingual instead of multilingual, but will save some memory.
@LexiconLanguages = qw(*) unless (@LexiconLanguages);
# }}}
+# {{{ Miscellaneous RT Settings
+
+# You can define new statuses and even reorder existing statuses here.
+# WARNING. DO NOT DELETE ANY OF THE DEFAULT STATUSES. If you do, RT
+# will break horribly.
+
+@ActiveStatus = qw(new open stalled) unless @ActiveStatus;
+@InactiveStatus = qw(resolved rejected deleted) unless @InactiveStatus;
+
+# Backward compatability setting. Add/Delete Link used to record one
+# transaction and run one scrip. Set this value to 0 if you want
+# both link transactions to have a scrip run.
+Set($LinkTransactionsRun1Scrip , 1);
+
+# }}}
+
+
+# {{{ Development Mode
+#
+# RT comes with a "Development mode" setting.
+# This setting, as a convenience for developers, turns on
+# all sorts of development options that you most likely don't want in
+# production:
+#
+# * Turns off Mason's 'static_source' directive. By default, you can't
+# edit RT's web ui components on the fly and have RT magically pick up
+# your changes. (It's a big performance hit)
+#
+# * More to come
+#
+
+Set($DevelMode, '0');
+
+# }}}
+
+
1;
-# BEGIN LICENSE BLOCK
+# BEGIN BPS TAGGED BLOCK {{{
#
-# Copyright (c) 1996-2002 Jesse Vincent <jesse@bestpractical.com>
+# COPYRIGHT:
+#
+# This software is Copyright (c) 1996-2005 Best Practical Solutions, LLC
+# <jesse@bestpractical.com>
#
-# (Except where explictly superceded by other copyright notices)
+# (Except where explicitly superseded by other copyright notices)
+#
+#
+# LICENSE:
#
# 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
+# 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.
#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
#
-# 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.
#
+# CONTRIBUTION SUBMISSION POLICY:
#
-# END LICENSE BLOCK
-
-
+# (The following paragraph is not intended to limit the rights granted
+# to you to modify and distribute this software under the terms of
+# the GNU General Public License and is only of importance to you if
+# you choose to contribute your changes and enhancements to the
+# community by submitting them to Best Practical Solutions, LLC.)
+#
+# By intentionally submitting any modifications, corrections or
+# derivatives to this work, or any other work intended for use with
+# Request Tracker, to Best Practical Solutions, LLC, you confirm that
+# you are the copyright holder for those contributions and you grant
+# Best Practical Solutions, LLC a nonexclusive, worldwide, irrevocable,
+# royalty-free, perpetual, license to use, copy, create derivative
+# works based on those contributions, and sublicense and distribute
+# those contributions and any derivatives thereof.
+#
+# END BPS TAGGED BLOCK }}}
package RT;
use strict;
use RT::I18N;
use vars qw($VERSION $System $SystemUser $Nobody $Handle $Logger
$CORE_CONFIG_FILE
$SITE_CONFIG_FILE
- $VENDOR_CONFIG_FILE
$BasePath
$EtcPath
$VarPath
$LocalEtcPath
$LocalLexiconPath
$LogDir
+ $BinPath
$MasonComponentRoot
$MasonLocalComponentRoot
$MasonDataDir
$MasonSessionDir
);
-$VERSION = '3.0.9';
+$VERSION = '3.4.6';
$CORE_CONFIG_FILE = "/opt/rt3/etc/RT_Config.pm";
$SITE_CONFIG_FILE = "/opt/rt3/etc/RT_SiteConfig.pm";
+
+
$BasePath = '/opt/rt3';
$EtcPath = '/opt/rt3/etc';
+$BinPath = '/opt/rt3/bin';
$VarPath = '/opt/rt3/var';
$LocalPath = '/opt/rt3/local';
$LocalEtcPath = '/opt/rt3/local/etc';
# $MasonComponentRoot is where your rt instance keeps its mason html files
-$MasonComponentRoot = '/opt/rt3/share/html';
+$MasonComponentRoot = '/var/www/freeside/rt';
# $MasonLocalComponentRoot is where your rt instance keeps its site-local
# mason html files.
# $MasonDataDir Where mason keeps its datafiles
-$MasonDataDir = '/opt/rt3/var/mason_data';
+$MasonDataDir = '/usr/local/etc/freeside/masondata';
# RT needs to put session data (for preserving state between connections
# via the web interface)
=head1 NAME
- RT - Request Tracker
+RT - Request Tracker
=head1 SYNOPSIS
- A fully featured request tracker package
+A fully featured request tracker package
=head1 DESCRIPTION
+=head2 LoadConfig
-=cut
-
-=item LoadConfig
+Load RT's config file. First, the site configuration file
+(C<RT_SiteConfig.pm>) is loaded, in order to establish overall site
+settings like hostname and name of RT instance. Then, the core
+configuration file (C<RT_Config.pm>) is loaded to set fallback values
+for all settings; it bases some values on settings from the site
+configuration file.
-Load RT's config file. First, go after the core config file.
-After that, try to load the vendor config.
-After that, go after the site config.
+In order for the core configuration to not override the site's
+settings, the function C<Set> is used; it only sets values if they
+have not been set already.
=cut
RT::I18N->Init;
}
-=item Init
+=head2 Init
+
+Conenct to the database, set up logging.
- Conenct to the database, set up logging.
-
=cut
sub Init {
$System = RT::System->new();
- InitLogging();
+ InitClasses();
+ InitLogging();
}
Get a database connection
=cut
-
+
sub ConnectToDatabase {
require RT::Handle;
unless ($Handle && $Handle->dbh && $Handle->dbh->ping) {
Create the RT::Logger object.
=cut
+
sub InitLogging {
- # We have to set the record seperator ($, man perlvar)
+ # We have to set the record separator ($, man perlvar)
# or Log::Dispatch starts getting
# really pissy, as some other module we use unsets it.
$RT::Logger=Log::Dispatch->new();
if ($RT::LogToFile) {
-
- unless (-d $RT::LogDir && -w $RT::LogDir) {
- # localizing here would be hard when we don't have a current user yet
- # die $self->loc("Log directory [_1] not found or couldn't be written.\n RT can't run.", $RT::LogDir);
- die ("Log directory $RT::LogDir not found or couldn't be written.\n RT can't run.");
- }
-
- my $filename;
+ my ($filename, $logdir);
if ($RT::LogToFileNamed =~ m![/\\]!) {
# looks like an absolute path.
$filename = $RT::LogToFileNamed;
+ ($logdir) = $RT::LogToFileNamed =~ m!^(.*[/\\])!;
}
else {
$filename = "$RT::LogDir/$RT::LogToFileNamed";
+ $logdir = $RT::LogDir;
}
+
+ unless ( -d $logdir && ( ( -f $filename && -w $filename ) || -w $logdir ) ) {
+ # localizing here would be hard when we don't have a current user yet
+ # die $self->loc("Log directory [_1] not found or couldn't be written.\n RT can't run.", $RT::LogDir);
+ die ("Log file $filename couldn't be written or created.\n RT can't run.");
+ }
+
+ package Log::Dispatch::File;
require Log::Dispatch::File;
));
}
if ($RT::LogToScreen) {
+ package Log::Dispatch::Screen;
require Log::Dispatch::Screen;
$RT::Logger->add(Log::Dispatch::Screen->new
( name => 'screen',
));
}
if ($RT::LogToSyslog) {
+ package Log::Dispatch::Syslog;
require Log::Dispatch::Syslog;
$RT::Logger->add(Log::Dispatch::Syslog->new
( name => 'syslog',
return "$p{message} ($filename:$line)\n"}
},
- stderr => 1
+ stderr => 1,
+ @RT::LogToSyslogConf
));
}
## Mason). It will log all problems through the standard logging
## mechanism (see above).
-$SIG{__WARN__} = sub {$RT::Logger->warning($_[0])};
+$SIG{__WARN__} = sub {
+ my $w = shift;
+ $w =~ s/(?:\r*\n)+$//;
+ # The 'wide character' warnings has to be silenced for now, at least
+ # until HTML::Mason offers a sane way to process both raw output and
+ # unicode strings.
+ $RT::Logger->warning($w) if index($w, 'Wide character in ') != 0;
+};
#When we call die, trap it and log->crit with the value of the die.
unless ($^S || !defined $^S ) {
$RT::Handle->Rollback();
$RT::Logger->crit("$_[0]");
- exit(-1);
- }
- else {
- #Get out of here if we're in an eval
- die $_[0];
}
+ die $_[0];
};
# }}}
}
+=head2 InitClasses
+
+Load all modules that define base classes
+
+=cut
+
+sub InitClasses {
+ require RT::Tickets;
+ require RT::Transactions;
+ require RT::Users;
+ require RT::CurrentUser;
+ require RT::Templates;
+ require RT::Queues;
+ require RT::ScripActions;
+ require RT::ScripConditions;
+ require RT::Scrips;
+ require RT::Groups;
+ require RT::GroupMembers;
+ require RT::CustomFields;
+ require RT::CustomFieldValues;
+ require RT::ObjectCustomFields;
+ require RT::ObjectCustomFieldValues;
+}
+
# }}}
return ($Nobody);
}
-
-=head2 DropSetGIDPermissions
-
-Drops setgid permissions.
-
-=cut
-
-sub DropSetGIDPermissions {
- # Now that we got the config read in, we have the database
- # password and don't need to be setgid
- # make the effective group the real group
- $) = $(;
-}
-
-
-=head1 SYNOPSIS
-
=head1 BUGS
-Please report them to rt-3.0-bugs@fsck.com, if you know what's broken and have at least some idea of what needs to be fixed.
-If you're not sure what's going on, report them rt-devel@lists.fsck.com.
+Please report them to rt-bugs@fsck.com, if you know what's broken and have at least
+some idea of what needs to be fixed.
+
+If you're not sure what's going on, report them rt-devel@lists.bestpractical.com.
=head1 SEE ALSO
L<RT::StyleGuide>
L<DBIx::SearchBuilder>
-
-
=begin testing
-
ok ($RT::Nobody->Name() eq 'Nobody', "Nobody is nobody");
ok ($RT::Nobody->Name() ne 'root', "Nobody isn't named root");
ok ($RT::SystemUser->Name() eq 'RT_System', "The system user is RT_System");
ok ($RT::SystemUser->Name() ne 'noname', "The system user isn't noname");
-
=end testing
=cut