[Rt-commit] r7372 - in rt/branches/3.7-EXPERIMENTAL-TUNIS: . html
html/Elements/RT__Ticket html/Search/Elements html/Ticket
html/Ticket/Elements lib/RT lib/RT/Interface lib/RT/Interface/Web
clkao at bestpractical.com
clkao at bestpractical.com
Tue Mar 27 10:57:23 EDT 2007
Author: clkao
Date: Tue Mar 27 10:57:22 2007
New Revision: 7372
Modified:
rt/branches/3.7-EXPERIMENTAL-TUNIS/ (props changed)
rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Elements/RT__Ticket/ColumnMap
rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Search/Elements/BuildFormatString
rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Search/Elements/EditFormat
rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Ticket/Elements/ShowHistory
rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Ticket/Forward.html
rt/branches/3.7-EXPERIMENTAL-TUNIS/html/autohandler
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Action/Notify.pm
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Action/SendEmail.pm
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Attachment_Overlay.pm
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Attachments_Overlay.pm
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Email.pm
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web.pm
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web/Handler.pm
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web/Request.pm
rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Transaction_Overlay.pm
Log:
merge down.
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Elements/RT__Ticket/ColumnMap
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Elements/RT__Ticket/ColumnMap (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Elements/RT__Ticket/ColumnMap Tue Mar 27 10:57:22 2007
@@ -60,42 +60,13 @@
if ( $COLUMN_MAP->{$name} ) {
return ( $COLUMN_MAP->{$name}->{$attr} );
}
+ elsif ( (my ($mainkey, $subkey) = $name =~ /^(.*?)\.{(.+)}$/) && $COLUMN_MAP->{$1} ) {
+ return $COLUMN_MAP->{$mainkey}->{$attr}
+ unless ref $COLUMN_MAP->{$mainkey}->{$attr} eq 'CODE';
- # now, let's deal with harder things, like Custom Fields
-
- elsif ( $name =~ /^(?:CF|CustomField)\.\{(.+)\}$/ ) {
- my $field = $1;
-
- if ( $attr eq 'attribute' ) {
- return (undef);
- }
- elsif ( $attr eq 'title' ) {
- return ( $field );
- }
- elsif ( $attr eq 'value' ) {
- # Display custom field contents, separated by newlines.
- # For Image custom fields we also show a thumbnail here.
- return sub {
- my $values = $_[0]->CustomFieldValues($field);
- my @values = map {
- (
- ($_->CustomFieldObj->Type eq 'Image')
- ? \($m->scomp( '/Elements/ShowCustomFieldImage', Object => $_ ))
- : $_->Content
- ),
- \'<br />',
- } @{ $values->ItemsArrayRef };
- pop @values; # Remove that last <br />
- return @values;
- };
- }
- }
- elsif ( $name =~ /^(WebPath|WebBaseURL|WebURL)$/ ) {
- if ( $attr eq 'value' ) {
- my $value = RT->Config->Get($1);
- return sub { return \$value };
- }
+ return sub { $COLUMN_MAP->{$mainkey}->{$attr}->( @_, $subkey ) };
}
+
};
my $LinkCallback = sub {
@@ -309,6 +280,12 @@
$_ => { value => $LinkCallback->( $_ ) }
} keys %RT::Ticket::LINKTYPEMAP),
+ (map {
+ my $value = RT->Config->Get($_);
+ $_ => { value => sub { return \$value } };
+
+ } qw(WebPath WebBaseURL WebURL)),
+
'_CLASS' => {
value => sub { return $_[1] % 2 ? 'oddline' : 'evenline' }
},
@@ -319,9 +296,33 @@
value => sub { return \('<input type="checkbox" class="checkbox" name="UpdateTicket'.$_[0]->id.'" value="1" checked />') }
},
+ CustomField => {
+ attribute => undef,
+ title => sub { return pop @_ },
+ value => sub {
+ # Display custom field contents, separated by newlines.
+ # For Image custom fields we also show a thumbnail here.
+
+ my $values = $_[0]->CustomFieldValues( $_[-1] );
+ my @values = map {
+ (
+ ($_->CustomFieldObj->Type eq 'Image')
+ ? \($m->scomp( '/Elements/ShowCustomFieldImage', Object => $_ ))
+ : $_->Content
+ ),
+ \'<br />',
+ } @{ $values->ItemsArrayRef };
+ pop @values; # Remove that last <br />
+ return @values;
+ },
+ },
};
+
+$COLUMN_MAP->{'CF'} = $COLUMN_MAP->{'CustomField'};
+
</%ONCE>
<%init>
-$m->callback( COLUMN_MAP => $COLUMN_MAP, CallbackName => 'ColumnMap', CallbackOnce => 1 );
+$m->callback( COLUMN_MAP => $COLUMN_MAP, CallbackName => 'Once', CallbackOnce => 1 );
+$m->callback( COLUMN_MAP => $COLUMN_MAP, CallbackName => 'ColumnMap' );
return $ColumnMap->( $Name, $Attr );
</%init>
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Search/Elements/BuildFormatString
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Search/Elements/BuildFormatString (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Search/Elements/BuildFormatString Tue Mar 27 10:57:22 2007
@@ -43,69 +43,58 @@
%# those contributions and any derivatives thereof.
%#
%# END BPS TAGGED BLOCK }}}
-<%args>
-$Format => undef
+<%ARGS>
+$Format => RT->Config->Get('DefaultSearchResultFormat')
+
%cfqueues => undef
+
$Face => undef
$Size => undef
$Link => undef
$Title => undef
+
$AddCol => undef
$RemoveCol => undef
$ColUp => undef
$ColDown => undef
+
$SelectDisplayColumns => undef
$CurrentDisplayColumns => undef
-</%args>
-<%init>
-
-$Format ||= RT->Config->Get('DefaultSearchResultFormat');
+</%ARGS>
+<%ONCE>
# All the things we can display in the format string by default
my @fields = qw(
- id
- Status
- ExtendedStatus
- Subject
- QueueName
- OwnerName
- Priority
- InitialPriority
- FinalPriority
- Type
- TimeWorked
- TimeLeft
- TimeEstimated
- CreatedBy
- LastUpdatedBy
- Requestors
- Cc
- AdminCc
- Starts
- StartsRelative
- Started
- StartedRelative
- Created
- CreatedRelative
- LastUpdated
- LastUpdatedRelative
- Told
- ToldRelative
- Due
- DueRelative
- Resolved
- ResolvedRelative
- RefersTo
- ReferredToBy
- DependsOn
- DependedOnBy
- MemberOf
- Members
- Parents
- Children
- NEWLINE
+ id QueueName Subject
+ Status ExtendedStatus UpdateStatus
+ Type
+
+ OwnerName Requestors Cc AdminCc CreatedBy LastUpdatedBy
+
+ Priority InitialPriority FinalPriority
+
+ TimeWorked TimeLeft TimeEstimated
+
+ Starts StartsRelative
+ Started StartedRelative
+ Created CreatedRelative
+ LastUpdated LastUpdatedRelative
+ Told ToldRelative
+ Due DueRelative
+ Resolved ResolvedRelative
+
+ RefersTo ReferredToBy
+ DependsOn DependedOnBy
+ MemberOf Members
+ Parents Children
+
+ NEWLINE
);
+</%ONCE>
+<%init>
+$m->callback( CallbackOnce => 1, CallbackName => 'SetFieldsOnce', Fields => \@fields );
+
my $CustomFields = RT::CustomFields->new( $session{'CurrentUser'});
foreach my $id (keys %cfqueues) {
# Gotta load up the $queue object, since queues get stored by name now. my $id
@@ -126,6 +115,8 @@
push @fields, "CustomField.{" . $CustomField->Name . "}";
}
+$m->callback( Fields => \@fields, ARGSRef => \%ARGS );
+
my ( @seen);
my @format = split( /,\s*/, $Format );
@@ -161,44 +152,44 @@
}
elsif ( $AddCol ) {
if ( defined $SelectDisplayColumns ) {
- my $selected = $SelectDisplayColumns;
- my @columns;
- if (ref($selected) eq 'ARRAY') {
- @columns = @$selected;
- } else {
- push @columns, $selected;
- }
- foreach my $col (@columns) {
- my %column = ();
- $column{Column} = $col;
-
- if ( $Face eq "Bold" ) {
- $column{Prefix} .= "<b>";
- $column{Suffix} .= "</b>";
- }
- if ( $Face eq "Italic" ) {
- $column{Prefix} .= "<i>";
- $column{Suffix} .= "</i>";
- }
- if ($Size) {
- $column{Prefix} .= "<" . $m->interp->apply_escapes( $Size, 'h' ) . ">";
- $column{Suffix} .= "</" . $m->interp->apply_escapes( $Size, 'h' ) . ">";
- }
- if ( $Link eq "Display" ) {
- $column{Prefix} .= q{<a HREF="__WebPath__/Ticket/Display.html?id=__id__">};
- $column{Suffix} .= "</a>";
- }
- elsif ( $Link eq "Take" ) {
- $column{Prefix} .= q{<a HREF="__WebPath__/Ticket/Display.html?Action=Take&id=__id__">};
- $column{Suffix} .= "</a>";
- }
-
- if ($Title) {
- $column{Suffix} .= "/TITLE:" . $m->interp->apply_escapes( $Title, 'h' );
+ my $selected = $SelectDisplayColumns;
+ my @columns;
+ if (ref($selected) eq 'ARRAY') {
+ @columns = @$selected;
+ } else {
+ push @columns, $selected;
+ }
+ foreach my $col (@columns) {
+ my %column = ();
+ $column{Column} = $col;
+
+ if ( $Face eq "Bold" ) {
+ $column{Prefix} .= "<b>";
+ $column{Suffix} .= "</b>";
+ }
+ if ( $Face eq "Italic" ) {
+ $column{Prefix} .= "<i>";
+ $column{Suffix} .= "</i>";
+ }
+ if ($Size) {
+ $column{Prefix} .= "<" . $m->interp->apply_escapes( $Size, 'h' ) . ">";
+ $column{Suffix} .= "</" . $m->interp->apply_escapes( $Size, 'h' ) . ">";
+ }
+ if ( $Link eq "Display" ) {
+ $column{Prefix} .= q{<a HREF="__WebPath__/Ticket/Display.html?id=__id__">};
+ $column{Suffix} .= "</a>";
+ }
+ elsif ( $Link eq "Take" ) {
+ $column{Prefix} .= q{<a HREF="__WebPath__/Ticket/Display.html?Action=Take&id=__id__">};
+ $column{Suffix} .= "</a>";
+ }
+
+ if ($Title) {
+ $column{Suffix} .= "/TITLE:" . $m->interp->apply_escapes( $Title, 'h' );
+ }
+ push @seen, \%column;
+ }
}
- push @seen, \%column;
-}
-}
}
elsif ( $ColUp ) {
my $index = $CurrentDisplayColumns;
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Search/Elements/EditFormat
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Search/Elements/EditFormat (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Search/Elements/EditFormat Tue Mar 27 10:57:22 2007
@@ -44,28 +44,23 @@
%#
%# END BPS TAGGED BLOCK }}}
<table>
+
<tr>
-<td>
-<&|/l&>Add Columns</&>:
-</td>
-<td>
-<&|/l&>Format</&>:
-</td>
-<td></td>
-<td>
-<&|/l&>Show Columns</&>:
-</td>
+<th><&|/l&>Add Columns</&>:</th>
+<th><&|/l&>Format</&>:</th>
+<th></th>
+<th><&|/l&>Show Columns</&>:</th>
+</tr>
+
<tr>
-<td valign="top">
-<select size="6" name="SelectDisplayColumns" multiple>
+
+<td valign="top"><select size="6" name="SelectDisplayColumns" multiple>
% foreach my $field ( @$AvailableColumns) {
-<option value="<%$field%>"><% loc( $field) %></option>
-%# $m->comp( '/Elements/RT__Ticket/ColumnMap', Name => $field, Attr => 'title') ||
+<option value="<% $field %>"><% loc($field) %></option>
% }
-</select>
-</td>
-<td>
-<&|/l&>Link</&>:
+</select></td>
+
+<td><&|/l&>Link</&>:
<select name="Link">
<option value="None">-</option>
<option value="Display"><&|/l&>Display</&></option>
@@ -85,15 +80,14 @@
<option value="Italic"><&|/l&>Italic</&></option>
</select>
</td>
-<td>
-<input type="submit" class="button" name="AddCol" value=" → " />
-</td>
+
+<td><input type="submit" class="button" name="AddCol" value=" → " /></td>
+
<td valign="top">
<select size="4" name="CurrentDisplayColumns">
% my $i=0;
-% foreach my $field (@$CurrentFormat) {
-<option value="<%$i++%>><%$field->{Column}%>">
-<%loc( $field->{Column}) %></option>
+% foreach my $field ( @$CurrentFormat ) {
+<option value="<% $i++ %>><% $field->{Column} %>"><% loc( $field->{Column} ) %></option>
% }
</select>
<br />
@@ -103,8 +97,7 @@
<input type="submit" class="button" name="RemoveCol" value="<%loc('Delete')%>" />
</center>
</td>
-<td colspan="3" align="center">
-</td>
+
</tr>
</table>
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Ticket/Elements/ShowHistory
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Ticket/Elements/ShowHistory (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Ticket/Elements/ShowHistory Tue Mar 27 10:57:22 2007
@@ -104,14 +104,10 @@
$m->comp( 'ShowTransaction',
%ARGS,
- AttachPath => $AttachPath,
- UpdatePath => $UpdatePath,
Ticket => $Ticket,
Transaction => $Transaction,
ShowHeaders => $ShowHeaders,
- Collapsed => $Collapsed,
RowNum => $i,
- ShowTitleBarCommands => $ShowTitleBarCommands,
Attachments => \@trans_attachments,
AttachmentContent => $trans_content,
LastTransaction => $Transactions->IsLast
@@ -158,10 +154,6 @@
$Attachments => undef
$AttachmentContent => undef
$ShowHeaders => undef
-$Collapsed => undef
$ShowTitle => 1
$ShowDisplayModes => 1
-$ShowTitleBarCommands => 1
-$AttachPath => RT->Config->Get('WebPath')."/Ticket/Attachment"
-$UpdatePath => RT->Config->Get('WebPath')."/Ticket/Update.html"
</%ARGS>
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Ticket/Forward.html
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Ticket/Forward.html (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/html/Ticket/Forward.html Tue Mar 27 10:57:22 2007
@@ -39,75 +39,9 @@
Abort( loc("Couldn't load transaction #[_1]", $QuoteTransaction) )
unless $txn->id;
-my $create_entity = sub {
- my $attachment = shift;
-
- my $entity = new MIME::Entity;
- $entity->head->add( split /:/, $_, 2 )
- foreach $attachment->SplitHeaders;
-
- use MIME::Body;
- $entity->bodyhandle(
- MIME::Body::Scalar->new( $attachment->OriginalContent )
- );
-
- return $entity;
-};
-
-
if ( $ARGS{'Forward'} ) {
- my $main_content = $txn->ContentObj;
-
- my $entity = $create_entity->( $main_content );
- if ( $main_content->Parent ) {
- # main content is not top most entity, we shouldn't loose
- # From/To/Cc headers that are on a top part
- my $attachments = RT::Attachments->new( $session{'CurrentUser'} );
- $attachments->Columns(qw(id Parent TransactionId Headers));
- $attachments->Limit( FIELD => 'TransactionId', VALUE => $txn->id );
- $attachments->Limit( FIELD => 'Parent', VALUE => 0 );
- $attachments->Limit( FIELD => 'Parent', OERATOR => 'IS', VALUE => 'NULL', QUOTEVALUE => 0 );
- $attachments->OrderBy( FIELD => 'id', ORDER => 'ASC' );
- my $tmp = $attachments->First;
- if ( $tmp && $tmp->id ne $main_content->id ) {
- $entity->make_multipart;
- $entity->head->add( split /:/, $_, 2 ) foreach $tmp->SplitHeaders;
- $entity->make_singlepart;
- }
- }
-
- my $attachments = RT::Attachments->new( $session{'CurrentUser'} );
- $attachments->Limit( FIELD => 'TransactionId', VALUE => $txn->id );
- $attachments->Limit(
- FIELD => 'id',
- OPERATOR => '!=',
- VALUE => $main_content->id,
- );
- $attachments->Limit(
- FIELD => 'ContentType',
- OPERATOR => 'NOT STARTSWITH',
- VALUE => 'multipart/',
- );
- $attachments->Limit(
- FIELD => 'Content',
- OPERATOR => '!=',
- VALUE => '',
- );
- while ( my $a = $attachments->Next ) {
- $entity->make_multipart;
- $entity->add_part( $create_entity->( $a ) );
- }
-
- my $mail = MIME::Entity->build(
- To => $ARGS{'To'},
- Cc => $ARGS{'Cc'},
- Bcc => $ARGS{'Bcc'},
- Subject => 'Fwd: '. ($txn->Subject || $TicketObj->Subject ),
- Type => 'message/rfc822',
- Encoding => '8bit',
- Data => $entity->as_string,
- );
- RT::Interface::Email::SendEmail( entity => $mail );
+ require RT::Interface::Email;
+ RT::Interface::Email::ForwardTransaction( $txn, %ARGS );
}
my $Title = loc('Forward message');
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/html/autohandler
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/html/autohandler (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/html/autohandler Tue Mar 27 10:57:22 2007
@@ -61,6 +61,12 @@
$m->autoflush( $m->request_comp->attr('AutoFlush') );
}
+# XXX: on a cold server (just after restart) people could have a principal object
+# in the session, as we deserialize it so we never call constructor of the principal
+# class, so the list of accessible fields is empty and we die with "Method xxx is
+# not implemented in RT::Principal"
+{ my $tmp = RT::Principal->new( $RT::SystemUser ) }
+
%ARGS = map {
# if they've passed multiple values, they'll be an array. if they've
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Action/Notify.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Action/Notify.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Action/Notify.pm Tue Mar 27 10:57:22 2007
@@ -45,12 +45,13 @@
# END BPS TAGGED BLOCK }}}
#
package RT::Action::Notify;
-require RT::Action::SendEmail;
-use Mail::Address;
+
use strict;
-use vars qw/@ISA/;
- at ISA = qw(RT::Action::SendEmail);
+use warnings;
+
+use base qw(RT::Action::SendEmail);
+use Mail::Address;
=head2 Prepare
@@ -65,8 +66,6 @@
$self->SUPER::Prepare();
}
-# {{{ sub SetRecipients
-
=head2 SetRecipients
Sets the recipients of this meesage to Owner, Requestor, AdminCc, Cc or All.
@@ -77,8 +76,9 @@
sub SetRecipients {
my $self = shift;
- my $arg = $self->Argument;
+ my $ticket = $self->TicketObj;
+ my $arg = $self->Argument;
$arg =~ s/\bAll\b/Owner,Requestor,AdminCc,Cc/;
my ( @To, @PseudoTo, @Cc, @Bcc );
@@ -86,64 +86,53 @@
if ( $arg =~ /\bOtherRecipients\b/ ) {
if ( my $attachment = $self->TransactionObj->Attachments->First ) {
- my @cc_addresses = Mail::Address->parse($attachment->GetHeader('RT-Send-Cc'));
- foreach my $addr (@cc_addresses) {
- push @Cc, $addr->address;
- }
- my @bcc_addresses = Mail::Address->parse($attachment->GetHeader('RT-Send-Bcc'));
-
- foreach my $addr (@bcc_addresses) {
- push @Bcc, $addr->address;
- }
-
+ push @Cc, map { $_->address } Mail::Address->parse(
+ $attachment->GetHeader('RT-Send-Cc')
+ );
+ push @Bcc, map { $_->address } Mail::Address->parse(
+ $attachment->GetHeader('RT-Send-Bcc')
+ );
}
}
if ( $arg =~ /\bRequestor\b/ ) {
- push ( @To, $self->TicketObj->Requestors->MemberEmailAddresses );
+ push @To, $ticket->Requestors->MemberEmailAddresses;
}
-
-
if ( $arg =~ /\bCc\b/ ) {
#If we have a To, make the Ccs, Ccs, otherwise, promote them to To
if (@To) {
- push ( @Cc, $self->TicketObj->Cc->MemberEmailAddresses );
- push ( @Cc, $self->TicketObj->QueueObj->Cc->MemberEmailAddresses );
+ push ( @Cc, $ticket->Cc->MemberEmailAddresses );
+ push ( @Cc, $ticket->QueueObj->Cc->MemberEmailAddresses );
}
else {
- push ( @Cc, $self->TicketObj->Cc->MemberEmailAddresses );
- push ( @To, $self->TicketObj->QueueObj->Cc->MemberEmailAddresses );
+ push ( @Cc, $ticket->Cc->MemberEmailAddresses );
+ push ( @To, $ticket->QueueObj->Cc->MemberEmailAddresses );
}
}
- if ( ( $arg =~ /\bOwner\b/ )
- && ( $self->TicketObj->OwnerObj->id != $RT::Nobody->id ) )
- {
-
- # If we're not sending to Ccs or requestors,
+ if ( $arg =~ /\bOwner\b/ && $ticket->OwnerObj->id != $RT::Nobody->id ) {
+ # If we're not sending to Ccs or requestors,
# then the Owner can be the To.
if (@To) {
- push ( @Bcc, $self->TicketObj->OwnerObj->EmailAddress );
+ push ( @Bcc, $ticket->OwnerObj->EmailAddress );
}
else {
- push ( @To, $self->TicketObj->OwnerObj->EmailAddress );
+ push ( @To, $ticket->OwnerObj->EmailAddress );
}
}
if ( $arg =~ /\bAdminCc\b/ ) {
- push ( @Bcc, $self->TicketObj->AdminCc->MemberEmailAddresses );
- push ( @Bcc, $self->TicketObj->QueueObj->AdminCc->MemberEmailAddresses );
+ push ( @Bcc, $ticket->AdminCc->MemberEmailAddresses );
+ push ( @Bcc, $ticket->QueueObj->AdminCc->MemberEmailAddresses );
}
- if (RT->Config->Get('UseFriendlyToLine')) {
+ if ( RT->Config->Get('UseFriendlyToLine') ) {
unless (@To) {
- push (
- @PseudoTo,
- sprintf(RT->Config->Get('FriendlyToLineFormat'), $arg, $self->TicketObj->id),
- );
+ push @PseudoTo,
+ sprintf RT->Config->Get('FriendlyToLineFormat'), $arg, $ticket->id;
}
}
@@ -167,8 +156,6 @@
}
-# }}}
-
eval "require RT::Action::Notify_Vendor";
die $@ if ($@ && $@ !~ qr{^Can't locate RT/Action/Notify_Vendor.pm});
eval "require RT::Action::Notify_Local";
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Action/SendEmail.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Action/SendEmail.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Action/SendEmail.pm Tue Mar 27 10:57:22 2007
@@ -75,22 +75,26 @@
Basically, you create another module RT::Action::YourAction which ISA
RT::Action::SendEmail.
+=head1 METHODS
+=head2 CleanSlate
-=head1 AUTHOR
-
-Jesse Vincent <jesse at bestpractical.com> and Tobias Brox <tobix at cpan.org>
+Cleans class-wide options, like L</SquelchMailTo> or L</AttachTickets>.
-=head1 SEE ALSO
-perl(1).
-=cut
+sub CleanSlate {
+ my $self = shift;
+ $self->SquelchMailTo( undef );
+ $self->AttachTickets( undef );
+}
-# {{{ Scrip methods (_Init, Commit, Prepare, IsApplicable)
+=head2 Commit
+Sends the prepared message and writes outgoing record into DB if the feature is
+activated in the config.
-# {{{ sub Commit
+=cut
sub Commit {
my $self = shift;
@@ -102,9 +106,11 @@
return (abs $ret);
}
-# }}}
+=head2 Prepare
-# {{{ sub Prepare
+Builds an outgoing email we're going to send using scrip's template.
+
+=cut
sub Prepare {
my $self = shift;
@@ -141,8 +147,8 @@
# If we don't have any 'To' header (but do have other recipients), drop in
# the pseudo-to header.
$self->SetHeader( 'To', join ( ', ', @{ $self->{'PseudoTo'} } ) )
- if ( $self->{'PseudoTo'} && ( @{ $self->{'PseudoTo'} } )
- and ( !$MIMEObj->head->get('To') ) ) and ( $MIMEObj->head->get('Cc') or $MIMEObj->head->get('Bcc'));
+ if $self->{'PseudoTo'} && @{ $self->{'PseudoTo'} } && !$MIMEObj->head->get('To')
+ && ( $MIMEObj->head->get('Cc') or $MIMEObj->head->get('Bcc') );
# We should never have to set the MIME-Version header
$self->SetHeader( 'MIME-Version', '1.0' );
@@ -158,21 +164,17 @@
$self->SetHeader( 'Content-Type', 'text/plain; charset="'. $output_enc .'"' );
# Build up a MIME::Entity that looks like the original message.
- $self->AddAttachments() if ( $MIMEObj->head->get('RT-Attach-Message') );
+ $self->AddAttachments if $MIMEObj->head->get('RT-Attach-Message');
+
+ $self->AddTickets;
return $result;
}
-# }}}
-
-# }}}
-
-
-
=head2 To
-Returns an array of Mail::Address objects containing all the To: recipients for this notification
+Returns an array of L<Mail::Address> objects containing all the To: recipients for this notification
=cut
@@ -183,7 +185,7 @@
=head2 Cc
-Returns an array of Mail::Address objects containing all the Cc: recipients for this notification
+Returns an array of L<Mail::Address> objects containing all the Cc: recipients for this notification
=cut
@@ -194,7 +196,7 @@
=head2 Bcc
-Returns an array of Mail::Address objects containing all the Bcc: recipients for this notification
+Returns an array of L<Mail::Address> objects containing all the Bcc: recipients for this notification
=cut
@@ -215,8 +217,6 @@
}
-# {{{ SendMessage
-
=head2 SendMessage MIMEObj
sends the message using RT's preferred API.
@@ -266,8 +266,6 @@
return (1);
}
-# {{{ AddAttachments
-
=head2 AddAttachments
Takes any attachments to this transaction and attaches them to the message
@@ -288,38 +286,126 @@
FIELD => 'TransactionId',
VALUE => $self->TransactionObj->Id
);
+ # Don't attach anything blank
+ $attachments->LimitNotEmpty;
$attachments->OrderBy( FIELD => 'id');
+ # We want to make sure that we don't include the attachment that's
+ # being sued as the "Content" of this message"
my $transaction_content_obj = $self->TransactionObj->ContentObj;
+ # XXX: this is legacy check of content type looks quite incorrect
+ # to me //ruz
+ if ( $transaction_content_obj && $transaction_content_obj->id
+ && $transaction_content_obj->ContentType =~ m{text/plain}i )
+ {
+ $attachments->Limit(
+ ENTRYAGGREGATOR => 'AND',
+ FIELD => 'id',
+ OPERATOR => '!=',
+ VALUE => $transaction_content_obj->id,
+ );
+ }
# attach any of this transaction's attachments
while ( my $attach = $attachments->Next ) {
+ $MIMEObj->make_multipart('mixed');
+ $self->AddAttachment( $attach );
+ }
- # Don't attach anything blank
- next unless ( $attach->ContentLength );
+}
-# We want to make sure that we don't include the attachment that's being sued as the "Content" of this message"
- next
- if ( $transaction_content_obj
- && $transaction_content_obj->Id == $attach->Id
- && $transaction_content_obj->ContentType =~ qr{text/plain}i );
- $MIMEObj->make_multipart('mixed');
- $MIMEObj->attach(
- Type => $attach->ContentType,
- Charset => $attach->OriginalEncoding,
- Data => $attach->OriginalContent,
- Filename => $self->MIMEEncodeString( $attach->Filename,
- RT->Config->Get('EmailOutputEncoding') ),
- 'RT-Attachment:' => $self->TicketObj->Id."/".$self->TransactionObj->Id."/".$attach->id,
- Encoding => '-SUGGEST'
- );
+=head2 AddAttachment $attachment
+
+Takes one attachment object of L<RT::Attachmment> class and attaches it to the message
+we're building.
+
+=cut
+
+sub AddAttachment {
+ my $self = shift;
+ my $attach = shift;
+ my $MIMEObj = shift || $self->TemplateObj->MIMEObj;
+
+ $MIMEObj->attach(
+ Type => $attach->ContentType,
+ Charset => $attach->OriginalEncoding,
+ Data => $attach->OriginalContent,
+ Filename => $self->MIMEEncodeString( $attach->Filename,
+ RT->Config->Get('EmailOutputEncoding') ),
+ 'RT-Attachment:' => $self->TicketObj->Id."/".$self->TransactionObj->Id."/".$attach->id,
+ Encoding => '-SUGGEST',
+ );
+}
+
+=head2 AttachTickets [@IDs]
+
+Returns or set list of ticket's IDs that should be attached to an outgoing message.
+
+B<Note> this method works as a class method and setup things global, so you have to
+clean list by passing undef as argument.
+
+=cut
+
+{
+ my $list = [];
+ sub AttachTickets {
+ my $self = shift;
+ $list = [ grep defined, @_ ] if @_;
+ return @$list;
}
+}
+=head2 AddTickets
+
+Attaches tickets to the current message, list of tickets' ids get from
+L</AttachTickets> method.
+
+=cut
+
+sub AddTickets {
+ my $self = shift;
+ $self->AddTicket($_) foreach $self->AttachTickets;
+ return;
}
-# }}}
+=head2 AddTicket $ID
+
+Attaches a ticket with ID to the message.
+
+Each ticket is attached as multipart entity and all its messages and attachments
+are attached as sub entities in order of creation, but only if transaction type
+is Create or Correspond.
+
+=cut
+
+sub AddTicket {
+ my $self = shift;
+ my $tid = shift;
-# {{{ RecordOutgoingMailTransaction
+ # XXX: we need a current user here, but who is current user?
+ my $attachs = RT::Attachments->new( $RT::SystemUser );
+ my $txn_alias = $attachs->TransactionAlias;
+ $attachs->Limit( ALIAS => $txn_alias, FIELD => 'Type', VALUE => 'Create' );
+ $attachs->Limit( ALIAS => $txn_alias, FIELD => 'Type', VALUE => 'Correspond' );
+ $attachs->LimitByTicket( $tid );
+ $attachs->LimitNotEmpty;
+ $attachs->OrderBy( FIELD => 'Created' );
+
+ my $ticket_mime = MIME::Entity->build(
+ Type => 'multipart/mixed',
+ Top => 0,
+ Description => "ticket #$tid",
+ );
+ while ( my $attachment = $attachs->Next ) {
+ $self->AddAttachment( $attachment, $ticket_mime );
+ }
+ if ( $ticket_mime->parts ) {
+ my $email_mime = $self->TemplateObj->MIMEObj;
+ $email_mime->make_multipart;
+ $email_mime->add_part( $ticket_mime );
+ }
+ return;
+}
=head2 RecordOutgoingMailTransaction MIMEObj
@@ -378,11 +464,6 @@
}
-# }}}
-#
-
-# {{{ sub SetRTSpecialHeaders
-
=head2 SetRTSpecialHeaders
This routine adds all the random headers that RT wants in a mail message
@@ -445,15 +526,13 @@
}
-# }}}
-
-=head2 SquelchMailTo
+=head2 SquelchMailTo [@ADDRESSES]
-Mark address to be removed from list of the recipients. Returns list of the addresses.
+Mark ADDRESSES to be removed from list of the recipients. Returns list of the addresses.
To empty list pass undefined argument.
B<Note> that this method can be called as class method and works globaly. Don't forget to
-clean this list when blocking is not required anymore.
+clean this list when blocking is not required anymore, pass undef to do this.
=cut
@@ -462,14 +541,12 @@
sub SquelchMailTo {
my $self = shift;
if ( @_ ) {
- $squelch = [ @_ ];
+ $squelch = [ grep defined, @_ ];
}
- return grep defined, @{ $squelch };
+ return @$squelch;
}
}
-# {{{ RemoveInappropriateRecipients
-
=head2 RemoveInappropriateRecipients
Remove addresses that are RT addresses or that are on this transaction's blacklist
@@ -549,9 +626,6 @@
}
}
-# }}}
-# {{{ sub SetReturnAddress
-
=head2 SetReturnAddress is_comment => BOOLEAN
Calculate and set From and Reply-To headers based on the is_comment flag.
@@ -608,10 +682,6 @@
}
-# }}}
-
-# {{{ sub SetHeader
-
=head2 SetHeader FIELD, VALUE
Set the FIELD of the current MIME object into VALUE.
@@ -630,11 +700,6 @@
return $self->TemplateObj->MIMEObj->head->get($field);
}
-# }}}
-
-
-# {{{ sub SetSubject
-
=head2 SetSubject
This routine sets the subject. it does not add the rt tag. that gets done elsewhere
@@ -671,10 +736,6 @@
}
-# }}}
-
-# {{{ sub SetSubjectToken
-
=head2 SetSubjectToken
This routine fixes the RT tag in the subject. It's unlikely that you want to overwrite this.
@@ -700,8 +761,6 @@
);
}
-# }}}
-
=head2 SetReferencesHeaders
Set References and In-Reply-To headers for this message.
@@ -773,8 +832,6 @@
}
-# }}}
-
=head2 PseudoReference
Returns a fake Message-ID: header for the ticket to allow a base level of threading
@@ -789,8 +846,6 @@
}
-# {{{ SetHeadingAsEncoding
-
=head2 SetHeaderAsEncoding($field_name, $charset_encoding)
This routine converts the field into specified charset encoding.
@@ -818,9 +873,6 @@
}
-# }}}
-
-# {{{ MIMEEncodeString
=head2 MIMEEncodeString STRING ENCODING
@@ -868,12 +920,20 @@
}
}
-# }}}
-
eval "require RT::Action::SendEmail_Vendor";
die $@ if ($@ && $@ !~ qr{^Can't locate RT/Action/SendEmail_Vendor.pm});
eval "require RT::Action::SendEmail_Local";
die $@ if ($@ && $@ !~ qr{^Can't locate RT/Action/SendEmail_Local.pm});
+=head1 AUTHOR
+
+Jesse Vincent <jesse at bestpractical.com> and Tobias Brox <tobix at cpan.org>
+
+=head1 SEE ALSO
+
+L<RT::Action::Notify>, L<RT::Action::NotifyAsComment> and L<RT::Action::Autoreply>
+
+=cut
+
1;
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Attachment_Overlay.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Attachment_Overlay.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Attachment_Overlay.pm Tue Mar 27 10:57:22 2007
@@ -46,8 +46,7 @@
=head1 SYNOPSIS
- use RT::Attachment;
-
+ use RT::Attachment;
=head1 DESCRIPTION
@@ -55,7 +54,6 @@
module which should only be instantiated through exported APIs in Ticket, Queue and other
similar objects.
-
=head1 METHODS
@@ -69,12 +67,9 @@
no warnings qw(redefine);
use RT::Transaction;
-
use MIME::Base64;
use MIME::QuotedPrint;
-
-# {{{ sub _OverlayAccessible
sub _OverlayAccessible {
{
TransactionId => { 'read'=>1, 'public'=>1, 'write' => 0 },
@@ -90,35 +85,6 @@
Created => { 'read'=>1, 'auto'=>1, },
};
}
-# }}}
-
-# {{{ sub TransactionObj
-
-=head2 TransactionObj
-
-Returns the transaction object asscoiated with this attachment.
-
-=cut
-
-sub TransactionObj {
- my $self = shift;
-
- unless ( $self->{_TransactionObj} ) {
- $self->{_TransactionObj} = RT::Transaction->new( $self->CurrentUser );
- $self->{_TransactionObj}->Load( $self->TransactionId );
- }
-
- unless ($self->{_TransactionObj}->Id) {
- $RT::Logger->crit( "Attachment ". $self->id
- ." can't find transaction ". $self->TransactionId
- ." which it is ostensibly part of. That's bad");
- }
- return $self->{_TransactionObj};
-}
-
-# }}}
-
-# {{{ sub Create
=head2 Create
@@ -221,9 +187,6 @@
}
}
-# }}}
-
-
=head2 Import
Create an attachment exactly as specified in the named parameters.
@@ -240,7 +203,59 @@
return ( $self->SUPER::Create(%args) );
}
-# {{{ sub Content
+=head2 TransactionObj
+
+Returns the transaction object asscoiated with this attachment.
+
+=cut
+
+sub TransactionObj {
+ my $self = shift;
+
+ unless ( $self->{_TransactionObj} ) {
+ $self->{_TransactionObj} = RT::Transaction->new( $self->CurrentUser );
+ $self->{_TransactionObj}->Load( $self->TransactionId );
+ }
+
+ unless ($self->{_TransactionObj}->Id) {
+ $RT::Logger->crit( "Attachment ". $self->id
+ ." can't find transaction ". $self->TransactionId
+ ." which it is ostensibly part of. That's bad");
+ }
+ return $self->{_TransactionObj};
+}
+
+=head2 ParentObj
+
+Returns a parent's L<RT::Attachment> object if this attachment
+has a parent, otherwise returns undef.
+
+=cut
+
+sub ParentObj {
+ my $self = shift;
+ return undef unless $self->Parent;
+
+ my $parent = RT::Attachment->new( $self->CurrentUser );
+ $parent->LoadById( $self->Parent );
+ return $parent;
+}
+
+=head2 Children
+
+Returns an L<RT::Attachments> object which is preloaded with
+all attachments objects with this attachment\'s Id as their
+C<Parent>.
+
+=cut
+
+sub Children {
+ my $self = shift;
+
+ my $kids = RT::Attachments->new( $self->CurrentUser );
+ $kids->ChildrenOf( $self->Id );
+ return($kids);
+}
=head2 Content
@@ -251,17 +266,13 @@
sub Content {
my $self = shift;
- return $self->_DecodeLOB( $self->ContentType,
- $self->ContentEncoding,
- $self->_Value('Content', decode_utf8 => 0),
- );
+ return $self->_DecodeLOB(
+ $self->ContentType,
+ $self->ContentEncoding,
+ $self->_Value('Content', decode_utf8 => 0),
+ );
}
-# }}}
-
-
-# {{{ sub OriginalContent
-
=head2 OriginalContent
Returns the attachment's content as octets before RT's mangling.
@@ -301,11 +312,6 @@
return $content;
}
-# }}}
-
-
-# {{{ sub OriginalEncoding
-
=head2 OriginalEncoding
Returns the attachment's original encoding.
@@ -317,49 +323,30 @@
return $self->GetHeader('X-RT-Original-Encoding');
}
-# }}}
+=head2 ContentLength
-=head2 ParentObj
-
-Returns a parent's L<RT::Attachment> object if this attachment
-has a parent, otherwise returns undef.
+Returns length of L</Content> in bytes.
=cut
-sub ParentObj {
+sub ContentLength {
my $self = shift;
- return undef unless $self->Parent;
-
- my $parent = RT::Attachment->new( $self->CurrentUser );
- $parent->LoadById( $self->Parent );
- return $parent;
-}
-
-# {{{ sub Children
-
-=head2 Children
-
-Returns an L<RT::Attachments> object which is preloaded with
-all attachments objects with this attachment\'s Id as their
-C<Parent>.
-=cut
+ return undef unless $self->TransactionObj->CurrentUserCanSee;
-sub Children {
- my $self = shift;
-
- my $kids = RT::Attachments->new( $self->CurrentUser );
- $kids->ChildrenOf( $self->Id );
- return($kids);
+ my $len = $self->GetHeader('Content-Length');
+ unless ( defined $len ) {
+ use bytes;
+ no warnings 'uninitialized';
+ $len = length($self->Content);
+ $self->SetHeader('Content-Length' => $len);
+ }
+ return $len;
}
-# }}}
-
-# {{{ UTILITIES
-
-# {{{ sub Quote
-
+=head2 Quote
+=cut
sub Quote {
my $self=shift;
@@ -411,9 +398,27 @@
return (\$body, $max);
}
-# }}}
-# {{{ sub NiceHeaders - pulls out only the most relevant headers
+=head2 ContentAsMIME
+
+Returns MIME entity built from this attachment.
+
+=cut
+
+sub ContentAsMIME {
+ my $self = shift;
+
+ my $entity = new MIME::Entity;
+ $entity->head->add( split /:/, $_, 2 )
+ foreach $self->SplitHeaders;
+
+ use MIME::Body;
+ $entity->bodyhandle(
+ MIME::Body::Scalar->new( $self->OriginalContent )
+ );
+
+ return $entity;
+}
=head2 NiceHeaders
@@ -432,9 +437,6 @@
}
return $hdrs;
}
-# }}}
-
-# {{{ sub Headers
=head2 Headers
@@ -450,12 +452,7 @@
return join("\n", $_[0]->SplitHeaders);
}
-
-# }}}
-
-# {{{ sub GetHeader
-
-=head2 GetHeader ( 'Tag')
+=head2 GetHeader $TAG
Returns the value of the header Tag as a string. This bypasses the weeding out
done in Headers() above.
@@ -475,9 +472,6 @@
# we found no header. return an empty string
return undef;
}
-# }}}
-
-# {{{ sub SetHeader
=head2 SetHeader ( 'Tag', 'Value' )
@@ -503,31 +497,6 @@
$newheader .= "$tag: $_[0]\n" if defined $tag;
$self->__Set( Field => 'Headers', Value => $newheader);
}
-# }}}
-
-# {{{ sub _Value
-
-=head2 _Value
-
-Takes the name of a table column.
-Returns its value as a string, if the user passes an ACL check
-
-=cut
-
-sub _Value {
- my $self = shift;
- my $field = shift;
-
- #if the field is public, return it.
- if ( $self->_Accessible( $field, 'public' ) ) {
- return ( $self->__Value( $field, @_ ) );
- }
-
- return undef unless $self->TransactionObj->CurrentUserCanSee;
- return $self->__Value( $field, @_ );
-}
-
-# }}}
=head2 SplitHeaders
@@ -563,24 +532,28 @@
}
-sub ContentLength {
- my $self = shift;
+=head2 _Value
- return undef unless $self->TransactionObj->CurrentUserCanSee;
+Takes the name of a table column.
+Returns its value as a string, if the user passes an ACL check
- my $len = $self->GetHeader('Content-Length');
- unless ( defined $len ) {
- use bytes;
- no warnings 'uninitialized';
- $len = length($self->Content);
- $self->SetHeader('Content-Length' => $len);
+=cut
+
+sub _Value {
+ my $self = shift;
+ my $field = shift;
+
+ #if the field is public, return it.
+ if ( $self->_Accessible( $field, 'public' ) ) {
+ return ( $self->__Value( $field, @_ ) );
}
- return $len;
-}
-# }}}
+ return undef unless $self->TransactionObj->CurrentUserCanSee;
+ return $self->__Value( $field, @_ );
+}
-# Transactions don't change. by adding this cache congif directiove, we don't lose pathalogically on long tickets.
+# Transactions don't change. by adding this cache congif directiove,
+# we don't lose pathalogically on long tickets.
sub _CacheConfig {
{
'cache_p' => 1,
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Attachments_Overlay.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Attachments_Overlay.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Attachments_Overlay.pm Tue Mar 27 10:57:22 2007
@@ -72,7 +72,6 @@
use RT::Attachment;
-# {{{ sub _Init
sub _Init {
my $self = shift;
$self->{'table'} = "Attachments";
@@ -83,10 +82,36 @@
);
return $self->SUPER::_Init( @_ );
}
-# }}}
+sub CleanSlate {
+ my $self = shift;
+ delete $self->{_sql_transaction_alias};
+ return $self->SUPER::CleanSlate( @_ );
+}
+
+
+=head2 TransactionAlias
+
+Returns alias for transactions table with applied join condition.
+Always return the same alias, so if you want to build some complex
+or recursive joining then you have to create new alias youself.
+
+=cut
+
+sub TransactionAlias {
+ my $self = shift;
+ return $self->{'_sql_transaction_alias'}
+ if $self->{'_sql_transaction_alias'};
-# {{{ sub ContentType
+ my $res = $self->NewAlias('Transactions');
+ $self->Limit(
+ ENTRYAGGREGATOR => 'AND',
+ FIELD => 'TransactionId',
+ VALUE => $res . '.id',
+ QUOTEVALUE => 0,
+ );
+ return $self->{'_sql_transaction_alias'} = $res;
+}
=head2 ContentType (VALUE => 'text/plain', ENTRYAGGREGATOR => 'OR', OPERATOR => '=' )
@@ -96,20 +121,16 @@
sub ContentType {
- my $self = shift;
- my %args = ( VALUE => 'text/plain',
- OPERATOR => '=',
- ENTRYAGGREGATOR => 'OR',
- @_);
-
- $self->Limit ( FIELD => 'ContentType',
- VALUE => $args{'VALUE'},
- OPERATOR => $args{'OPERATOR'},
- ENTRYAGGREGATOR => $args{'ENTRYAGGREGATOR'});
-}
-# }}}
+ my $self = shift;
+ my %args = (
+ VALUE => 'text/plain',
+ OPERATOR => '=',
+ ENTRYAGGREGATOR => 'OR',
+ @_
+ );
-# {{{ sub ChildrenOf
+ return $self->Limit ( %args, FIELD => 'ContentType' );
+}
=head2 ChildrenOf ID
@@ -126,7 +147,65 @@
VALUE => $attachment
);
}
-# }}}
+
+=head2 LimitNotEmpty
+
+Limit result set to attachments with not empty content.
+
+=cut
+
+sub LimitNotEmpty {
+ my $self = shift;
+ $self->Limit(
+ ENTRYAGGREGATOR => 'AND',
+ FIELD => 'Content',
+ OPERATOR => 'IS NOT',
+ VALUE => 'NULL',
+ QUOTEVALUE => 0,
+ );
+ $self->Limit(
+ ENTRYAGGREGATOR => 'AND',
+ FIELD => 'Content',
+ OPERATOR => '!=',
+ VALUE => '',
+ );
+ return;
+}
+
+=head2 LimitByTicket $ticket_id
+
+Limit result set to attachments of a ticket.
+
+=cut
+
+sub LimitByTicket {
+ my $self = shift;
+ my $tid = shift;
+
+ my $transactions = $self->TransactionAlias;
+ $self->Limit(
+ ENTRYAGGREGATOR => 'AND',
+ ALIAS => $transactions,
+ FIELD => 'ObjectType',
+ VALUE => 'RT::Ticket',
+ );
+
+ my $tickets = $self->NewAlias('Tickets');
+ $self->Limit(
+ ENTRYAGGREGATOR => 'AND',
+ ALIAS => $tickets,
+ FIELD => 'id',
+ VALUE => $transactions . '.ObjectId',
+ QUOTEVALUE => 0,
+ );
+ $self->Limit(
+ ENTRYAGGREGATOR => 'AND',
+ ALIAS => $tickets,
+ FIELD => 'EffectiveId',
+ VALUE => $tid,
+ );
+ return;
+}
# {{{ sub NewItem
sub NewItem {
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Email.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Email.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Email.pm Tue Mar 27 10:57:22 2007
@@ -386,7 +386,63 @@
return 1;
}
+sub ForwardTransaction {
+ my $txn = shift;
+ my %args = ( To => '', Cc => '', Bcc => '', @_ );
+
+ my $main_content = $txn->ContentObj;
+ my $entity = $main_content->ContentAsMIME;
+
+ if ( $main_content->Parent ) {
+ # main content is not top most entity, we shouldn't loose
+ # From/To/Cc headers that are on a top part
+ my $attachments = RT::Attachments->new( $txn->CurrentUser );
+ $attachments->Columns(qw(id Parent TransactionId Headers));
+ $attachments->Limit( FIELD => 'TransactionId', VALUE => $txn->id );
+ $attachments->Limit( FIELD => 'Parent', VALUE => 0 );
+ $attachments->Limit( FIELD => 'Parent', OPERATOR => 'IS', VALUE => 'NULL', QUOTEVALUE => 0 );
+ $attachments->OrderBy( FIELD => 'id', ORDER => 'ASC' );
+ my $tmp = $attachments->First;
+ if ( $tmp && $tmp->id ne $main_content->id ) {
+ $entity->make_multipart;
+ $entity->head->add( split /:/, $_, 2 ) foreach $tmp->SplitHeaders;
+ $entity->make_singlepart;
+ }
+ }
+ my $attachments = RT::Attachments->new( $txn->CurrentUser );
+ $attachments->Limit( FIELD => 'TransactionId', VALUE => $txn->id );
+ $attachments->Limit(
+ FIELD => 'id',
+ OPERATOR => '!=',
+ VALUE => $main_content->id,
+ );
+ $attachments->Limit(
+ FIELD => 'ContentType',
+ OPERATOR => 'NOT STARTSWITH',
+ VALUE => 'multipart/',
+ );
+ $attachments->Limit(
+ FIELD => 'Content',
+ OPERATOR => '!=',
+ VALUE => '',
+ );
+ while ( my $a = $attachments->Next ) {
+ $entity->make_multipart unless $entity->is_multipart;
+ $entity->add_part( $a->ContentAsMIME );
+ }
+
+ my $mail = MIME::Entity->build(
+ To => $args{'To'},
+ Cc => $args{'Cc'},
+ Bcc => $args{'Bcc'},
+ Subject => 'Fwd: '. ($txn->Subject || $txn->Object->Subject ),
+ Type => 'message/rfc822',
+ Encoding => '8bit',
+ Data => $entity->as_string,
+ );
+ SendEmail( entity => $mail );
+}
sub CreateUser {
my ( $Username, $Address, $Name, $ErrorsTo, $entity ) = @_;
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web.pm Tue Mar 27 10:57:22 2007
@@ -378,6 +378,16 @@
RT::Action::SendEmail->SquelchMailTo( RT::Action::SendEmail->SquelchMailTo, @temp_squelch );
}
+ if ( $ARGS{'AttachTickets'} ) {
+ require RT::Action::SendEmail;
+ RT::Action::SendEmail->AttachTickets(
+ RT::Action::SendEmail->AttachTickets,
+ ref $ARGS{'AttachTickets'}?
+ @{ $ARGS{'AttachTickets'} }
+ :( $ARGS{'AttachTickets'} )
+ );
+ }
+
foreach my $arg (keys %ARGS) {
next if $arg =~ /-(?:Magic|Category)$/;
@@ -520,7 +530,7 @@
# skip updates if the content contains only user's signature
# and we don't update other fields
- if( $args{'SkipSignatureOnly'} ) {
+ if ( $args{'SkipSignatureOnly'} ) {
my $sig = $args{'TicketObj'}->CurrentUser->UserObj->Signature || '';
$sig =~ s/^\s*|\s*$//g;
if( $args{ARGSRef}->{'UpdateContent'} =~ /^\s*(--)?\s*\Q$sig\E\s*$/ ) {
@@ -578,6 +588,16 @@
foreach values %{ $args{ARGSRef}->{'UpdateAttachments'} };
}
+ if ( $args{ARGSRef}->{'AttachTickets'} ) {
+ require RT::Action::SendEmail;
+ RT::Action::SendEmail->AttachTickets(
+ RT::Action::SendEmail->AttachTickets,
+ ref $args{ARGSRef}->{'AttachTickets'}?
+ @{ $args{ARGSRef}->{'AttachTickets'} }
+ :( $args{ARGSRef}->{'AttachTickets'} )
+ );
+ }
+
## TODO: Implement public comments
if ( $args{ARGSRef}->{'UpdateType'} =~ /^(private|public)$/ ) {
my ( $Transaction, $Description, $Object ) = $args{TicketObj}->Comment(
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web/Handler.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web/Handler.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web/Handler.pm Tue Mar 27 10:57:22 2007
@@ -190,7 +190,7 @@
# cleanup global squelching of the mails
require RT::Action::SendEmail;
- RT::Action::SendEmail->SquelchMailTo( undef );
+ RT::Action::SendEmail->CleanSlate;
}
# }}}
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web/Request.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web/Request.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Interface/Web/Request.pm Tue Mar 27 10:57:22 2007
@@ -17,9 +17,7 @@
$class->alter_superclass( $new_class );
$class->valid_params( %{ $new_class->valid_params } );
- my $self = $class->SUPER::new(@_);
- return if $self->is_subrequest;
- return $self;
+ return $class->SUPER::new(@_);
}
=head2 callback
Modified: rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Transaction_Overlay.pm
==============================================================================
--- rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Transaction_Overlay.pm (original)
+++ rt/branches/3.7-EXPERIMENTAL-TUNIS/lib/RT/Transaction_Overlay.pm Tue Mar 27 10:57:22 2007
@@ -358,18 +358,7 @@
elsif ( $Attachment->ContentType =~ '^multipart/' ) {
my $plain_parts = $Attachment->Children;
$plain_parts->ContentType( VALUE => 'text/plain' );
- $plain_parts->Limit(
- FIELD => 'Content',
- OPERATOR => 'IS NOT',
- VALUE => 'NULL',
- QUOTEVALUE => 0,
- );
- $plain_parts->Limit(
- ENTRYAGGREGATOR => 'AND',
- FIELD => 'Content',
- OPERATOR => '!=',
- VALUE => '',
- );
+ $plain_parts->LimitNotEmpty;
# If we actully found a part, return its content
if ( my $first = $plain_parts->First ) {
More information about the Rt-commit
mailing list