Perl - 与 base64 之间的编码

Perl - Encoding to and from base64

我已经编写了以下脚本来将文件与 base64 相互转换。

# Setup default mode
my $mode = '';
my $encoding = 'base64';
my $file = '';


GetOptions(
'mode=s'        => $mode,  # mode = Encode / decode
'help!'         => $help,      # help message
'encoding=s'    => $encoding,
'file=s'        => $file
) or die "Incorrect usage!\n";

if( $help ) {
print "Common on, it's really not that hard.\n";
} else {
print "# Script parameters provided : \n";
print "# Mode set to $mode.\n";
print "# Encoding is set to $encoding\n";
print "# Input File set to $file \n";
}


open(FILE, "$file") or die "$!";
open FILEOT, ">$file.out" or die "$!";  
binmode FILEOT;
binmode STDOUT; 

switch ($mode) {

case "encode" { 

        print "# Encoding file $file to $encoding \n";
        print "# Processing .... \n\n";

        while (read(FILE, $buf, 60*57)) {
            $encoded = encode_base64($buf);
            print $encoded;
            print FILEOT $encoded;
        }
}

case "decode" {
        print "# Decoding file $file from $encoding \n";
        print "# Processing .... \n\n";

        while ( read(FILE, $buf, 60*57 ) {
            $decoded = decode_base64($buf);
            print $decoded;
            print FILEOT $decoded;
          }
       }

编码部分按预期工作。解码部分不给出任何输出。我给了它一个类似的输入文件:

 My name is John
 I eat pineapples

它没有输出。我认为在解码之前已经使用此脚本编码的文件的情况下,可能不需要缓冲读取。我使用上面的测试生成了 base64 编码版本,但反过来什么也没给出。谁能帮帮我?

块式 encode/decode 将不起作用。编码将产生比必要更大的输出,因为您每 60 * 57 = 3420 字节重新启动一次,但对于解码,3420 字节将不是一个完整的 Base64 块。看看你的结果,你可能会看到以一些 = 个字符结尾的未完全填充的行。

这里有一个块大小为 10 的简短示例用于演示:

use MIME::Base64 qw(encode_base64);

my $in = "abcdefghijklmnopqrstuvwxyz";
while (my $block = substr($in,0,10,"")) {
    print encode_base64($block);
}

YWJjZGVmZ2hpag==
a2xtbm9wcXJzdA==
dXZ3eHl6

尝试以 10 个字符为单位对其进行解码将尝试对这些字符串进行解码:

YWJjZGVmZ2
hpag==\na2x
tbm9wcXJzd
A==\ndXZ3eH
l6\n

第一行正确翻译成 abcdefg,但第二行被解码为垃圾。

有一个名为 base64 的命令行工具,其功能完全相同:对 Base64 文件进行编码和解码。您应该删除该块处理,对文件进行编码并尝试使用命令行工具对其进行解码(假设它做对了)。如果这有效,则您的编码也有效,否则您的编码可能不起作用。让它工作并继续解码部分。

您应该阅读有关 PerlIO 层的内容。您也对 PerlIO::via::Base64 模块

感兴趣
 use PerlIO::via::Base64 eol => "\n";

 open( my $in,'<:via(Base64)','file.mime' )
  or die "Can't open file.mime for reading: $!\n";

 open( my $out,'>:via(Base64)','file.mime' )
  or die "Can't open file.mime for writing: $!\n";