+=item payby
+
+I<CARD> (credit card - automatic), I<DCRD> (credit card - on-demand), I<CHEK> (electronic check - automatic), I<DCHK> (electronic check - on-demand), I<LECB> (Phone bill billing), I<BILL> (billing), I<COMP> (free), or I<PREPAY> (special billing type: applies a credit - see L<FS::prepay_credit> and sets billing type to I<BILL>)
+
+=item payinfo
+
+Card Number, P.O., comp issuer (4-8 lowercase alphanumerics; think username) or prepayment identifier (see L<FS::prepay_credit>)
+
+=cut
+
+sub payinfo {
+ my($self,$payinfo) = @_;
+ if ( defined($payinfo) ) {
+ $self->paymask($payinfo);
+ $self->setfield('payinfo', $payinfo); # This is okay since we are the 'setter'
+ } else {
+ $payinfo = $self->getfield('payinfo'); # This is okay since we are the 'getter'
+ return $payinfo;
+ }
+}
+
+
+=item paycvv
+
+Card Verification Value, "CVV2" (also known as CVC2 or CID), the 3 or 4 digit number on the back (or front, for American Express) of the credit card
+
+=cut
+
+=item paymask - Masked payment type
+
+=over 4
+
+=item Credit Cards
+
+Mask all but the last four characters.
+
+=item Checks
+
+Mask all but last 2 of account number and bank routing number.
+
+=item Others
+
+Do nothing, return the unmasked string.
+
+=back
+
+=cut
+
+sub paymask {
+ my($self,$value)=@_;
+
+ # If it doesn't exist then generate it
+ my $paymask=$self->getfield('paymask');
+ if (!defined($value) && (!defined($paymask) || $paymask eq '')) {
+ $value = $self->payinfo;
+ }
+
+ if ( defined($value) && !$self->is_encrypted($value)) {
+ my $payinfo = $value;
+ my $payby = $self->payby;
+ if ($payby eq 'CARD' || $payby eq 'DCARD') { # Credit Cards (Show last four)
+ $paymask = 'x'x(length($payinfo)-4). substr($payinfo,(length($payinfo)-4));
+ } elsif ($payby eq 'CHEK' ||
+ $payby eq 'DCHK' ) { # Checks (Show last 2 @ bank)
+ my( $account, $aba ) = split('@', $payinfo );
+ $paymask = 'x'x(length($account)-2). substr($account,(length($account)-2))."@".$aba;
+ } else { # Tie up loose ends
+ $paymask = $payinfo;
+ }
+ $self->setfield('paymask', $paymask); # This is okay since we are the 'setter'
+ } elsif (defined($value) && $self->is_encrypted($value)) {
+ $paymask = 'N/A';
+ }
+ return $paymask;
+}
+