Comment puis-je générer un CSV UTF-8 en PHP qu'Excel lira correctement?

191

J'ai ce truc très simple qui sort juste des trucs au format CSV, mais ça doit être UTF-8. J'ouvre ce fichier dans TextEdit ou TextMate ou Dreamweaver et il affiche correctement les caractères UTF-8, mais si je l'ouvre dans Excel, c'est ce genre de chose stupide à la place. Voici ce que j'ai en tête de mon document:

header("content-type:application/csv;charset=UTF-8");
header("Content-Disposition:attachment;filename=\"CHS.csv\"");

Tout cela semble avoir l'effet souhaité, sauf qu'Excel (Mac, 2008) ne veut pas l'importer correctement. Il n'y a pas d'options dans Excel pour que je puisse "ouvrir en UTF-8" ou quoi que ce soit, alors ... Je suis un peu ennuyé.

Je n'arrive pas à trouver de solutions claires à ce problème, même si beaucoup de gens ont le même problème. La chose que je vois le plus est d'inclure la nomenclature, mais je ne sais pas exactement comment faire cela. Comme vous pouvez le voir ci-dessus, je viens d' echoingérer ces données, je n'écris aucun fichier. Je peux le faire si j'en ai besoin, je ne le suis tout simplement pas parce que cela ne semble pas nécessaire à ce stade. De l'aide?

Mise à jour: j'ai essayé de faire écho à la nomenclature que echo pack("CCC", 0xef, 0xbb, 0xbf);je viens de retirer d'un site qui essayait de détecter la nomenclature. Mais Excel ajoute simplement ces trois caractères à la toute première cellule lors de l'importation et gâche toujours les caractères spéciaux.

Ben Saufley
la source
2
Excel ne fournit pas d'option pour ajuster le jeu de caractères du fichier entrant? En êtes-vous sûr à 100%? Je n'ai pas de copie sous la main, donc je ne peux pas essayer mais j'imagine qu'il doit y avoir une liste déroulante quelque part.
Pekka
C'est Excel sur un Mac - cela semble plus limité qu'Excel sur le PC. Il n'y a pas du tout de liste déroulante dans la boîte de dialogue Ouvrir, au-delà des types de fichiers à ouvrir. J'ai regardé partout. Si c'est là, c'est obscur. Je dirais que 98% sont sûrs.
Ben Saufley
Bureau Microsoft ou openoffice?
ajreal
Microsoft est meilleur à cet égard, il n'y a aucun moyen (que j'ai trouvé) de faire en sorte qu'OpenOffice détecte le jeu de caractères, pas même la nomenclature. Mince.
Ciantic
La nomenclature n'a pas non plus d'effet sur Microsoft Excel 2008 pour Mac.
Ben Saufley

Réponses:

134

Pour citer un ingénieur du support Microsoft ,

Excel pour Mac ne prend actuellement pas en charge UTF-8

Mise à jour, 2017 : Ceci est vrai pour toutes les versions de Microsoft Excel pour Mac avant Office 2016 . Les versions plus récentes (à partir d'Office 365) prennent désormais en charge UTF-8.

Afin de produire du contenu UTF-8 qu'Excel à la fois sous Windows et OS X pourra lire avec succès, vous devrez faire deux choses:

  1. Assurez-vous de convertir votre texte CSV UTF-8 en UTF-16LE

    mb_convert_encoding($csv, 'UTF-16LE', 'UTF-8');
  2. Assurez-vous que vous ajoutez la marque d'ordre d'octet UTF-16LE au début du fichier

    chr(255) . chr(254)

Le problème suivant qui apparaît uniquement avec Excel sous OS X (mais pas Windows) sera lors de l'affichage d'un fichier CSV avec des valeurs séparées par des virgules, Excel ne rendra les lignes qu'avec une ligne et tout le texte avec les virgules dans la première ligne.

Le moyen d'éviter cela est d'utiliser des tabulations comme valeur séparée.

J'ai utilisé cette fonction à partir des commentaires PHP (en utilisant les onglets "\ t" au lieu des virgules) et cela fonctionnait parfaitement sur OS X et Windows Excel.

Notez que pour résoudre un problème avec une colonne vide à la fin d'une ligne, j'ai dû changer la ligne de code qui dit:

    $field_cnt = count($fields);

à

    $field_cnt = count($fields)-1;

Comme le disent certains des autres commentaires sur cette page, d'autres applications de feuille de calcul comme OpenOffice Calc, les propres chiffres d'Apple et la feuille de calcul de Google Doc n'ont aucun problème avec les fichiers UTF-8 avec des virgules.

Consultez le tableau de cette question pour savoir ce qui fonctionne et ne fonctionne pas pour les fichiers CSV Unicode dans Excel


En passant, je pourrais ajouter que si vous utilisez Composer , vous devriez jeter un œil à l'ajout League\Csvde vos besoins. League\Csva une très belle API pour créer des fichiers CSV .

Pour utiliser League\Csvcette méthode de création de fichiers CSV, consultez cet exemple

Tim Groeneveld
la source
1
Appelez-moi stupide, mais je ne peux pas faire fonctionner ça. J'ai converti mes données à l'aide de la fonction mb_convert_encoding et j'ai sorti la nomenclature précédant le contenu du fichier, mais je n'obtiens qu'une seule ligne de caractères chinois lorsque j'ouvre le fichier dans Excel. J'utilise toujours des virgules plutôt que des tabulations pour l'instant, mais cela ne devrait probablement pas causer ce que je vois.
John Rix
@JohnRix c'est étrange. Ce code a littéralement résolu tous les problèmes que j'ai rencontrés avec les fichiers CSV exportés - à l'exception des importateurs qui n'acceptent que des virgules. Pouvez-vous s'il vous plaît m'envoyer un pastebin du code que vous utilisez, ainsi qu'un tableau que vous transformez en CSV et une copie du fichier exporté?
Tim Groeneveld
2
Cette solution a également résolu le problème UTF8 pour moi sur Mac et Windows. J'ai également constaté que l'ajout d'une ligne avec sep=;ou sep=,au fichier CSV indique à Excel comment le CSV est séparé et les colonnes seront créées correctement à nouveau.
Luc Wollants
5
J'ai trouvé que les choses étaient déformées si je commençais la chaîne comme simplement la nomenclature, puis sur une autre ligne, ajoutais, puis sur une "sep=,\n"autre ligne, ajoutais les données. Les choses allaient bien si je faisais tout en une seule ligne ( $csv = chr(255) . chr(254) /* BOM */ . "sep=,\n" . mb_convert_encoding($csv, 'UTF-16LE', 'UTF-8');). Tout va bien maintenant sur Mac. Je n'ai pas Windows pour tester.
tremby
2
La seule chose qui a pleinement fonctionné pour moi. L'incohérence de Microsoft ne cesse de m'étonner. L'enregistrement d'un fichier csv normal utilise "," comme délimiteur mais s'il y a une nomenclature, il enregistre en utilisant "\ t" pour une raison quelconque. Le C en .csv signifie "COMMA" dammit. Ce n'est vraiment pas difficile à faire.
Phil
288

J'ai le même problème (ou similaire).

Dans mon cas, si j'ajoute une nomenclature à la sortie, cela fonctionne:

header('Content-Encoding: UTF-8');
header('Content-type: text/csv; charset=UTF-8');
header('Content-Disposition: attachment; filename=Customers_Export.csv');
echo "\xEF\xBB\xBF"; // UTF-8 BOM

Je pense que c'est un hack assez laid, mais cela a fonctionné pour moi, au moins pour Excel 2007 Windows. Je ne suis pas sûr que cela fonctionnera sur Mac.

Daniel Magliola
la source
10
Moche, mais super utile. Je vous remercie.
abelito
7
Je suis à peu près sûr que cela ne fonctionne pas du tout sous OS X, malheureusement. Je pense qu'il pourrait en fait afficher la nomenclature lorsque vous importez (avertissement: souvenirs
flous
2
C'est correct. Au moins, j'ai essayé de faire précéder une nomenclature, comme dans l'exemple ci-dessus, mais cela montrait en effet des caractères géniaux au début et continuait à afficher les caractères spéciaux de manière incorrecte (testé dans Excel 2011). Cela a semblé fonctionner le mieux pour moi dans tous les paramètres: stackoverflow.com/a/1648671/1005334 (en utilisant PHP).
kasimir
4
Je reçois continuellement des alertes sur cette question parce que, apparemment, beaucoup d'autres personnes trébuchent dessus. J'aimerais pouvoir marquer cela comme correct, car il a été beaucoup voté. Malheureusement, j'ai finalement donné une chance à cette solution (abandonné ce projet il y a longtemps) et cela ne fonctionne pas pour moi dans Excel 2008 pour Mac. Heureux que cela fonctionne pour vous. J'ai voté pour la solution. Mais cela ne résout pas le problème d'Excel pour Mac 2008. Si quelqu'un a de la chance sur le Mac, faites le moi (et apparemment tout le monde ) le savoir.
Ben Saufley
Fonctionne à merveille avec la sortie d'un fichier CSV vers MS Excel Starter 2010. Merci beaucoup!
Jamie Dexter
32

Voici comment je l'ai fait (c'est pour inviter le navigateur à télécharger le fichier csv):

header('Content-Description: File Transfer');
header('Content-Type: application/octet-stream');
header('Content-Disposition: attachment; filename=file.csv');
header('Content-Transfer-Encoding: binary');
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Pragma: public');
echo "\xEF\xBB\xBF"; // UTF-8 BOM
echo $csv_file_content;
exit();

La seule chose qui a résolu le problème d'encodage UTF8 dans l'aperçu CSV lorsque vous appuyez sur la barre d'espace sur Mac ... mais pas dans Excel Mac 2008 ... je ne sais pas pourquoi

Jazzer
la source
1
UTF-8 BOM line of the code save my day with exporting to xls
Mladen Janjetovic
7
Je cherchais un moyen de sortir directement sur le navigateur en tant que utf8, quand je suis tombé sur ce post, voici ma solution avec des crédits pour ce post pour la nomenclature et l'en-tête de transfert binaire. $outstream = fopen( "php://output", 'w' ); fputs( $outstream, "\xEF\xBB\xBF" ); foreach ( $export as $fields ) { fputcsv( $outstream, $fields ); } fclose( $outstream );
fyrye
Typo - supprimez le double )).
sitilge
22

Je viens de traiter le même problème et j'ai trouvé deux solutions.

  1. Utilisez la classe PHPExcel comme suggéré par bpeterson76 .

    • L'utilisation de cette classe génère le fichier le plus largement compatible, j'ai pu générer un fichier à partir de données encodées UTF-8 qui s'ouvraient correctement dans Excel 2008 Mac, Excel 2007 Windows et Google Docs.
    • Le plus gros problème avec l'utilisation de PHPExcel est qu'il est lent et utilise beaucoup de mémoire, ce qui n'est pas un problème pour les fichiers de taille raisonnable, mais si votre fichier Excel / CSV contient des centaines ou des milliers de lignes, cette bibliothèque devient inutilisable .
    • Voici une méthode PHP qui prendra certaines données TSV et produira un fichier Excel dans le navigateur, notez qu'elle utilise Excel5 Writer, ce qui signifie que le fichier doit être compatible avec les anciennes versions d'Excel, mais je n'ai plus accès à aucune, donc je ne peux pas les tester.

      function excel_export($tsv_data, $filename) {
          $export_data = preg_split("/\n/", $tsv_data);
          foreach($export_data as &$row) {
              $row = preg_split("/\t/", $row);
          }
      
          include("includes/PHPExcel.php");
          include('includes/PHPExcel/Writer/Excel5.php');
      
          $objPHPExcel = new PHPExcel();          
      
          $objPHPExcel->setActiveSheetIndex(0);
          $sheet = $objPHPExcel->getActiveSheet();
          $row = '1';
          $col = "A";
          foreach($export_data as $row_cells) {
              if(!is_array($row_cells)) { continue; }
                  foreach($row_cells as $cell) {
                      $sheet->setCellValue($col.$row, $cell);
                      $col++;
                  }
              $row += 1;
              $col = "A";
          }
      
          $objWriter = new PHPExcel_Writer_Excel5($objPHPExcel);
          header('Content-Type: application/vnd.ms-excel');
          header('Content-Disposition: attachment;filename="'.$filename.'.xls"');
          header('Cache-Control: max-age=0');
          $objWriter->save('php://output');   
          exit;   
      }
  2. En raison des problèmes d'efficacité avec PHPExcel, j'ai également dû trouver comment générer un fichier CSV ou TSV compatible UTF-8 et Excel.

    • Le mieux que j'ai pu trouver était un fichier compatible avec Excel 2008 Mac et Excel 2007 PC, mais pas Google Docs, ce qui est assez bon pour mon application.
    • J'ai trouvé la solution ici , spécifiquement, cette réponse , mais vous devriez également lire la réponse acceptée car elle explique le problème.
    • Voici le code PHP que j'ai utilisé, notez que j'utilise des données tsv (tabulations comme délimiteurs au lieu de virgules):

      header ( 'HTTP/1.1 200 OK' );
      header ( 'Date: ' . date ( 'D M j G:i:s T Y' ) );
      header ( 'Last-Modified: ' . date ( 'D M j G:i:s T Y' ) );
      header ( 'Content-Type: application/vnd.ms-excel') ;
      header ( 'Content-Disposition: attachment;filename=export.csv' );
      print chr(255) . chr(254) . mb_convert_encoding($tsv_data, 'UTF-16LE', 'UTF-8');
      exit;
Jasdeep Gosal
la source
Je suis confronté au même problème sur Windows-7 Excel 2007 et j'ai essayé toutes les suggestions mais j'ai échoué :(
PHP Ferrari
La solution UTF-16LE est celle qui a fonctionné. Notez que vous devez formater correctement le tsv, et qu'il doit être tsc, donc délimité par des tabulations et non par des virgules. Voir aussi l'article de Marc ici: stackoverflow.com/a/1648671/1697370
Ellert van Koperen
17

J'avais le même problème et il a été résolu comme ci-dessous:

    header('Content-Encoding: UTF-8');
    header('Content-Type: text/csv; charset=utf-8' );
    header(sprintf( 'Content-Disposition: attachment; filename=my-csv-%s.csv', date( 'dmY-His' ) ) );
    header('Content-Transfer-Encoding: binary');
    header('Expires: 0');
    header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
    header('Pragma: public');

    $df = fopen( 'php://output', 'w' );

    //This line is important:
    fputs( $df, "\xEF\xBB\xBF" ); // UTF-8 BOM !!!!!

    foreach ( $rows as $row ) {
        fputcsv( $df, $row );
    }
    fclose($df);
    exit();
Reza Mamun
la source
13

Excel ne prend pas en charge UTF-8. Vous devez encoder votre texte UTF-8 dans UCS-2LE.

mb_convert_encoding($output, 'UCS-2LE', 'UTF-8');
Léopold Gault
la source
3
Mieux vaut utiliser UTF-16LE comme suggéré ci-dessus, qui couvre tous les caractères existants.
Ellert van Koperen
J'ai remarqué que ce mb_convert_encoding fonctionne correctement et affiche correctement les diacritiques dans mon fichier XLS exporté. J'ai des configurations par défaut de mysql et apache + php pour fonctionner avec utf-8
Junior Mayhé
10

Dans mon cas, la suite fonctionne très bien pour créer un fichier CSV avec des caractères UTF-8 correctement affichés dans Excel.

$out = fopen('php://output', 'w');
fprintf($out, chr(0xEF).chr(0xBB).chr(0xBF));
fputcsv($out, $some_csv_strings);

L'en- 0xEF 0xBB 0xBFtête de nomenclature indiquera à Excel le codage correct.

Codemole
la source
1
big up for you bro <3
Adrien G
fprintf($out, chr(0xEF).chr(0xBB).chr(0xBF));<- c'est exactement ce dont j'avais besoin. Il fonctionne comme un charme.
Alex
8

Pour faire le suivi:

Il semble que le problème vient simplement d'Excel sur Mac. Ce n'est pas comme ça que je génère les fichiers, car même générer des CSV à partir d'Excel les brise. J'enregistre au format CSV, et je réimporte, et tous les personnages sont foirés.

Donc… il ne semble pas y avoir de réponse correcte à cela. Merci pour toutes les suggestions.

Je dirais que d'après tout ce que j'ai lu, la suggestion de @Daniel Magliola concernant la nomenclature serait probablement la meilleure réponse pour un autre ordinateur. Mais cela ne résout toujours pas mon problème.

Ben Saufley
la source
Étant donné que le support UTF8 est incohérent entre Mac et Windows, le meilleur pari est d'utiliser un encodage complètement différent. J'ai trouvé que cp1252 fonctionne généralement bien avec les éléments Microsoft. en.wikipedia.org/wiki/Windows-1252
s29
1
Ben, il y a une bonne réponse à cette question :) Voir la mienne!
Tim Groeneveld
7

Cela fonctionne très bien dans Excel pour Windows et Mac OS.

Correction des problèmes dans Excel qui n'affichaient pas les caractères contenant des signes diacritiques, des lettres cyrilliques, des lettres grecques et des symboles monétaires.

function writeCSV($filename, $headings, $data) {   

    //Use tab as field separator
    $newTab  = "\t";
    $newLine  = "\n";

    $fputcsv  =  count($headings) ? '"'. implode('"'.$newTab.'"', $headings).'"'.$newLine : '';

    // Loop over the * to export
    if (! empty($data)) {
      foreach($data as $item) {
        $fputcsv .= '"'. implode('"'.$newTab.'"', $item).'"'.$newLine;
      }
    }

    //Convert CSV to UTF-16
    $encoded_csv = mb_convert_encoding($fputcsv, 'UTF-16LE', 'UTF-8');

    // Output CSV-specific headers
    header('Set-Cookie: fileDownload=true; path=/'); //This cookie is needed in order to trigger the success window.
    header("Pragma: public");
    header("Expires: 0");
    header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
    header("Cache-Control: private",false);
    header("Content-Type: application/octet-stream");
    header("Content-Disposition: attachment; filename=\"$filename.csv\";" );
    header("Content-Transfer-Encoding: binary");
    header('Content-Length: '. strlen($encoded_csv));
    echo chr(255) . chr(254) . $encoded_csv; //php array convert to csv/excel

    exit;
}
Murali Krishna
la source
cette solution m'a permis de faire fonctionner l'exportation pour Google Sheets également (certains autres ont échoué)
Cafn
6

Le fichier CSV doit inclure une marque d'ordre d'octet.

Ou comme suggéré et solution de contournement, faites-en écho avec le corps HTTP

Cybot
la source
5

Ajouter:

fprintf($file, chr(0xEF).chr(0xBB).chr(0xBF));

Ou:

fprintf($file, "\xEF\xBB\xBF");

Avant d'écrire un contenu dans un fichier CSV.

Exemple:

<?php
$file = fopen( "file.csv", "w");
fprintf( $file, "\xEF\xBB\xBF");
fputcsv( $file, ["english", 122, "বাংলা"]);
fclose($file);
Rejaul
la source
4

Étant donné que l'encodage UTF8 ne fonctionne pas bien avec Excel. Vous pouvez convertir les données en un autre type d'encodage à l'aide de iconv().

par exemple

iconv('UTF-8', 'ISO-8859-1//TRANSLIT', $value),
Abrar A. Shareef
la source
C'était la seule solution qui fonctionnait pour moi avec Excel Mac 2011
Christer Fernstrom
3

Il mb_convert_encodingn'est pas nécessaire de convertir du texte déjà encodé en utf-8 à l'aide de . Ajoutez simplement trois caractères devant le contenu original:

$newContent = chr(239) . chr(187) . chr(191) . $originalContent

Pour moi, cela a résolu le problème des caractères spéciaux dans les fichiers csv.

Rvanlaak
la source
Incroyable; J'ai essayé au moins 10 autres solutions et la seule solution pour moi semble être celle-ci, lorsqu'elle est combinée avec UTF-8 BOM via fputs.
kaarto
2

En enquêtant et en trouvant que UTF-8 ne fonctionne pas bien sur MAC et Windows, j'ai donc essayé avec Windows-1252, il prend bien en charge les deux mais vous devez sélectionner le type d'encodage sur ubuntu. Voici mon code$valueToWrite = mb_convert_encoding($value, 'Windows-1252');

$response->headers->set('Content-Type', $mime . '; charset=Windows-1252');
    $response->headers->set('Pragma', 'public');
    $response->headers->set('Content-Endcoding','Windows-1252');
    $response->headers->set('Cache-Control', 'maxage=1');
    $response->headers->set('Content-Disposition', $dispositionHeader);
    echo "\xEF\xBB\xBF"; // UTF-8 BOM
Ho Ha
la source
2
**This is 100% works fine in excel for both Windows7,8,10 and also All Mac OS.**
//Fix issues in excel that are not displaying characters containing diacritics, cyrillic letters, Greek letter and currency symbols.

function generateCSVFile($filename, $headings, $data) {

    //Use tab as field separator
    $newTab  = "\t";
    $newLine  = "\n";

    $fputcsv  =  count($headings) ? '"'. implode('"'.$newTab.'"', $headings).'"'.$newLine : '';

    // Loop over the * to export
    if (! empty($data)) {
      foreach($data as $item) {
        $fputcsv .= '"'. implode('"'.$newTab.'"', $item).'"'.$newLine;
      }
    }

    //Convert CSV to UTF-16
    $encoded_csv = mb_convert_encoding($fputcsv, 'UTF-16LE', 'UTF-8');

    // Output CSV-specific headers
    header('Set-Cookie: fileDownload=true; path=/'); //This cookie is needed in order to trigger the success window.
    header("Pragma: public");
    header("Expires: 0");
    header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
    header("Cache-Control: private",false);
    header("Content-Type: application/octet-stream");
    header("Content-Disposition: attachment; filename=\"$filename.csv\";" );
    header("Content-Transfer-Encoding: binary");
    header('Content-Length: '. strlen($encoded_csv));
    echo chr(255) . chr(254) . $encoded_csv; //php array convert to csv/excel
    exit;
}
Sagar72427
la source
2
En général, les réponses sont beaucoup plus utiles si elles incluent une explication de ce que le code est censé faire et pourquoi cela résout le problème sans en présenter d'autres.
Tim Diekmann
1

Que diriez-vous simplement de sortir pour Excel lui-même? C'est une excellente classe qui vous permet de générer des fichiers XLS côté serveur. Je l'utilise fréquemment pour les clients qui ne peuvent pas "comprendre" les csv et qui n'ont jusqu'à présent jamais eu de plainte. Il permet également un formatage supplémentaire (ombrage, hauteur de ligne, calculs, etc.) que csv ne fera jamais.

bpeterson76
la source
Sachez que phpexcel a des problèmes avec de grandes quantités de données.
Ellert van Koperen
1

vous pouvez convertir votre chaîne CSV avec iconv . par exemple:

$csvString = "Möckmühl;in Möckmühl ist die Hölle los\n";
file_put_contents('path/newTest.csv',iconv("UTF-8", "ISO-8859-1//TRANSLIT",$csvString) );
foued611
la source
Grands exemples de textes;)
ngeek
1

Vous devez utiliser l'encodage "Windows-1252".

header('Content-Encoding: Windows-1252');
header('Content-type: text/csv; charset=Windows-1252');
header("Content-Disposition: attachment; filename={$filename}");

Vous devez peut-être convertir vos chaînes:

private function convertToWindowsCharset($string) {
  $encoding = mb_detect_encoding($string);

  return iconv($encoding, "Windows-1252", $string);
}
roNn23
la source
1

Vous pouvez ajouter les 3 octets au fichier avant d'exporter, cela fonctionne pour moi. Avant de faire ce système ne fonctionne que sous Windows et HP -UX mais a échoué sous Linux.

FileOutputStream fStream = new FileOutputStream( f );
final byte[] bom = new byte[] { (byte) 0xEF, (byte) 0xBB, (byte) 0xBF };
OutputStreamWriter writer = new OutputStreamWriter( fStream, "UTF8" );
fStream.write( bom );

Avoir une nomenclature UTF-8 (3 octets, hex EF BB BF) au début du fichier. Sinon, Excel interprétera les données selon le codage par défaut de vos paramètres régionaux (par exemple, cp1252) au lieu de utf-8

Générer un fichier CSV pour Excel, comment avoir une nouvelle ligne dans une valeur

Cherry Yap
la source
1

Je suis sur Mac, dans mon cas, je devais juste spécifier le séparateur avec "sep=;\n"et encoder le fichier en UTF-16LE comme ceci:

$data = "sep=;\n" .mb_convert_encoding($data, 'UTF-16LE', 'UTF-8');
Sébastien Horin
la source
1

Pour moi, aucune des solutions ci-dessus n'a fonctionné. Voici ce que j'ai fait pour résoudre le problème: modifiez la valeur à l'aide de cette fonction dans le code PHP:

$value = utf8_encode($value);

Cette valeur de sortie correctement dans une feuille Excel.

Barani r
la source
0

J'ai eu ce même problème lorsque j'avais une routine Excel VBA qui importait des données. Étant donné que CSV est un format de texte brut, je travaillais à ce problème en ouvrant par programme les données dans un simple éditeur de fichiers comme wordpad, et en les réenregistrant en tant que texte Unicode, ou en les copiant dans le presse-papiers à partir de là et en les collant dans Excel. Si Excel n'analyse pas automatiquement le CSV en cellules, cela est facilement résolu en utilisant la fonction intégrée "Texte en colonnes".

Alain
la source
J'ai essayé ça! Mais il est déjà codé en tant que texte Unicode… l'enregistrer en tant que texte Unicode ne change rien. Comment l'enregistrer sous forme de texte brut sans qu'il n'interprète mal tous les caractères spéciaux?
Ben Saufley
Je pense qu'en "le sauvegardant en tant que texte Unicode", Alain pourrait vouloir dire "UTF-16LE". Windows utilise souvent (malheureusement) "Unicode" pour faire référence à tort à UTF-16LE ou UTF-16LE avec une nomenclature en tête. La boîte de dialogue Fichier -> Enregistrer du Bloc-notes utilise "Unicode" de cette manière.
Thanatos
0

Le problème se produit-il toujours lorsque vous l'enregistrez en tant que fichier .txt et que vous l'ouvrez dans Excel avec une virgule comme délimiteur?

Le problème n'est peut-être pas du tout l'encodage, il se peut simplement que le fichier ne soit pas un CSV parfait selon les normes Excel.

Alain
la source
Autant que je sache, le formatage CSV est correct. Je peux créer un CSV "parfait" dans TextEdit, sans problème, ou même renommer un txt en csv, pour ne rien manquer de secret - les CSV ne sont que des fichiers texte. De plus, la mise en forme est parfaite dans Excel, ce ne sont que les caractères spéciaux qui cassent. Mais au cas où, j'ai essayé votre suggestion, et cela pose malheureusement les mêmes problèmes.
Ben Saufley
Du département "WTF pensaient-ils": sachez que, selon Microsoft, le séparateur de champ correct dépend des paramètres régionaux. Un fichier `` séparé par des virgules '' peut donc exiger que les champs soient en fait séparés par des points-virgules dans certains paramètres régionaux - et vous ne pouvez rien faire d'autre que suggérer OpenOffice
djn
c'est assez fou - malheureusement je n'ai pas de difficulté à délimiter correctement les champs. J'ai juste des problèmes avec ces caractères spéciaux.
Ben Saufley
0

Ce message est assez ancien, mais après des heures d'essais, je veux partager ma solution… peut-être que cela aide quelqu'un qui a affaire à Excel, Mac et CSV et à trébucher sur cette menace. Je génère un csv dynamiquement en tant que sortie d'une base de données avec les utilisateurs Excel à l'esprit. (UTF-8 avec BOM)

J'ai essayé beaucoup d'iconv mais je n'ai pas pu faire fonctionner les trémas allemands sous Mac Excel 2004. Une solution: PHPExcel. C'est super mais pour mon projet un peu trop. Ce qui fonctionne pour moi, c'est de créer le fichier csv et de convertir ce fichier csv en xls avec ce PHPsnippet: csv2xls . le résultat xls fonctionne avec des trémas allemands excellents (ä, ö, Ü, ...).

t Réserver
la source
0

Je viens d'essayer ces en-têtes et j'ai Excel 2013 sur un PC Windows 7 pour importer correctement le fichier CSV avec des caractères spéciaux. La marque d'ordre d'octet (BOM) était la clé finale qui l'a fait fonctionner.

    en-tête ('Content-Encoding: UTF-8');
    header ('Content-type: text / csv; charset = UTF-8');
    header ("Content-disposition: pièce jointe; filename = filename.csv");
    en-tête ("Pragma: public");
    en-tête ("Expire: 0");
    echo "\ xEF \ xBB \ xBF"; // Nomenclature UTF-8

Brian
la source
Oui, c'est correct, cela fonctionnera correctement dans Excel pour Windows, mais comme expliqué dans ma réponse, cela ne fonctionnera pas sur Excel pour OS X.
Tim Groeneveld
0

Sinon, vous pouvez:

header("Content-type: application/x-download");
header("Content-Transfer-Encoding: binary");
header("Content-disposition: attachment; filename=".$fileName."");
header("Cache-control: private");

echo utf8_decode($output);
user3519396
la source
0

Solution FACILE pour Mac Excel 2008: J'ai eu du mal avec cela tellement de fois, mais voici ma solution simple: ouvrez le fichier .csv dans Textwrangler qui devrait ouvrir correctement vos caractères UTF-8. Maintenant, dans la barre d'état inférieure, changez le format de fichier de "Unicode (UTF-8)" à "Western (ISO Latin 1)" et enregistrez le fichier. Maintenant, allez sur votre Mac Excel 2008 et sélectionnez Fichier> Importer> Sélectionnez csv> Trouvez votre fichier> dans Origine du fichier, sélectionnez "Windows (ANSI)" et voilà, les caractères UTF-8 s'affichent correctement. Au moins ça le fait pour moi ...

Poul
la source
0

J'utilise ça et ça marche

header('Content-Description: File Transfer');
header('Content-Type: text/csv; charset=UTF-16LE');
header('Content-Disposition: attachment; filename=file.csv');
header('Content-Transfer-Encoding: binary');
header('Expires: 0');
header('Cache-Control: must-revalidate, post-check=0, pre-check=0');
header('Pragma: public');
// output headers so that the file is downloaded rather than displayed
// create a file pointer connected to the output stream
$output = fopen('php://output', 'w');
fputs( $output, "\xEF\xBB\xBF" );
// output the column headings
fputcsv($output, array('Thông tin khách hàng đăng ký'));
// fetch the data
$setutf8 = "SET NAMES utf8";
$q = $conn->query($setutf8);
$setutf8c = "SET character_set_results = 'utf8', character_set_client =
'utf8', character_set_connection = 'utf8', character_set_database = 'utf8',
character_set_server = 'utf8'";
$qc = $conn->query($setutf8c);
$setutf9 = "SET CHARACTER SET utf8";
$q1 = $conn->query($setutf9);
$setutf7 = "SET COLLATION_CONNECTION = 'utf8_general_ci'";
$q2 = $conn->query($setutf7);
$sql = "SELECT id, name, email FROM myguests";
$rows = $conn->query($sql);
$arr1= array();
if ($rows->num_rows > 0) {
// output data of each row
while($row = $rows->fetch_assoc()) {
    $rcontent = " Name: " . $row["name"]. " - Email: " . $row["email"];  
    $arr1[]["title"] =  $rcontent;
}
} else {
     echo "0 results";
}
$conn->close();
// loop over the rows, outputting them
foreach($arr1 as $result1):
   fputcsv($output, $result1);
endforeach;
BoRnbeBaD
la source
0

#output un CSV UTF-8 en PHP qu'Excel lira correctement.

//Use tab as field separator   
$sep  = "\t";  
$eol  = "\n";    
$fputcsv  =  count($headings) ? '"'. implode('"'.$sep.'"', $headings).'"'.$eol : '';
Murali Krishna
la source
Une réponse par personne suffit. À l'avenir, rappelez-vous que vous pouvez ajouter des informations à votre réponse à tout moment, vous n'avez pas besoin de créer 2
RiggsFolly
-1
//convert UTF-8 file without BOM to UTF-16LE for excel on mac
$fileUtf8String = file_get_contents("file.ext");
file_put_contents("file.ext", "\xFF\xFE" . mb_convert_encoding($fileUtf8String, "UTF-16LE", "UTF-8"));
b3wii
la source
Cette question ne demande pas comment convertir, elle demande comment sortir. La partie pertinente de cette contribution, sortie en UTF-16, est déjà apportée dans la réponse sélectionnée .
Ben Saufley
@BenSaufley Eh bien mais ça résout le problème de la question avec 2 simples lignes de code
b3wii
La question est déjà résolue et expliquée de manière plus approfondie également.
Ben Saufley