0

Gmail API's developer guide我如何正確地base64編碼Gmail API的MIMEText?

下面的代碼示例演示創建MIME消息,編碼一個base64url串,並將其分配給該消息的資源的原始字段:

def create_message(sender, to, subject, message_text): 
    """Create a message for an email. 

    Args: 
    sender: Email address of the sender. 
    to: Email address of the receiver. 
    subject: The subject of the email message. 
    message_text: The text of the email message. 

    Returns: 
    An object containing a base64url encoded email object. 
    """ 
    message = MIMEText(message_text) 
    message['to'] = to 
    message['from'] = sender 
    message['subject'] = subject 
    return {'raw': base64.urlsafe_b64encode(message.as_string())} 

但如果我這樣做

from email.MIMEText import MIMEText 
import base64 
message = MIMEText('This is a test') 
message['to'] = '[email protected]' 
message['from'] = '[email protected]' 
message['subject'] = 'Test' 
body = {'raw': base64.urlsafe_b64encode(message.as_string())} 

我得到TypeError: a bytes-like object is required, not 'str' 相反,如果我做的:

body = {'raw': base64.urlsafe_b64encode(message.as_bytes())} 
message = (service.users().messages().send(userId='me', body=body) 
       .execute()) 

我得到一些二進制不是JSON序列化下面的回溯:

~/env/lib/python3.5/site-packages/googleapiclient/discovery.py in method(self, **kwargs) 
    792  headers = {} 
    793  headers, params, query, body = model.request(headers, 
--> 794   actual_path_params, actual_query_params, body_value) 
    795 
    796  expanded_url = uritemplate.expand(pathUrl, params) 

~/env/lib/python3.5/site-packages/googleapiclient/model.py in request(self, headers, path_params, query_params, body_value) 
    149  if body_value is not None: 
    150  headers['content-type'] = self.content_type 
--> 151  body_value = self.serialize(body_value) 
    152  self._log_request(headers, path_params, query, body_value) 
    153  return (headers, path_params, query, body_value) 

~/env/lib/python3.5/site-packages/googleapiclient/model.py in serialize(self, body_value) 
    258   self._data_wrapper): 
    259  body_value = {'data': body_value} 
--> 260  return json.dumps(body_value) 
    261 
    262 def deserialize(self, content): 

/usr/lib/python3.5/json/__init__.py in dumps(obj, skipkeys, ensure_ascii, check_circular, allow_nan, cls, indent, separators, default, sort_keys, **kw) 
    228   cls is None and indent is None and separators is None and 
    229   default is None and not sort_keys and not kw): 
--> 230   return _default_encoder.encode(obj) 
    231  if cls is None: 
    232   cls = JSONEncoder 

/usr/lib/python3.5/json/encoder.py in encode(self, o) 
    196   # exceptions aren't as detailed. The list call should be roughly 
    197   # equivalent to the PySequence_Fast that ''.join() would do. 
--> 198   chunks = self.iterencode(o, _one_shot=True) 
    199   if not isinstance(chunks, (list, tuple)): 
    200    chunks = list(chunks) 

/usr/lib/python3.5/json/encoder.py in iterencode(self, o, _one_shot) 
    254     self.key_separator, self.item_separator, self.sort_keys, 
    255     self.skipkeys, _one_shot) 
--> 256   return _iterencode(o, 0) 
    257 
    258 def _make_iterencode(markers, _default, _encoder, _indent, _floatstr, 

/usr/lib/python3.5/json/encoder.py in default(self, o) 
    177 
    178   """ 
--> 179   raise TypeError(repr(o) + " is not JSON serializable") 
    180 
    181  def encode(self, o): 

TypeError: b'Q29udGVudC1UeXBlOiB0ZXh0L3BsYWluOyBjaGFyc2V0PSJ1cy1hc2NpaSIKTUlNRS1WZXJzaW9uOiAxLjAKQ29udGVudC1UcmFuc2Zlci1FbmNvZGluZzogN2JpdApGcm9tOiBUZXN0IFB5dGhvbgpUbzogcmFwaGFlbC5hLmR1bWFzQGdtYWlsLmNvbQpTdWJqZWN0OiBQbGVhc2Ugc3RheSBjYWxtLCB0aGlzIGlzIGEgdGVzdAoKVGhpcyBpcyBhIHRlc3Q=' is not JSON serializable 

回答

1

嘗試:

b64_bytes = base64.urlsafe_b64encode(message.as_bytes()) 
b64_string = b64_bytes.decode() 
body = {'raw': b64_string} 

base64.urlsafe_b64encode返回bytes對象(見docs ),所以你需要在將它輸出爲JSON之前將輸出轉換爲字符串。

+0

對我來說,答案本質上是這樣做的:直接對encode(message.as_bytes())。decode()進行編碼,但是在這裏我們是,並且它工作正常。 – raphael

相關問題