Search code examples
javaemailgmailgmail-api

How to insert a message with an attachment using Gmail API (Java)


I use Gmail API via Java client library and I've found out that Gmail API insert(java.lang.String userId, com.google.api.services.gmail.model.Message content) method inserts only files smaller than 5Mb.

I tried to use Insert insert(java.lang.String userId, com.google.api.services.gmail.model.Message content, com.google.api.client.http.AbstractInputStreamContent mediaContent) to insert a message with a file (size 10MB).

MimeMessage email = GmailAPI.createEmail("[email protected]", "[email protected]", "subject", "message body");
FileContent content = new FileContent("message/rfc822", new File("C:\\Users\\user\\someFile"));
Message message = createMessageWithEmail(email);
message = service.users().messages().insert(userId, message, mediaContent).execute();

CreateEmail is simple method from quickstart:

   public static MimeMessage createEmail(String to,
                                              String from,
                                              String subject,
                                              String bodyText)
                throws MessagingException {
            Properties props = new Properties();
            Session session = Session.getDefaultInstance(props, null);

            MimeMessage email = new MimeMessage(session);

            email.setFrom(new InternetAddress(from));
            email.addRecipient(javax.mail.Message.RecipientType.TO,
                    new InternetAddress(to));
            email.setSubject(subject);
            email.setText(bodyText);
            return email;
        }

The message appeared in my email box but without the file.

What's wrong here?

UPD1: Inserting with media content, inserts only an email without an attachment. I think I use it in a wrong way.


Solution

  • I've figured out how to use resumable upload using java library (the same idea via REST):

    byte[] bytes = Base64.decodeBase64(message.getRaw());
    Insert insertReq;
    Message content = new Message();
    content.setLabelIds(message.getLabelIds());
    try {
        insertReq = gmail.users().messages().insert(account, content,
            new ByteArrayContent("message/rfc822", bytes, 0, bytes.length));
        helper.execute(insertReq, task.getPartnerID(), task.isUnderWhiteLable());
    } catch (IOException e) {
        Log.error("Failed to insert a message with resumable upload message", e);
    }
    

    The method's description turned out to be quite understandable but post factum. I have no idea why the description is so poor:

    /**                                                                                                                                                                                                
     * Directly inserts a message into only this user's mailbox similar to IMAP APPEND, bypassing most                                                                                                 
     * scanning and classification. Does not send a message.                                                                                                                                           
     *                                                                                                                                                                                                 
     * Create a request for the method "messages.insert".                                                                                                                                              
     *                                                                                                                                                                                                 
     * This request holds the parameters needed by the the gmail server.  After setting any optional                                                                                                   
     * parameters, call the {@link Insert#execute()} method to invoke the remote operation.                                                                                                            
     *                                                                                                                                                                                                 
     * <p>                                                                                                                                                                                             
     * This method should be used for uploading media content.                                                                                                                                         
     * </p>                                                                                                                                                                                            
     *                                                                                                                                                                                                 
     * @param userId The user's email address. The special value me can be used to indicate the authenticated user.                                                                                    
     *        [default: me]                                                                                                                                                                            
     * @param content the {@link com.google.api.services.gmail.model.Message} media metadata or {@code null} if none                                                                                   
     * @param mediaContent The media HTTP content or {@code null} if none.                                                                                                                             
     * @return the request                                                                                                                                                                             
     * @throws java.io.IOException if the initialization of the request fails                                                                                                                          
     */                                                                                                                                                                                                
    public Insert insert(java.lang.String userId, com.google.api.services.gmail.model.Message content, com.google.api.client.http.AbstractInputStreamContent mediaContent) throws java.io.IOException {
      Insert result = new Insert(userId, content, mediaContent);                                                                                                                                       
      initialize(result);                                                                                                                                                                              
      return result;                                                                                                                                                                                   
    }