2016-07-16 57 views
2

我是python的新手,我试图用vobject 0.9.2 python包解析VCARD 2.1文件。
我试图解析这个vCard文件:使用python VObject包解析VCARD文件时出错

BEGIN:VCARD 
VERSION:2.1 
N;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:I;AM;DUMMY;; 
TEL;CELL:123456789 
END:VCARD 

这些都是我用Python命令:

import vobject 
f=open('sample.vcf','r') 
vcf=vobject.readOne(f) 

然后我收到以下错误:

Traceback (most recent call last): 
     File "<stdin>", line 1, in <module> 
     File "C:\Program Files\Anaconda3\lib\site-packages\vobject\base.py", line 1129, in readOne 
     allowQP)) 
     File "C:\Program Files\Anaconda3\lib\site-packages\vobject\base.py", line 1073, in readComponents 
     vline = textLineToContentLine(line, n) 
     File "C:\Program Files\Anaconda3\lib\site-packages\vobject\base.py", line 912, in textLineToContentLine 
     'lineNumber' : n}) 
     File "C:\Program Files\Anaconda3\lib\site-packages\vobject\base.py", line 336, in __init__ 
     self.value = self.value.decode('quoted-printable') 
     AttributeError: 'str' object has no attribute 'decode' 

链接错误日志https://paste.fedoraproject.org/391670/46866724/

Py thon显示str对象没有任何属性decode

这里是VOBJECT包源代码的代码段错误发生:

if 'ENCODING' in self.params: 
     if 'QUOTED-PRINTABLE' in self.params['ENCODING']: 
      qp = True 
      self.params['ENCODING'].remove('QUOTED-PRINTABLE') 
      if 0==len(self.params['ENCODING']): 
       del self.params['ENCODING'] 
    if 'QUOTED-PRINTABLE' in self.singletonparams: 
     qp = True 
     self.singletonparams.remove('QUOTED-PRINTABLE') 
    if qp: 
     self.value = self.value.decode('quoted-printable') 

通过计算器阅读类似的问题,我的理解是VOBJECT包试图解码已经解码string.So我甚至试过将vcf文件转换为二进制字符串并将其作为vobject.readOne的输入。

binstr = f.read('sample.vcf','r').encode('utf-8') 
x=vobject.readOne(binstr) 

但它不起作用。

我该怎么做才能成功解析VCARD文件?
请人可以帮我...

编辑: 现在我明白了,这个错误是由于使用Python 3.我可以做任何一点的黑客攻击,克服这种错误的vobject不兼容?

+0

你使用Python 3吧? –

+0

@MartijnPieters是 – anapneo

+2

我认为你发现了一个错误'ENCODING = QUOTED-PRINTABLE'是如何处理的;该项目在Python 3上读取* Unicode字符串*,但期望'decode'方法能够正常工作。我认为https://github.com/eventable/vobject/issues/20是同样的问题。 –

回答

1

您的问题有三个问题。

第一:在野外N,你就错过了“:”

二:VOBJECT似乎需要FN eventhough你的电子名片的版本是2.1,其stricly来说并不需要它。

三:代替readOne的我建议你使用vobject.readComponents

在任何情况下,如果你不想将使用readComponents,代码:

f=open(vcardfile,'r') 
    vcf=vobject.readOne(f) 

适用于以下文件:

BEGIN:VCARD 
    VERSION:2.1 
    N:;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:I;AM;DUMMY;; 
    FN:;;;; 
    TEL;TYPE=CELL:123456789 
    END:VCARD 

下面的代码也可与上面的文件:

#!/usr/bin/env python3 

    import vobject 

    vcardfile='/Users/foo/bar/abovefile.vcf' 

    with open(vcardfile) as source_file: 
     vcardlist = vobject.readComponents(source_file) 
     for vcard in vcardlist: 
      print vcard 
      print vcard.serialize() 
      print vcard.prettyPrint 

,你应该得到的输出:

<VCARD| [<VERSION{}2.1>, <FN{};;;;>, <N{}AM ENCODING=QUOTED-PRINTABLE CHARSET=UTF-8:I DUMMY>, <TEL{'TYPE': ['CELL']}123456789>]> 

    BEGIN:VCARD 
    VERSION:2.1 
    FN:\;\;\;\; 
    N:;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:I;AM;DUMMY 
    TEL;TYPE=CELL:123456789 
    END:VCARD 

    VCARD 
     VERSION: 2.1 
     TEL: 123456789 
     params for TEL: 
     TYPE ['CELL'] 
     FN: ;;;; 
     N: AM ENCODING=QUOTED-PRINTABLE CHARSET=UTF-8:I DUMMY