#!/usr/bin/perl -w # # This script outputs all reminders that are due within the next e.g. two # days and mails the result to the corresponding owners. # package RT::Importer; #use lib ("/etc/request-tracker3.6", "/usr/lib/rt/", # "/usr/local/share/request-tracker3.6/lib"); use lib ("/etc/request-tracker3.6", "/usr/share/request-tracker3.6/lib", "/usr/local/share/request-tracker3.6/lib"); use RT::Interface::CLI qw(CleanEnv GetCurrentUser); use RT::Ticket; use RT::User; use RT::Attachment; use RT::Transaction; use MIME::Base64; use Data::Dumper; use XML::Simple; use strict; use Getopt::Std; my %opts; getopts('c:r:f:h', \%opts); my $cf=$opts{'c'}; my $rtname=$opts{'r'}; my $file=$opts{'f'}; unless (!$opts{'h'} && $cf && $rtname && $file) { print "rt-ticket-importer -f -r -c \n"; exit; } # clean out all the nasties from the environment.. CleanEnv(); # load the config file.. RT::LoadConfig(); # connect to the database and get RT::SystemUser and RT::Nobody loaded.. RT::Init(); # reset the RT die signal handler, we don't need the extra info.. $SIG{__DIE__} = ""; # drop setgid permissions, which is version 3.0 specific eval { RT::DropSetGIDPermissions() }; my $data = XMLin($file); print STDERR "File Loaded\n"; my $attachments = $data->{'Attachments'}; my $links = $data->{'Links'}; my $transactions = $data->{'Transactions'}; my $tickets = $data->{'Tickets'}; my %USERS; my %TICKETS; my %TRANSACTIONS; my %LINKS; my %ATTACHMENTS; sub ConvertUser { my $user = shift; return $RT::Nobody->Id unless ($user) ; return $USERS{$user} if ($USERS{$user}); my $userObj = new RT::User($RT::SystemUser); $userObj->LoadOrCreateByEmail($user); $USERS{$user} = $userObj->Id; return $USERS{$user}; } sub ConvertTicket { my $id = shift; return $TICKETS{$id} if ($TICKETS{$id}); return undef unless ($id); my $ticket = $tickets->{$id}; return undef unless (defined($ticket)); foreach my $key (keys %$ticket) { $ticket->{$key} = undef if (ref($ticket->{$key})); } my $ticketObj = new RT::Ticket($RT::SystemUser); $ticket->{'Owner'} = ConvertUser($ticket->{'Owner'}); $ticket->{'Creator'} = ConvertUser($ticket->{'Creator'}); $ticket->{'LastUpdatedBy'} = ConvertUser($ticket->{'LastUpdatedBy'}); if ($ticket->{'Requestor'}) { my $watchers = $ticket->{'Requestor'}; my @trq = split(/, /, $watchers); $ticket->{'Requestor'} = \@trq; } if ($ticket->{'Cc'}) { my $watchers = $ticket->{'Cc'}; my @tcc = split(/, /, $watchers); $ticket->{'Cc'} = \@tcc; } if ($ticket->{'AdminCc'}) { my $watchers = $ticket->{'AdminCc'}; my @tacc = split(/, /, $watchers); $ticket->{'AdminCc'} = \@tacc; } my $eid = $ticket->{'EffectiveId'}; $ticket->{'EffectiveId'} = '0'; my ($newid, $msg) = $ticketObj->Import( %$ticket ); unless ($newid) { print STDERR "Failed to create Ticket $id!!!\n"; return undef; } print "Created Ticket # $id : as # $newid\n"; $| = 1; $ticketObj->SetEffectiveId(ConvertTicket($eid)) if ($eid != $id); $ticketObj->{'_AccessibleCache'}{Created} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $ticketObj->{'_AccessibleCache'}{Creator} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $ticketObj->{'_AccessibleCache'}{LastUpdated} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $ticketObj->{'_AccessibleCache'}{LastUpdatedBy} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $ticketObj->SetCreated($ticket->{'Created'}); $ticketObj->SetCreator($ticket->{'Creator'}); $ticketObj->SetLastUpdated($ticket->{'LastUpdated'}); $ticketObj->SetLastUpdatedBy($ticket->{'LastUpdatedBy'}); $ticketObj->AddCustomFieldValue(Field => $cf, Value => "[$rtname #$id]" ); $TICKETS{$id} = $newid; return $newid; } sub ConvertTransaction { my $id = shift; return $TRANSACTIONS{$id} if ($TRANSACTIONS{$id}); my $transaction = $transactions->{$id}; my $transactionObj = new RT::Transaction($RT::SystemUser); foreach my $key (keys %$transaction) { $transaction->{$key} = undef if (ref($transaction->{$key})); } # We're cheating and only importing Ticket Transactions $transaction->{'ObjectId'} = ConvertTicket($transaction->{'ObjectId'}); $transaction->{'Creator'} = ConvertUser($transaction->{'Creator'}); return undef unless (defined($transaction->{'ObjectId'})); if ( ($transaction->{'Type'} eq 'Owner') || ($transaction->{'Type'} eq 'Requestor') || ($transaction->{'Type'} eq 'Cc') || ($transaction->{'Type'} eq 'AdminCc') ) { $transaction->{'OldValue'} = ConvertUser($transaction->{'OldValue'}); $transaction->{'NewValue'} = ConvertUser($transaction->{'NewValue'}); } if ( ($transaction->{'Type'} eq 'DependsOn') || ($transaction->{'Type'} eq 'DependedOnBy') || ($transaction->{'Type'} eq 'RefersTo') || ($transaction->{'Type'} eq 'ReferredToBy') || ($transaction->{'Type'} eq 'MemberOf') || ($transaction->{'Type'} eq 'MergedInto') || ($transaction->{'Type'} eq 'HasMember') ) { $transaction->{'OldValue'} =ConvertTicket($transaction->{'OldValue'}); $transaction->{'NewValue'} =ConvertTicket($transaction->{'NewValue'}); } $transaction->{'ActivateScrips'} = 0; my ($newid, $msg) = $transactionObj->Create( %$transaction ); unless ($newid) { print STDERR "Failed to create Transaction $id ($msg)!!!\n"; return undef; } print "Created Transaction # $id : as # $newid\n"; $| = 1; $transactionObj->{'_AccessibleCache'}{Created} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $transactionObj->{'_AccessibleCache'}{Creator} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $transactionObj->SetCreated($transaction->{'Created'}); $transactionObj->SetCreator($transaction->{'Creator'}); $TRANSACTIONS{$id} = $newid; return $newid; } sub ConvertAttachment { my $id = shift; return $ATTACHMENTS{$id} if ($ATTACHMENTS{$id}); my $attachment = $attachments->{$id}; foreach my $key (keys %$attachment) { $attachment->{$key} = undef if (ref($attachment->{$key})); } if ($attachment->{'Parent'}) { my $parent = $attachment->{'Parent'} ; $attachment->{'Parent'} = ConvertAttachment($parent); } my $attachObj = new RT::Attachment($RT::SystemUser); $attachment->{'Creator'} = ConvertUser($attachment->{'Creator'}); $attachment->{'TransactionId'} = ConvertTransaction($attachment->{'TransactionId'}); return undef unless (defined ($attachment->{'TransactionId'})); Encode::_utf8_off($attachment->{'Content'}); $attachment->{'Content'} = decode_base64($attachment->{'Content'}); my ($newid, $msg) = $attachObj->Import( %$attachment ); unless ($newid) { print STDERR "Failed to create Attachment $id ($msg)!!!\n"; return undef; } print "Created Attachment # $id : as # $newid\n"; $| = 1; $attachObj->{'_AccessibleCache'}{Created} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $attachObj->{'_AccessibleCache'}{Creator} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $attachObj->SetCreated($attachment->{'Created'}); $attachObj->SetCreator($attachment->{'Creator'}); $ATTACHMENTS{$id} = $newid; return $newid; } sub ConvertLink { my $id = shift; return $LINKS{$id} if ($LINKS{$id}); my $link = $links->{$id}; my $linkObj = new RT::Link($RT::SystemUser); my $base = $link->{'Base'}; $base =~ /([0-9]*)$/; $base = $1; my $target = $link->{'Target'}; $target =~ /([0-9]*)$/; $target = $1; my $newid = $linkObj->Create( Base => ConvertTicket($base), Target => ConvertTicket($target), Type => $link->{'Type'} ); if ($newid == 0) { print STDERR "Failed to create Link $id!!!\n"; return undef } print "Created Link # $id : as # $newid\n"; $| = 1; $LINKS{$id} = $newid; $linkObj->{'_AccessibleCache'}{Created} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $linkObj->{'_AccessibleCache'}{Creator} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $linkObj->{'_AccessibleCache'}{LastUpdated} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $linkObj->{'_AccessibleCache'}{LastUpdatedBy} = { 'read' => 1, 'write' => 1, 'auto' => 0 }; $linkObj->SetCreated($link->{'Created'}); $linkObj->SetCreator(ConvertUser($link->{'Creator'})); $linkObj->SetLastUpdated($link->{'LastUpdated'}); $linkObj->SetLastUpdatedBy($link->{'LastUpdatedBy'}); return $newid; } foreach (sort {$a <=> $b} keys %$tickets) { ConvertTicket($_); } foreach (sort {$a <=> $b} keys %$transactions ) { next unless ($transactions->{$_}->{'ObjectType'} eq 'RT::Ticket'); ConvertTransaction($_); } foreach (sort {$a <=> $b} keys %$attachments ) { ConvertAttachment($_); } foreach (sort {$a <=> $b} keys %$links ) { ConvertLink($_); }