Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to send a csv attachment with lines longer than 990 characters?

Alright. I thought this problem had something to do with my rails app, but it seems to have to do with the deeper workings of email attachments.

I have to send out a csv file from my rails app to a warehouse that fulfills orders places in my store. The warehouse has a format for the CSV, and ironically the header line of the CSV file is super long (1000+ characters).

I was getting a line break in the header line of the csv file when I received the test emails and couldn't figure out what put it there. However, some googling has finally showed the reason: attached files have a line character limit of 1000. Why? I don't know. It seems ridiculous, but I still have to send this csv file somehow.

I tried manually setting the MIME type of the attachment to text/csv, but that was no help. Does anybody know how to solve this problem?

Some relevant google results : http://www.google.com/search?client=safari&rls=en&q=csv+wrapped+990&ie=UTF-8&oe=UTF-8

update

I've tried encoding the attachment in base64 like so:

    attachments['205.csv'] = {:data=> ActiveSupport::Base64.encode64(@string), :encoding => 'base64', :mime_type => 'text/csv'}

That doesn't seem to have made a difference. I'm receiving the email with a me.com account via Sparrow for Mac. I'll try using gmail's web interface.

like image 932
CharlieMezak Avatar asked May 01 '12 17:05

CharlieMezak


2 Answers

This seems to be because the SendGrid mail server is modifying the attachment content. If you send an attachment with a plain text storage mime type (e.g text/csv) it will wrap the content every 990 characters, as you observed. I think this is related to RFC 2045/821:

  1. Content-Transfer-Encoding Header Field

    Many media types which could be usefully transported via email are represented, in their "natural" format, as 8bit character or binary
    data. Such data cannot be transmitted over some transfer protocols.
    For example, RFC 821 (SMTP) restricts mail messages to 7bit US-ASCII
    data with lines no longer than 1000 characters including any trailing CRLF line separator.

    It is necessary, therefore, to define a standard mechanism for
    encoding such data into a 7bit short line format. Proper labelling
    of unencoded material in less restrictive formats for direct use over less restrictive transports is also desireable. This document
    specifies that such encodings will be indicated by a new "Content-
    Transfer-Encoding" header field. This field has not been defined by
    any previous standard.

If you send the attachment using base64 encoding instead of the default 7-bit the attachment remains unchanged (no added line breaks):

attachments['file.csv']= { :data=> ActiveSupport::Base64.encode64(@string), :encoding => 'base64' }
like image 170
pjumble Avatar answered Oct 22 '22 16:10

pjumble


Could you have newlines in your data that would cause this? Check and see if

csv_for_orders(orders).lines.count == orders.count

If so, a quick/hackish fix might be changing where you call values_for_line_item(item) to values_for_line_item(item).map{|c| c.gsub(/(\r|\n)/, '')} (same for the other line_item calls).

like image 22
Abe Voelker Avatar answered Oct 22 '22 16:10

Abe Voelker