4 This script is for fixing CDRs that were supposed to receive Taqua
5 accountcode/caller ID rewrites but didn't. It will reprocess records that
6 were already rewritten, so use with caution. Options:
8 -s DATE: find calls on or after DATE (required)
9 -e DATE: find calls on or before DATE (optional, defaults to right now)
10 -v: show records as they're updated
15 use FS::Record qw(qsearch qsearchs dbh);
22 die $usage unless $opt{start};
27 my $extra_sql = 'WHERE lastapp IS NOT NULL '.
28 ' AND cdrtypenum = 1'.
29 ' AND calldate >= to_timestamp('.$opt{start}.')';
31 $extra_sql .= ' AND calldate < to_timestamp('.$opt{end}.')';
33 my $cursor = FS::Cursor->new({
36 extra_sql => $extra_sql,
39 $FS::UID::AutoCommit = 0;
41 while (my $cdr = $cursor->fetch) {
42 # copy-paste from cdrrewrited, except:
43 # - move all conditions for this rewrite into the SQL
44 # - don't check for config option to enable rewriting
45 # - don't retry, don't remember not-found acctids
49 #find the matching CDR
50 my %search = ( 'sessionnum' => $cdr->sessionnum );
51 if ( $cdr->lastapp eq 'acctcode' ) {
52 $search{'src'} = $cdr->subscriber;
53 } elsif ( $cdr->lastapp eq 'CallerId' ) {
54 $search{'dst'} = $cdr->subscriber;
57 my $desc = '#'.$cdr->acctid . ': sessionnum ' . $cdr->sessionnum . ', '.
58 "subscriber ".$cdr->subscriber;
61 my $primary = qsearchs('cdr', \%search);
65 my $cantfind = "can't find primary CDR with session ". $cdr->sessionnum .
68 $cantfind .= 'src '.$search{'src'};
70 $cantfind .= 'dst '.$search{'dst'};
72 warn "ERROR: $cantfind\n";
78 if ( $cdr->lastapp eq 'acctcode' ) {
79 # lastdata contains the dialed account code
80 $primary->accountcode( $cdr->lastdata );
81 push @status, 'taqua-accountcode';
82 warn '#'.$primary->acctid . ': accountcode = '.$cdr->lastdata . "\n"
84 } elsif ( $cdr->lastapp eq 'CallerId' ) {
85 # lastdata contains "allowed" or "restricted"
86 # or case variants thereof
87 if ( lc($cdr->lastdata) eq 'restricted' ) {
88 $primary->clid( 'PRIVATE' );
90 push @status, 'taqua-callerid';
91 warn '#'.$primary->acctid . ': clid = '.$cdr->lastdata . "\n"
94 warn "unknown Taqua service name: ".$cdr->lastapp."\n";
96 #$primary->freesiderewritestatus( 'taqua-accountcode-primary' );
97 my $error = $primary->replace if $primary->modified;
99 warn "WARNING: error rewriting primary CDR: $error\n";
104 if ( $primary->freesidestatus eq 'done' and
105 $cdr->lastapp eq 'acctcode' and
106 $primary->rated_price > 0 ) {
107 # then have to update the billing detail also
109 if ( $primary->detailnum ) {
110 # has been on 3.x since January 2016...
111 $detail = qsearchs('cust_bill_pkg_detail', {
112 'detailnum' => $primary->detailnum
115 # otherwise, try our best: find a detail with the right price,
116 # source number, and start and end dates
117 $detail = qsearchs('cust_bill_pkg_detail', {
118 'amount' => $primary->rated_price,
119 'classnum' => $primary->rated_classnum,
120 'duration' => $primary->rated_seconds,
121 'startdate' => $primary->startdate,
123 'phonenum' => $primary->src, # not perfect
127 warn "detail #".$detail->detailnum."\n" if $DEBUG;
128 $detail->set('accountcode', $primary->accountcode);
129 $error = $detail->replace;
131 warn "WARNING: error rewriting invoice detail: $error\n";
137 warn "ERROR: can't find invoice detail for cdr#".$primary->acctid."\n";
142 } # if this is an acctcode record and the primary was billed
144 $cdr->status('done'); #so it doesn't try to rate
148 $cdr->freesiderewritestatus(
149 scalar(@status) ? join('/', @status) : 'skipped'
152 my $error = $cdr->replace;
154 warn "WARNING: error rewriting CDR: $error\n";
165 Primary record not found: $notfound