Comment puis-je exporter des tableaux vers Excel à partir d'une page Web. Je veux que l'exportation contienne toute la mise en forme et les couleurs.
<td style="background-color: ...
Comment puis-je exporter des tableaux vers Excel à partir d'une page Web. Je veux que l'exportation contienne toute la mise en forme et les couleurs.
<td style="background-color: ...
Réponses:
De loin, l'exportation la plus propre et la plus simple des tableaux vers Excel est le plugin Jquery DataTables Table Tools. Vous obtenez une grille qui trie, filtre, ordonne et page vos données, et avec seulement quelques lignes de code supplémentaires et deux petits fichiers inclus, vous obtenez une exportation vers Excel, PDF, CSV, vers le presse-papiers et vers l'imprimante.
C'est tout le code requis:
$(document).ready( function () {
$('#example').dataTable( {
"sDom": 'T<"clear">lfrtip',
"oTableTools": {
"sSwfPath": "/swf/copy_cvs_xls_pdf.swf"
}
} );
} );
Donc, rapide à déployer, aucune limitation de navigateur, aucun langage côté serveur requis et surtout très FACILE à comprendre. C'est gagnant-gagnant. La seule chose sur laquelle il a des limites, cependant, est le formatage strict des colonnes.
Si le formatage et les couleurs sont des facteurs de rupture absolus, la seule méthode de navigation croisée à 100% fiable que j'ai trouvée consiste à utiliser un langage côté serveur pour traiter les fichiers Excel appropriés à partir de votre code. Ma solution de choix est PHPExcel C'est la seule que j'ai trouvée jusqu'à présent qui gère positivement l'exportation avec mise en forme vers une version MODERNE d'Excel à partir de n'importe quel navigateur lorsque vous ne lui donnez que du HTML. Permettez-moi de clarifier cependant, ce n'est certainement pas aussi facile que la première solution, et c'est aussi un peu une corvée de ressources. Cependant, du côté positif, il peut également sortir directement au format PDF. Et, une fois que vous l'avez configuré, cela fonctionne, à chaque fois.
MISE À JOUR - 15 septembre 2016: TableTools a été abandonné au profit d'un nouveau plugin appelé " boutons ". Ces outils remplissent les mêmes fonctions que l'ancienne extension TableTools, mais sont BEAUCOUP plus faciles à installer et utilisent des téléchargements HTML5 pour les navigateurs modernes, avec la possibilité de revenir au téléchargement Flash d'origine pour les navigateurs qui ne prennent pas en charge la norme HTML5. Comme vous pouvez le voir dans les nombreux commentaires depuis que j'ai publié cette réponse en 2011, la principale faiblesse de TableTools a été corrigée. Je ne peux toujours pas recommander suffisamment DataTables pour gérer simplement de grandes quantités de données, à la fois pour le développeur et l'utilisateur.
Il y a longtemps, j'ai découvert qu'Excel ouvrirait un fichier HTML avec un tableau si nous l'envoyions avec le type de contenu Excel. Considérez le document ci-dessus:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>Java Friends</title>
</head>
<body>
<table style="font-weight: bold">
<tr style="background-color:red"><td>a</td><td>b</td></tr>
<tr><td>1</td><td>2</td></tr>
</table>
</body>
</html>
J'ai couru le bookmarklet suivant dessus:
javascript:window.open('data:application/vnd.ms-excel,'+document.documentElement.innerHTML);
et en fait je l'ai téléchargé sous forme de fichier Excel. Cependant , je n'ai pas obtenu le résultat attendu - le fichier était ouvert dans OpenOffice.org Writer. C'est mon problème: je n'ai pas Excel dans cette machine donc je ne peux pas mieux l'essayer. De plus, cette astuce a fonctionné il y a plus ou moins six ans avec des navigateurs plus anciens et une ancienne version de MS Office, donc je ne peux vraiment pas dire si cela fonctionnera aujourd'hui.
Quoi qu'il en soit, dans le document ci-dessus, j'ai ajouté un bouton qui téléchargerait l'intégralité du document sous forme de fichier Excel, en théorie:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>Java Friends</title>
</head>
<body>
<table style="font-weight: bold">
<tr style="background-color:red"><td>a</td><td>b</td></tr>
<tr><td>1</td><td>2</td></tr>
<tr>
<td colspan="2">
<button onclick="window.open('data:application/vnd.ms-excel,'+document.documentElement.innerHTML);">
Get as Excel spreadsheet
</button>
</td>
</tr>
</table>
</body>
</html>
Enregistrez-le dans un fichier et cliquez sur le bouton. J'adore savoir si cela a fonctionné ou non, je vous demande de commentaires , même pour dire que cela n'a pas fonctionné.
document.getElementById('id').innerHTML
pour saisir sélectivement la table uniquement, sinon tout votre contenu est exporté vers la feuille de calcul. Ne fonctionne pas dans l'ancien IE cependant, ouvre juste une nouvelle fenêtre avec tout le code HTML dans le titre
Il est possible d'utiliser l'ancien format XML Excel 2003 (avant OpenXML) pour créer une chaîne contenant le XML souhaité, puis côté client, vous pouvez utiliser un URI de données pour ouvrir le fichier en utilisant le type mime XSL, ou envoyer le fichier au client en utilisant le type MIME Excel "Content-Type: application / vnd.ms-excel" du côté serveur.
<script type="text/javascript">
var worksheet_template = '<?xml version="1.0"?><ss:Workbook xmlns:ss="urn:schemas-microsoft-com:office:spreadsheet">'+
'<ss:Styles><ss:Style ss:ID="1"><ss:Font ss:Bold="1"/></ss:Style></ss:Styles><ss:Worksheet ss:Name="Sheet1">'+
'<ss:Table>{{ROWS}}</ss:Table></ss:Worksheet></ss:Workbook>';
var row_template = '<ss:Row ss:StyleID="1"><ss:Cell><ss:Data ss:Type="String">{{name}}</ss:Data></ss:Cell></ss:Row>';
</script>
<script type="text/javascript">
var rows = document.getElementById("my-table").getElementsByTagName('tr'),
row_data = '';
for (var i = 0, length = rows.length; i < length; ++i) {
row_data += row_template.replace('{{name}}', rows[i].getElementsByTagName('td')[0].innerHTML);
}
</script>
Une fois les informations collectées, créez la chaîne finale et ouvrez une nouvelle fenêtre en utilisant l'URI de données
<script type="text/javascript"> var worksheet = worksheet_template.replace('{{ROWS}}', row_data);
window.open('data:application/vnd.ms-excel,'+worksheet); </script>
Il est à noter que les navigateurs plus anciens ne prennent pas en charge le schéma URI de données, vous devrez peut-être produire le côté serveur de fichiers pour les navigateurs qui ne le prennent pas en charge.
Vous devrez peut-être également effectuer un encodage en base64 sur le contenu de l'URI de données, ce qui peut nécessiter une bibliothèque js , ainsi que l'ajout de la chaîne '; base64' après le type mime dans l'URI de données.
Excel a une fonctionnalité peu connue appelée "requêtes Web" qui vous permet de récupérer des données de presque toutes les pages Web sans programmation supplémentaire.
Une requête Web exécute essentiellement une requête HTTP directement à partir d'Excel et copie une partie ou la totalité des données reçues (et éventuellement le formatage) dans la feuille de calcul.
Après avoir défini la requête Web, vous pouvez l'actualiser à tout moment sans même quitter Excel. Vous n'avez donc pas à "exporter" les données et à les enregistrer dans un fichier - vous préférez actualiser les données comme à partir d'une base de données.
Vous pouvez même utiliser les paramètres d'URL en demandant à Excel de vous demander certains critères de filtre, etc.
Cependant, les inconvénients que j'ai remarqués jusqu'à présent sont:
Voici une question sur la façon de créer des requêtes Web dans Excel. Il renvoie à un site d'aide Microsoft sur la procédure d'obtention de données externes à partir d'une page Web
Ceci est un php mais vous pourrez peut-être le changer en javascript:
<?php>
$colgroup = str_repeat("<col width=86>",5);
$data = "";
$time = date("M d, y g:ia");
$excel = "<html xmlns:o=\"urn:schemas-microsoft-com:office:office\" xmlns:x=\"urn:schemas-microsoft-com:office:excel\" xmlns=\"http://www.w3.org/TR/REC-html40\">
<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">
<html>
<head>
<meta http-equiv=\"Content-type\" content=\"text/html;charset=utf-8\" />
<style id=\"Classeur1_16681_Styles\">
.xl4566 {
color: red;
}
</style>
</head>
<body>
<div id=\"Classeur1_16681\" align=center x:publishsource=\"Excel\">
<table x:str border=0 cellpadding=0 cellspacing=0 style=\"border-collapse: collapse\">
<colgroup>$colgroup</colgroup>
<tr><td class=xl2216681><b>Col1</b></td><td class=xl2216681><b>Col2</b></td><td class=xl2216681 ><b>Col3</b></td><td class=xl2216681 ><b>Col4</b></td><td class=xl2216681 ><b>Col5</b></td></tr>
<tr><td class=xl4566>1</td><td>2</td><td>3</td><td>4</td><td>5</td></tr>
</table>
</div>
</body>
</html>";
$fname = "Export".time().".xls";
$file = fopen($fname,"w+");
fwrite($file,$excel);
fclose($file);
header('Content-Type: application/vnd.ms-excel');
header('Content-Disposition: attachment; filename="'.basename($fname).'"');
readfile($fname);
unlink($fname); ?>
Tout d'abord, je ne recommanderais pas d' essayer d'exporter Html et j'espère que l'instance d'Excel de l'utilisateur la récupérera. Mon expérience que cette solution est lourde de problèmes, y compris des incompatibilités avec les clients Macintosh et jette une erreur à l'utilisateur que le fichier en question n'est pas du format spécifié. La solution la plus fiable et la plus conviviale est une solution côté serveur où vous utilisez une bibliothèque pour créer un fichier Excel réel et le renvoyer à l'utilisateur. La meilleure solution suivante et la solution la plus universelle serait d'utiliser le format Open XML. J'ai rencontré quelques rares problèmes de compatibilité avec les anciennes versions d'Excel, mais dans l'ensemble, cela devrait vous donner une solution qui fonctionnera sur n'importe quelle version d'Excel, y compris les Mac.
mozilla prend toujours en charge les URI de base 64. Cela vous permet de composer dynamiquement le contenu binaire en utilisant javascript:
<a href="data:application/vnd.ms-excel<base64 encoded binary excel content here>"> download xls</a>
si votre fichier excel n'est pas très sophistiqué (pas de diagrammes, de formules, de macros) vous pouvez creuser dans le format et composer des octets pour votre fichier, puis les encoder avec base64 et les mettre dans le href
se référer à https://developer.mozilla.org/en/data_URIs
C'est en fait plus simple que vous ne le pensez: "Il suffit" de copier le tableau HTML (c'est-à-dire: le code HTML du tableau) dans le presse-papiers. Excel sait comment décoder les tableaux HTML; il essaiera même de préserver les attributs.
La partie la plus difficile est de «copier le tableau dans le presse-papiers» puisqu'il n'y a pas de moyen standard d'accéder au presse-papiers à partir de JavaScript. Voir ce billet de blog: Accéder au presse-papiers système avec JavaScript - Un Saint Graal?
Maintenant, tout ce dont vous avez besoin est le tableau au format HTML. Je suggère jQuery et la méthode html () .
Ce code est IE uniquement, il n'est donc utile que dans les situations où vous savez que tous vos utilisateurs utiliseront IE (comme, par exemple, dans certains environnements d'entreprise.)
<script Language="javascript">
function ExportHTMLTableToExcel()
{
var thisTable = document.getElementById("tbl").innerHTML;
window.clipboardData.setData("Text", thisTable);
var objExcel = new ActiveXObject ("Excel.Application");
objExcel.visible = true;
var objWorkbook = objExcel.Workbooks.Add;
var objWorksheet = objWorkbook.Worksheets(1);
objWorksheet.Paste;
}
</script>
Hypothèses:
URL donnée
la conversion doit être effectuée côté client
les systèmes sont Windows, Mac et Linux
Solution pour Windows:
code python qui ouvre la fenêtre ie et y a accès: la variableeurl contient l'url ('http: //')
ie = Dispatch("InternetExplorer.Application")
ie.Visible = 1
ie.Navigate(theurl)
Remarque: si la page n'est pas accessible directement, mais que vous vous connectez, vous devrez gérer cela en entrant les données du formulaire et en émulant les actions de l'utilisateur avec python
voici l'exemple
from win32com.client import Dispatch
ie.Document.all('username').value=usr
ie.Document.all('password').value=psw
de la même manière pour la récupération des données de la page Web Supposons que l'élément avec l'identifiant 'el1' contienne les données. récupérer le texte de l'élément dans la variable
el1 = ie.Document.all('el1').value
alors, lorsque les données sont dans la variable python, vous pouvez ouvrir l'écran Excel de la même manière en utilisant python:
from win32com.client import Dispatch
xlApp = Dispatch("Excel.Application")
xlWb = xlApp.Workbooks.Open("Read.xls")
xlSht = xlWb.WorkSheets(1)
xlSht.Cells(row, col).Value = el1
Solution pour Mac:
seulement le conseil: utilisez AppleScript - il a une API simple et similaire à win32com.client Dispatch
Solution pour Linux:
java.
une simple recherche Google a révélé ceci:
Si les données sont en fait une page HTML et n'ont PAS été créées par ASP, PHP ou un autre langage de script, et que vous utilisez Internet Explorer 6 et que Excel est installé sur votre ordinateur, cliquez simplement avec le bouton droit sur la page et regardez à travers le menu. Vous devriez voir «Exporter vers Microsoft Excel». Si toutes ces conditions sont remplies, cliquez sur l'élément de menu et après quelques invites, il sera importé dans Excel.
si vous ne pouvez pas faire cela, il donne une autre méthode "glisser-déposer":
Et maintenant, il existe un meilleur moyen.
SDK OpenXML pour JavaScript.
Il existe deux façons pratiques de le faire automatiquement, alors qu'une seule solution peut être utilisée dans tous les navigateurs. Tout d'abord, vous devez utiliser la spécification open xml pour créer la feuille Excel. Il existe des plugins gratuits de Microsoft qui rendent ce format également disponible pour les anciennes versions de bureau. Le xml ouvert est standard depuis Office 2007. Les deux manières sont évidentes du côté serveur ou côté client.
L'implémentation côté client utilise une nouvelle norme de CSS qui vous permet de stocker des données au lieu de simplement l'URL des données. C'est une excellente approche car vous n'avez besoin d'aucun appel de serveur, juste des données et du javascript. L'inconvénient est que Microsoft ne prend pas en charge toutes ses parties dans les versions actuelles d'IE (je ne sais pas pour IE9). Microsoft limite les données à une image mais nous aurons besoin d'un document. Dans Firefox, cela fonctionne très bien. Pour moi, l'IE était le point mortel.
L'autre moyen consiste à utiliser une implémentation côté serveur. Il devrait y avoir beaucoup d'implémentations d'Open XML pour toutes les langues. Vous avez juste besoin d'en attraper un. Dans la plupart des cas, ce sera le moyen le plus simple de modifier un modèle de vue pour obtenir un document, mais vous pouvez certainement renvoyer toutes les données du côté client vers le serveur et faire de même.
function normalexport() {
try {
var i;
var j;
var mycell;
var tableID = "tblInnerHTML";
var drop = document.getElementById('<%= ddl_sections.ClientID %>');
var objXL = new ActiveXObject("Excel.Application");
var objWB = objXL.Workbooks.Add();
var objWS = objWB.ActiveSheet;
var str = filterNum(drop.options[drop.selectedIndex].text);
objWB.worksheets("Sheet1").activate; //activate dirst worksheet
var XlSheet = objWB.activeSheet; //activate sheet
XlSheet.Name = str; //rename
for (i = 0; i < document.getElementById("ctl00_ContentPlaceHolder1_1").rows.length - 1; i++) {
for (j = 0; j < document.getElementById("ctl00_ContentPlaceHolder1_1").rows(i).cells.length; j++) {
mycell = document.getElementById("ctl00_ContentPlaceHolder1_1").rows(i).cells(j);
objWS.Cells(i + 1, j + 1).Value = mycell.innerText;
// objWS.Cells(i + 1, j + 1).style.backgroundColor = mycell.style.backgroundColor;
}
}
objWS.Range("A1", "L1").Font.Bold = true;
// objWS.Range("A1", "L1").Font.ColorIndex = 2;
// objWS.Range("A1", "Z1").Interior.ColorIndex = 47;
objWS.Range("A1", "Z1").EntireColumn.AutoFit();
//objWS.Range("C1", "C1").ColumnWidth = 50;
objXL.Visible = true;
} catch (err) {
alert("Error. Scripting for ActiveX might be disabled")
return
}
idTmr = window.setInterval("Cleanup();", 1);
}
function filterNum(str) {
return str.replace(/[ / ]/g, '');
}