Example usage for javax.mail Part getSize

List of usage examples for javax.mail Part getSize

Introduction

In this page you can find the example usage for javax.mail Part getSize.

Prototype

public int getSize() throws MessagingException;

Source Link

Document

Return the size of the content of this part in bytes.

Usage

From source file:dtw.webmail.model.JwmaMessagePartImpl.java

/**
 * Creates a <tt>JwmaMessagePartImpl</tt> instance from a given
 * <tt>javax.mail.Part</tt> instance.
 *
 * @param part a <tt>javax.mail.Part</tt> instance.
 * @param number the number of the part as <tt>int</tt>.
 *
 * @return the newly created instance.// ww  w . jav a  2 s .  c  o m
 * @throws JwmaException if it fails to create the new instance.
 */
public static JwmaMessagePartImpl createJwmaMessagePartImpl(Part part, int number) throws JwmaException {
    JwmaMessagePartImpl partinfo = new JwmaMessagePartImpl(part, number);

    //content type
    try {
        partinfo.setContentType(part.getContentType());

        //size
        int size = part.getSize();
        //JwmaKernel.getReference().debugLog().write("Part size="+size);
        String fileName = part.getFileName();
        //correct size of encoded parts
        String[] encoding = part.getHeader("Content-Transfer-Encoding");
        if (fileName != null && encoding != null && encoding.length > 0
                && (encoding[0].equalsIgnoreCase("base64") || encoding[0].equalsIgnoreCase("uuencode"))) {
            if ((fileName.startsWith("=?GB2312?B?") && fileName.endsWith("?="))) {
                byte[] decoded = Base64.decodeBase64(fileName.substring(11, fileName.indexOf("?=")).getBytes());
                fileName = new String(decoded, "GB2312");
                /*fileName = CipherUtils.decrypt(fileName);
                System.out.println("fileName----"+fileName);*/
                //fileName = getFromBASE64(fileName.substring(11,fileName.indexOf("?=")));  
            } else if ((fileName.startsWith("=?UTF-8?") || fileName.startsWith("=?UTF8?"))
                    && fileName.endsWith("?=")) {
                fileName = MimeUtility.decodeText(fileName);
            }
            //an encoded file is about 35% smaller in reality,
            //so correct the size
            size = (int) (size * 0.65);
        }

        partinfo.setSize(size);
        //description
        partinfo.setDescription(part.getDescription());

        //filename
        partinfo.setName(fileName);

        //textcontent
        if (partinfo.isMimeType("text/*")) {
            Object content = part.getContent();
            if (content instanceof String) {
                partinfo.setTextContent((String) content);
            } else if (content instanceof InputStream) {
                InputStream in = (InputStream) content;
                ByteArrayOutputStream bout = new ByteArrayOutputStream();
                byte[] buffer = new byte[8192];
                int amount = 0;
                while ((amount = in.read(buffer)) >= 0) {
                    bout.write(buffer, 0, amount);
                }
                partinfo.setTextContent(new String(bout.toString()));
            }
        }
    } catch (Exception mex) {
        throw new JwmaException("jwma.messagepart.failedcreation", true).setException(mex);
    }
    return partinfo;
}

From source file:mitm.common.mail.MailUtils.java

/**
 * Returns the Part as a byte array. The Part is converted to a byte array using MimeMessage.writeTo. 
 * If a message contains a corrupt body (like incorrect base64) writeTo can throw an exception. 
 *///  w  ww.j  av  a  2 s .c om
public static byte[] partToByteArray(Part part) throws IOException, MessagingException {
    /*
     * create a buffer with some 'guess' of the size plus some constant value. If size is unknown size = -1 so
     * the buffer will be 1023.
     */
    ByteArrayOutputStream bos = new ByteArrayOutputStream(part.getSize() + 1024);

    part.writeTo(bos);

    return bos.toByteArray();
}

From source file:mitm.common.mail.filter.UnsupportedFormatStripper.java

private int getNewMessageSize(List<Part> currentParts, Part newPart) throws MessagingException {
    int size = newPart.getSize();

    for (Part part : currentParts) {
        size = size + part.getSize();//from   www.j  ava 2 s .  com
    }

    return size;
}

From source file:org.zilverline.core.IMAPCollection.java

/**
 * Index a part./*from   ww w  .  j a  v a  2 s  .c  o  m*/
 */
private void indexPart(final Document doc, final Part p) throws MessagingException, IOException {
    int size = p.getSize();
    String ct = p.getContentType();
    String cd = p.getDescription();
    log.debug("IndexContent, type: " + ct + ", description: " + cd);
    Object content = null;

    if (ct != null) {
        doc.add(Field.Keyword(F_CT, ct));
    }
    doc.add(Field.Keyword("type", "MAIL"));

    if (cd != null) {
        doc.add(Field.Keyword(F_CD, cd));
    }

    if (ct != null && ct.toLowerCase().startsWith("image/")) {
        // no point for now but maybe in the future we see if any forms such as jpegs have some strings
        return;
    }

    try {
        // get content object, indirectly calls into JAF which decodes based on MIME type and char
        content = p.getContent();
    } catch (IOException ioe) {
        log.warn("OUCH decoding attachment, p=" + p, ioe);
        doc.add(Field.Text(F_CONTENTS, new InputStreamReader(p.getInputStream())));
        return;
    }

    if (content instanceof MimeMultipart) {
        int n = ((MimeMultipart) content).getCount();
        for (int i = 0; i < n; i++) {
            BodyPart bp = ((MimeMultipart) content).getBodyPart(i);
            // same thing ends up happening regardless, if/else left it to show structure
            indexPart(doc, bp);
        }
    } else if (content instanceof MimePart) {
        indexPart(doc, (MimePart) content);
    } else if (content instanceof Part) {
        indexPart(doc, (Part) content);
    } else if (content instanceof String) {
        indexString(doc, (String) content, ct);
    } else if (content instanceof InputStream) {
        indexStream(doc, (InputStream) content, ct);
    } else {
        log.error("***** Strange content: " + content + "/" + content.getClass() + " ct=" + ct + " cd=" + cd);
    }
}

From source file:com.silverpeas.mailinglist.service.job.MailProcessor.java

/**
 * Processes a part for a multi-part email.
 *
 * @param part the part to be processed.
 * @param message the message corresponding to the email.
 * @throws MessagingException/*from   www .  j av a  2  s. c o  m*/
 * @throws IOException
 */
public void processMailPart(Part part, Message message) throws MessagingException, IOException {
    if (!isTextPart(part)) {
        Object content = part.getContent();
        if (content instanceof Multipart) {
            processMultipart((Multipart) content, message);
        } else {
            String fileName = getFileName(part);
            if (fileName != null) {
                Attachment attachment = new Attachment();
                attachment.setSize(part.getSize());
                attachment.setFileName(fileName);
                attachment.setContentType(extractContentType(part.getContentType()));
                String attachmentPath = saveAttachment(part, message.getComponentId(), message.getMessageId());
                attachment.setPath(attachmentPath);
                message.getAttachments().add(attachment);
            }
        }
    } else {
        processBody((String) part.getContent(), extractContentType(part.getContentType()), message);
    }
}

From source file:de.mendelson.comm.as2.message.AS2MessageParser.java

/**Looks if the data is compressed and decompresses it if necessary
 *///from ww  w .j a va2s.co  m
public Part decompressData(Part part, AS2Message message) throws Exception {
    Part compressedPart = this.getCompressedEmbeddedPart(part);
    if (compressedPart == null) {
        return (part);
    }
    SMIMECompressed compressed = null;
    if (compressedPart instanceof MimeBodyPart) {
        compressed = new SMIMECompressed((MimeBodyPart) compressedPart);
    } else {
        compressed = new SMIMECompressed((MimeMessage) compressedPart);
    }
    byte[] decompressedData = compressed.getContent();
    ((AS2MessageInfo) message.getAS2Info()).setCompressionType(AS2Message.COMPRESSION_ZLIB);
    if (this.logger != null) {
        this.logger.log(Level.INFO,
                this.rb.getResourceString("data.compressed.expanded",
                        new Object[] { message.getAS2Info().getMessageId(),
                                AS2Tools.getDataSizeDisplay(part.getSize()),
                                AS2Tools.getDataSizeDisplay(decompressedData.length) }),
                message.getAS2Info());
    }
    ByteArrayInputStream memIn = new ByteArrayInputStream(decompressedData);
    MimeBodyPart uncompressedPayload = new MimeBodyPart(memIn);
    memIn.close();
    return (uncompressedPayload);
}

From source file:com.liferay.mail.imap.IMAPAccessor.java

protected void getParts(long userId, StringBundler bodyPlain, StringBundler bodyHtml, String contentPath,
        Part part, List<MailFile> mailFiles) throws IOException, MessagingException {

    String fileName = part.getFileName();
    Object content = part.getContent();

    if (content instanceof Multipart) {
        Multipart multipart = (Multipart) content;

        for (int i = 0; i < multipart.getCount(); i++) {
            Part curPart = multipart.getBodyPart(i);

            getParts(userId, bodyPlain, bodyHtml,
                    contentPath.concat(StringPool.PERIOD).concat(String.valueOf(i)), curPart, mailFiles);
        }/*from w ww. j a v  a  2s .  co  m*/
    } else if (Validator.isNull(fileName)) {
        String contentType = StringUtil.toLowerCase(part.getContentType());

        if (contentType.startsWith(ContentTypes.TEXT_PLAIN)) {
            bodyPlain.append(content.toString().replaceAll("\r\n", "<br />"));
        } else if (contentType.startsWith(ContentTypes.TEXT_HTML)) {
            bodyHtml.append(HtmlContentUtil.getInlineHtml(content.toString()));
        }
        //else if (contentType.startsWith(ContentTypes.MESSAGE_RFC822)) {
        //}
    } else {
        MailFile mailFile = new MailFile(contentPath.concat(StringPool.PERIOD).concat("-1"), fileName,
                part.getSize());

        mailFiles.add(mailFile);
    }
}

From source file:de.mendelson.comm.as2.message.AS2MessageCreation.java

/**Builds up a new message from the passed message parts
 * @param messageType one of the message types definfed in the class AS2Message
 *//*from   w w  w  .  j  av  a  2 s . c  o  m*/
public AS2Message createMessage(Partner sender, Partner receiver, AS2Payload[] payloads, int messageType,
        String messageId) throws Exception {
    if (messageId == null) {
        messageId = UniqueId.createMessageId(sender.getAS2Identification(), receiver.getAS2Identification());
    }
    BCCryptoHelper cryptoHelper = new BCCryptoHelper();
    AS2MessageInfo info = new AS2MessageInfo();
    info.setMessageType(messageType);
    info.setSenderId(sender.getAS2Identification());
    info.setReceiverId(receiver.getAS2Identification());
    info.setSenderEMail(sender.getEmail());
    info.setMessageId(messageId);
    info.setDirection(AS2MessageInfo.DIRECTION_OUT);
    info.setSignType(receiver.getSignType());
    info.setEncryptionType(receiver.getEncryptionType());
    info.setRequestsSyncMDN(receiver.isSyncMDN());
    if (!receiver.isSyncMDN()) {
        info.setAsyncMDNURL(sender.getMdnURL());
    }
    info.setSubject(receiver.getSubject());
    try {
        info.setSenderHost(InetAddress.getLocalHost().getCanonicalHostName());
    } catch (UnknownHostException e) {
        //nop
    }
    //create message object to return
    AS2Message message = new AS2Message(info);
    //stores all the available body parts that have been prepared
    List<MimeBodyPart> contentPartList = new ArrayList<MimeBodyPart>();
    for (AS2Payload as2Payload : payloads) {
        //add payload
        message.addPayload(as2Payload);
        if (this.runtimeConnection != null) {
            MessageAccessDB messageAccess = new MessageAccessDB(this.configConnection, this.runtimeConnection);
            messageAccess.initializeOrUpdateMessage(info);
        }
        //no MIME message: single payload, unsigned, no CEM
        if (info.getSignType() == AS2Message.SIGNATURE_NONE && payloads.length == 1
                && info.getMessageType() != AS2Message.MESSAGETYPE_CEM) {
            return (this.createMessageNoMIME(message, receiver));
        }
        //MIME message
        MimeBodyPart bodyPart = new MimeBodyPart();
        String contentType = null;
        if (as2Payload.getContentType() == null) {
            contentType = receiver.getContentType();
        } else {
            contentType = as2Payload.getContentType();
        }
        bodyPart.setDataHandler(new DataHandler(new ByteArrayDataSource(as2Payload.getData(), contentType)));
        bodyPart.addHeader("Content-Type", contentType);
        if (as2Payload.getContentId() != null) {
            bodyPart.addHeader("Content-ID", as2Payload.getContentId());
        }
        if (receiver.getContentTransferEncoding() == AS2Message.CONTENT_TRANSFER_ENCODING_BASE64) {
            bodyPart.addHeader("Content-Transfer-Encoding", "base64");
        } else {
            bodyPart.addHeader("Content-Transfer-Encoding", "binary");
        }
        //prepare filename to not violate the MIME header rules
        if (as2Payload.getOriginalFilename() == null) {
            as2Payload.setOriginalFilename(new File(as2Payload.getPayloadFilename()).getName());
        }
        String newFilename = as2Payload.getOriginalFilename().replace(' ', '_');
        newFilename = newFilename.replace('@', '_');
        newFilename = newFilename.replace(':', '_');
        newFilename = newFilename.replace(';', '_');
        newFilename = newFilename.replace('(', '_');
        newFilename = newFilename.replace(')', '_');
        bodyPart.addHeader("Content-Disposition", "attachment; filename=" + newFilename);
        contentPartList.add(bodyPart);
    }
    Part contentPart = null;
    //sigle attachment? No CEM? Every CEM is in a multipart/related container
    if (contentPartList.size() == 1 && info.getMessageType() != AS2Message.MESSAGETYPE_CEM) {
        contentPart = contentPartList.get(0);
    } else {
        //build up a new MimeMultipart container for the multiple attachments, content-type
        //is "multipart/related"
        MimeMultipart multipart = null;
        //CEM messages are always in a multipart container (even the response which contains only a single
        //payload) with the subtype "application/ediint-cert-exchange+xml".
        if (info.getMessageType() == AS2Message.MESSAGETYPE_CEM) {
            multipart = new MimeMultipart("related; type=\"application/ediint-cert-exchange+xml\"");
        } else {
            multipart = new MimeMultipart("related");
        }
        for (MimeBodyPart bodyPart : contentPartList) {
            multipart.addBodyPart(bodyPart);
        }
        contentPart = new MimeMessage(Session.getInstance(System.getProperties(), null));
        contentPart.setContent(multipart, multipart.getContentType());
        ((MimeMessage) contentPart).saveChanges();
    }
    //should the content be compressed and enwrapped or just enwrapped?
    if (receiver.getCompressionType() == AS2Message.COMPRESSION_ZLIB) {
        info.setCompressionType(AS2Message.COMPRESSION_ZLIB);
        int uncompressedSize = contentPart.getSize();
        contentPart = this.compressPayload(receiver, contentPart);
        int compressedSize = contentPart.getSize();
        //sometimes size() is unable to determine the size of the compressed body part and will return -1. Dont log the
        //compression ratio in this case.
        if (uncompressedSize == -1 || compressedSize == -1) {
            if (this.logger != null) {
                this.logger.log(Level.INFO, this.rb.getResourceString("message.compressed.unknownratio",
                        new Object[] { info.getMessageId() }), info);
            }
        } else {
            if (this.logger != null) {
                this.logger.log(Level.INFO,
                        this.rb.getResourceString("message.compressed",
                                new Object[] { info.getMessageId(),
                                        AS2Tools.getDataSizeDisplay(uncompressedSize),
                                        AS2Tools.getDataSizeDisplay(compressedSize) }),
                        info);
            }
        }
    }
    //compute content mic. Try to use sign digest as hash alg. For unsigned messages take sha-1
    String digestOID = null;
    if (info.getSignType() == AS2Message.SIGNATURE_MD5) {
        digestOID = cryptoHelper.convertAlgorithmNameToOID(BCCryptoHelper.ALGORITHM_MD5);
    } else {
        digestOID = cryptoHelper.convertAlgorithmNameToOID(BCCryptoHelper.ALGORITHM_SHA1);
    }
    String mic = cryptoHelper.calculateMIC(contentPart, digestOID);
    if (info.getSignType() == AS2Message.SIGNATURE_MD5) {
        info.setReceivedContentMIC(mic + ", md5");
    } else {
        info.setReceivedContentMIC(mic + ", sha1");
    }
    this.enwrappInMessageAndSign(message, contentPart, sender, receiver);
    //encryption requested for the receiver?
    if (info.getEncryptionType() != AS2Message.ENCRYPTION_NONE) {
        String cryptAlias = this.encryptionCertManager
                .getAliasByFingerprint(receiver.getCryptFingerprintSHA1());
        this.encryptDataToMessage(message, cryptAlias, info.getEncryptionType(), receiver);
    } else {
        message.setRawData(message.getDecryptedRawData());
        if (this.logger != null) {
            this.logger.log(Level.INFO,
                    this.rb.getResourceString("message.notencrypted", new Object[] { info.getMessageId() }),
                    info);
        }
    }
    return (message);
}

From source file:com.duroty.utils.mail.MessageUtilities.java

/**
 * Given a message that we are replying to, or forwarding,
 *
 * @param part The part to decode./*  ww  w .j  a v  a2 s. c o  m*/
 * @param buffer The new message body text buffer.
 * @param dmailParts Vector for new message's attachments.
 *
 * @return The buffer being filled in with the body.
 *
 * @throws MessagingException DOCUMENT ME!
 * @throws IOException
 */
protected static StringBuffer subDecodeContent(Part part, StringBuffer buffer, Vector dmailParts,
        boolean chooseHtml, String breakLine) throws MessagingException, IOException {
    boolean attachIt = true;

    // decode based on content type and disposition
    ContentType xctype = MessageUtilities.getContentType(part);

    ContentDisposition xcdisposition = MessageUtilities.getContentDisposition(part);

    if (xctype.match("multipart/*")) {
        attachIt = false;

        Multipart xmulti = (Multipart) MessageUtilities.getPartContent(part);

        int xparts = 0;

        try {
            xparts = xmulti.getCount();
        } catch (MessagingException e) {
            attachIt = true;
            xparts = 0;
        }

        for (int xindex = 0; xindex < xparts; xindex++) {
            MessageUtilities.subDecodeContent(xmulti.getBodyPart(xindex), buffer, dmailParts, chooseHtml,
                    breakLine);
        }
    } else if (xctype.match("message/rfc822")) {
        MimeMessage newMessage = new MimeMessage((Session) null, part.getInputStream());
        decodeContent(newMessage, buffer, dmailParts, chooseHtml, breakLine);
    } else if (xctype.match("text/plain") && !chooseHtml) {
        if (xcdisposition.match("inline")) {
            attachIt = false;

            String xjcharset = xctype.getParameter("charset");

            if (xjcharset == null) {
                // not present, assume ASCII character encoding                       
                try {
                    Header xheader;
                    Enumeration xe = part.getAllHeaders();

                    for (; xe.hasMoreElements();) {
                        xheader = (Header) xe.nextElement();

                        String aux = xheader.getName().toLowerCase().trim();

                        if (aux.indexOf("subject") > -1) {
                            int pos1 = aux.indexOf("=?");
                            int pos2 = aux.indexOf("?q?");

                            if ((pos1 > -1) && (pos2 > -1)) {
                                xjcharset = aux.substring(pos1, pos2);
                            }

                            break;
                        }
                    }
                } catch (Exception ex) {
                    System.out.print(ex.getMessage());
                }

                if (xjcharset == null) {
                    xjcharset = Charset.defaultCharset().displayName(); // US-ASCII in JAVA terms
                }
            }

            MessageUtilities.decodeTextPlain(buffer, part, breakLine, xjcharset);
        }
    } else if (xctype.match("text/html") && chooseHtml) {
        if (xcdisposition.match("inline")) {
            attachIt = false;

            String xjcharset = xctype.getParameter("charset");

            if (xjcharset == null) {
                // not present, assume ASCII character encoding                       
                try {
                    Header xheader;
                    Enumeration xe = part.getAllHeaders();

                    for (; xe.hasMoreElements();) {
                        xheader = (Header) xe.nextElement();

                        String aux = xheader.getName().toLowerCase().trim();

                        if (aux.indexOf("subject") > -1) {
                            int pos1 = aux.indexOf("=?");
                            int pos2 = aux.indexOf("?q?");

                            if ((pos1 > -1) && (pos2 > -1)) {
                                xjcharset = aux.substring(pos1, pos2);
                            }

                            break;
                        }
                    }
                } catch (Exception ex) {
                }

                if (xjcharset == null) {
                    xjcharset = Charset.defaultCharset().displayName(); // US-ASCII in JAVA terms
                }
            }

            MessageUtilities.decodeTextHtml(buffer, part, xjcharset);
        }
    }

    if (attachIt) {
        // UNDONE should simple single line entries be
        //        created for other types and attachments?
        //
        // UNDONE should attachements only be created for "attachments" or all
        // unknown content types?
        if (dmailParts != null) {
            MailPart aux = new MailPart();
            aux.setPart(part);
            aux.setId(dmailParts.size());
            aux.setName(MessageUtilities.encodeStringToXml(MessageUtilities.getPartName(part)));
            aux.setContentType(xctype.getBaseType());
            aux.setSize(part.getSize());

            dmailParts.addElement(aux);
        }
    }

    return buffer;
}

From source file:edu.stanford.muse.email.EmailFetcherStats.java

/**
 * recursively processes attachments, fetching and saving it if needed
 * parses the given part p, and adds it to hte attachmentsList.
 * in some cases, like a text/html type without a filename, we instead append it to the textlist
 * @throws MessagingException/*from  ww  w  .  jav  a  2 s  . c o  m*/
 */
private void handleAttachments(int idx, Message m, Part p, List<String> textList, List<Blob> attachmentsList)
        throws MessagingException {
    String ct = null;
    if (!(m instanceof MimeMessage)) {
        Exception e = new IllegalArgumentException("Not a MIME message!");
        e.fillInStackTrace();
        log.warn(Util.stackTrace(e));
        return;
    }

    String filename = null;
    try {
        filename = p.getFileName();
    } catch (Exception e) {
        // seen this happen with:
        // Folders__gmail-sent Message #12185 Expected ';', got "Message"
        // javax.mail.internet.ParseException: Expected ';', got "Message"

        dataErrors.add("Unable to read attachment name: " + folder_name() + " Message# " + idx);
        return;
    }

    String sanitizedFName = Util.sanitizeFolderName(emailStore.getAccountID() + "." + folder_name());
    if (filename == null) {
        String tempFname = sanitizedFName + "." + idx;
        dataErrors.add("attachment filename is null for " + sanitizedFName + " Message#" + idx
                + " assigning it the name: " + tempFname);
        if (p.isMimeType("text/html")) {
            try {
                log.info("Turning message " + sanitizedFName + " Message#" + idx
                        + " into text although it is an attachment");
                String html = (String) p.getContent();
                String text = Util.unescapeHTML(html);
                org.jsoup.nodes.Document doc = Jsoup.parse(text);

                StringBuilder sb = new StringBuilder();
                HTMLUtils.extractTextFromHTML(doc.body(), sb);
                textList.add(sb.toString());
                return;
            } catch (Exception e) {
                Util.print_exception("Error reading contents of text/html multipart without a filename!", e,
                        log);
                return;
            }
        }
        filename = tempFname;
    }

    // Replacing any of the disallowed filename characters (\/:*?"<>|&) to _
    // (note: & causes problems with URLs for serveAttachment etc, so it's also replaced)
    String newFilename = Util.sanitizeFileName(filename);

    // Updating filename if it's changed after sanitizing.
    if (!newFilename.equals(filename)) {
        log.info("Filename changed from " + filename + " to " + newFilename);
        filename = newFilename;
    }

    try {
        ct = p.getContentType();
        if (filename.indexOf(".") < 0) // no ext in filename... let's fix it if possible
        {
            // Using startsWith instead of equals because sometimes the ct has crud beyond the image/jpeg;...crud....
            // Below are the most common file types, more type can be added if needed

            // Most common APPLICATION TYPE
            if (ct.startsWith("application/pdf"))
                filename = filename + ".pdf";
            if (ct.startsWith("application/zip"))
                filename = filename + ",zip";
            // Most common IMAGE TYPE
            if (ct.startsWith("image/jpeg"))
                filename = filename + ".jpg";
            if (ct.startsWith("image/gif"))
                filename = filename + ".gif";
            if (ct.startsWith("image/png"))
                filename = filename + ".png";
            // Most Common VIDEO TYPE
            if (ct.startsWith("video/x-ms-wmv"))
                filename = filename + ".wmv";
            // Most Common AUDIO TYPE
            if (ct.startsWith("audio/mpeg"))
                filename = filename + ".mp3";
            if (ct.startsWith("audio/mp4"))
                filename = filename + ".mp4";
            // Most Common TEXT TYPE
            if (ct.startsWith("text/html"))
                filename = filename + ".html";
            // Windows Office
            if (ct.startsWith("application/vnd.openxmlformats-officedocument.wordprocessingml.document")) //Word
                filename = filename + ".docx";
            if (ct.startsWith("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")) //Excel
                filename = filename + ".xlsx";
            if (ct.startsWith("application/vnd.openxmlformats-officedocument.presentationml.presentation")) //PowerPoint
                filename = filename + ".pptx";
        }
        // retain only up to first semi-colon; often ct is something like text/plain; name="filename"' we don't want to log the filename
        int x = ct.indexOf(";");
        if (x >= 0)
            ct = ct.substring(0, x);
        log.info("Attachment content type: " + ct + " filename = " + Util.blurKeepingExtension(filename));
    } catch (Exception pex) {
        dataErrors.add("Can't read CONTENT-TYPE: " + ct + " filename:" + filename + " size = " + p.getSize()
                + " subject: " + m.getSubject() + " Date : " + m.getSentDate().toString() + "\n Exception: "
                + pex + "\n" + Util.stackTrace(pex));
        return;
    }

    //       if (filename == null && !p.isMimeType("text/html") && !p.isMimeType("message/partial")) // expected not to have a filename with mime type text/html
    //          log.warn ("Attachment filename is null: " + Util.stackTrace());

    boolean success = true;
    // the size passed in here is the part size, which is not really the binary blob size.
    // when we read the stream below in blobStore.add(), we'll set it again to the binary blob size
    Blob b = new EmailAttachmentBlob(filename, p.getSize(), (MimeMessage) m, p);

    if (fetchConfig.downloadAttachments) {
        // this containment check is only on the basis of file name and size currently,
        // not on the actual hash
        if (archive.getBlobStore().contains(b)) {
            log.debug("Cache hit! " + b);
        } else {
            try {
                if (filename.endsWith(".tif"))
                    log.info("Fetching attachment..." + Util.blurKeepingExtension(filename));

                // performance critical! use large buffer! currently 256KB
                // stream will be closed by callee

                long start = System.currentTimeMillis();
                long nBytes = archive.getBlobStore().add(b,
                        new BufferedInputStream(p.getInputStream(), 256 * 1024));
                long end = System.currentTimeMillis();
                if (nBytes != -1) {
                    long diff = end - start;
                    String s = "attachment size " + nBytes + " bytes, fetched in " + diff + " millis";
                    if (diff > 0)
                        s += " (" + (nBytes / diff) + " KB/s)";
                    log.info(s);
                }

                Util.ASSERT(archive.getBlobStore().contains(b));

            } catch (IOException ioe) {
                success = false;
                dataErrors.add("WARNING: Unable to fetch attachment: filename: " + filename + " size = "
                        + p.getSize() + " subject: " + m.getSubject() + " Date : " + m.getSentDate().toString()
                        + "\nException: " + ioe);
                ioe.printStackTrace(System.out);
            }
        }

        if (success) {
            attachmentsList.add(b);

            /// generate thumbnail only if not already cached
            try {
                archive.getBlobStore().generate_thumbnail(b); // supplement
            } catch (IOException ioe) {
                log.warn("failed to create thumbnail, filename: " + filename + " size = " + p.getSize()
                        + " subject: " + m.getSubject() + " Date : " + m.getSentDate().toString()
                        + "\nException: " + ioe);
                ioe.printStackTrace(System.out);
            }
        }
    }
}