Rails3 CSV ставит & quot; вместо реальных цитат

Похож на этот вопрос, но я не пользуюсь html_safe где угодно во всем проекте.

Я генерирую файл CSV в index.csv.erb как это:

<%=
response.content_type = 'application/octet-stream'
CSV.generate do |csv|
  @persons.each do |person|
    csv << [ person[:name], person[:nickname] ]
  end
end
%>

ПРОБЛЕМА: Если в базе данных (ActiveRecord/MySQL) псевдоним имеет значение NULL, то элемент, связанный с файлом CSV, становится &quot;&quot;, Я бы ожидал "" или вообще ничего.

Пример файла результата:

Nicolas, Nico
Joe, &quot;&quot;

Как я могу предотвратить это?

2 ответа

Решение

Проблема в том, что вы не используете html_safe, Ваше поле псевдонима пусто и преобразовано в "" в файле csv, но Rails считает его небезопасным, а html избежал.

Просто позвони html_safe по результату:

<%=
response.content_type = 'application/octet-stream'
CSV.generate do |csv|
  @persons.each do |person|
    csv << [ person[:name], person[:nickname] ]
  end
end .html_safe
%>

Решение, на которое вы ссылаетесь, больше не работает с Rails 3, поскольку по умолчанию все строки считаются небезопасными, чего не было в Rails 2.

Refactored

Бенуа абсолютно прав, и спасибо за этот совет. Посмотрев на ваш код, я вижу гораздо более чистый подход к генерации вашего CSV, который, как я думал, я поделюсь тем, кто приземлится здесь (как я!):

<%=
response.content_type = 'application/octet-stream'
@persons.collect{ |person| [ person[:name], person[:nickname] ].to_csv }.join.html_safe 
%>

По сути, вам не нужно все, что генерирует CSV. Руби может взять Array и превратить его в строку CSV, а затем просто использовать collect а также join собрать все это вместе.

Вы также можете сделать следующее, если вы предпочитаете иметь его в отдельных строках, что я делаю:

<% response.content_type = 'application/octet-stream' -%> 
<% @persons.each do |person| -%>
  <%= [ person[:name], person[:nickname] ].to_csv( row_sep: nil ).html_safe %>
<% end -%>

Здесь вам нужно использовать -%> чтобы убедиться, что вы не получите лишних пустых строк, и вам нужно будет использовать row_sep: nil вариант, чтобы to_csv не добавляет \n в конце каждой строки.

В любом случае, надеюсь, это поможет очистить код некоторых людей.

Другие вопросы по тегам