1 package FS::UI::bytecount;
4 use vars qw($DEBUG $me @ISA @EXPORT_OK);
7 use Number::Format 1.50;
11 @EXPORT_OK = qw( bytecount_unexact parse_bytecount display_bytecount );
14 $me = '[FS::UID::bytecount]';
18 FS::UI::bytecount - Subroutines for parsing and displaying byte counters
22 use FS::UI::bytecount;
28 =item bytecount_unexact COUNT
30 Returns a two decimal place value for COUNT followed by bytes, Kbytes, Mbytes,
31 or GBytes as appropriate.
35 sub bytecount_unexact {
39 return(sprintf("%.2f Kbytes", $bc/1024))
41 return(sprintf("%.2f Mbytes", $bc/1048576))
42 if ($bc < 1073741824);
43 return(sprintf("%.2f Gbytes", $bc/1073741824));
46 =item parse_bytecount AMOUNT
48 Accepts a number (digits and a decimal point) possibly followed by k, m, g, or
49 t (and an optional 'b') in either case. Returns a pure number representing
50 the input or the input itself if unparsable. Discards commas as noise.
56 return $bc if (($bc =~ tr/.//) > 1);
57 $bc =~ /^\s*([,\d.]*)\s*([kKmMgGtT]?)[bB]?\s*$/ or return $bc;
60 return $bc unless length $base;
61 my $exponent = index ' kmgt', lc($2);
62 return $bc if ($exponent < 0 && $2);
63 $exponent = 0 if ($exponent < 0);
64 return int($base * 1024 ** $exponent); #bytecounts are integer values
67 =item display_bytecount AMOUNT
69 Converts a pure number to a value followed possibly followed by k, m, g, or
74 sub display_bytecount {
76 return $bc unless ($bc =~ /^(\d+)$/);
77 my $conf = new FS::Conf;
78 my $f = new Number::Format;
79 my $precision = ( $conf->exists('datavolume-significantdigits') &&
80 $conf->config('datavolume-significantdigits') =~ /^\s*\d+\s*$/ )
81 ? $conf->config('datavolume-significantdigits')
83 my $unit = $conf->exists('datavolume-forcemegabytes') ? 'M' : 'A';
85 return $f->format_bytes($bc, precision => $precision, unit => $unit);