我正在使用以下命令处理大量要转换为 IDN 的域列表:
cat list | idn > clean
列表格式示例:
президент.рф
mañana.com
bücher.com
café.fr
cliché.com
hualañe.cl
köln-düsseldorfer-rhein-main.de
mūsųlaikas.lt
sendesık.com
sushicorner-würzburg.de
domain.com
# almost 1 M lines
但我收到以下消息
idn: idna_to_ascii_4z (big list): Output would be too big or too small
然后我必须确保我的列表不超过允许的限制(太大或太小)
我找到了这个:
RFC 1035FQDN 的长度限制为 255 个字符,每个标签(由主机名中的点分隔的节点)限制为 63 个字符
和
1 个字符的限制按钮(示例:t.co)
问题: 如何通过命令行从我的列表中删除主机名大于 63 个字符且小于 1 个字符的域? (bash运行idn没有错误)
行动: 我已经尝试过以下操作(尽管我希望这一切都在一个命令中)(部分来源):
sed -n '/.\{63\}/p' list > out
grep -vi -f <(sed 's:^\(.*\)$:\\\1\$:' out) list | sort -u > out2
但是当我运行 idn 命令时,会出现相同的消息 idn
cat out2 | idn
idn: idna_to_ascii_4z (big list): Output would be too big or too small
我很感激任何帮助
PD:也许问题与 IDN 和列表的大小(非常大)有关。我不知道。我不知道 IDN 是否对行数有任何限制 |域 |要处理的主机名。帮助文件没有提供关于这一点的太多信息
更新: 问题解决了,但正确答案被作者@cas删除了,显然是由于垃圾邮件事件。投票结束
答案1
我不认为idn
有任何开关可以跳过不可接受的字符串而不是错误退出,因此剩下的唯一选择是在预期的错误:
idn_skip(){
while ! error=$(idn 2>&1 >&3); do
case $error in *'Punycode failed'*|*'Output would be too large'*) ;; # restart
*) break;;
esac
done 3>&1
}
idn_skip < domain_list
这是丑陋和愚蠢的,并且在从不可查找的文件中读取域列表时不起作用(可以通过将其运行为 bash 风格来修复stdbuf -i1 idn
,但这只会使它变得更加荒谬)。
idn
我的建议是使用Net::LibIDN
perl 包(apt-get install libnet-libidn-perl
在 debian 上)并用 perl 编写整个内容,而不是试图克服的限制。