-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathlens-input-csv.html
162 lines (126 loc) · 4.44 KB
/
lens-input-csv.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
<link rel="import" href="../polymer/polymer.html">
<link rel="import" href="../core-input/core-input.html">
<link rel="import" href="../core-icons/core-icons.html">
<!--
CSV Data loader component to load and parse online CSV files. If the API returns JSON with a header followed by an array of results, the results become the <code>output</code>.
##### Example
<lens-input-csv url="https://data.cityofnewyork.us/api/views/8586-3zfm/rows.csv?accessType=DOWNLOAD"></lens-input-csv>
@element lens-input-csv
@group Lenses input component
@blurb CSV Data loader component to load and parse online CSV files.
@status alpha
@homepage http://lenses.github.io/lens-input-csv
-->
<polymer-element name="lens-input-csv" attributes="url output">
<template>
<style>
label {
color: #2fa3af;
}
core-input {
border: 1px solid #eee;
padding: 2px;
}
</style>
<div class="lens-container lens-input">
<label>URL</label><input is="core-input" value="{{url}}" placeHolder="CSV file URL">
<span id="upload" on-click="{{uDialog}}">
<core-icon icon="file-upload"></core-icon>
<label>Upload a File</label><input is="core-input" id="uploadInput" type="file" hidden value="">
</span>
<!-- <div><label class="label">Num Records: </label><div class="data">{{output.length}}</div></div> -->
</div>
</template>
<script src="../d3/d3.min.js"></script>
<script>
Polymer('lens-input-csv', {
/**
* URL path to CSV file.
* If the file is hosted online,
* the url should begin with <code>http://</code>, <code>https://</code> or <code>ftp://</code>.
*
* @property url
* @type String
* @default ''
*/
url: '',
/**
* Output data
*
* @property output
* @type Object
* @default undefined
*/
output: undefined,
_CORS_PROXY: 'http://lenses-cors.herokuapp.com/',
ready: function() {
var self = this;
console.log('de csv');
console.log(this.url);
// setup the upload input
self.$.uploadInput.onchange = function(e) {
self._handleFileSelect(e, self);
};
},
urlChanged: function() {
var self = this;
var corsurl = self.url.replace(/(ftp|http|https):\/\//, self._CORS_PROXY);
d3.csv(corsurl, function(d) {
console.log(d);
self._setOutput(d);
}.bind(this));
},
// FILE UPLOAD
// click on hidden <input> element to open file select dialog
uDialog: function(e) {
var self = this;
self.$.uploadInput.click();
},
// get selected file from <input id="uploadInput">
_handleFileSelect: function(e, scope) {
var self = scope;
var file = self.$.uploadInput.files[0];
// check mime type
var mimes = ['application/vnd.ms-excel','text/plain','text/csv','text/tsv']
var okMime = mimes.some(function(mime) {
return file.type === mime;
});
if (!okMime) {
alert('Unable to upload: ' + file.name + ' is not a CSV file');
return;
}
// create a new reader to parse the file
var reader = new FileReader();
reader.onload = function(e) {
self._stringToCSV(e, self);
}
reader.onerror = function(e) {
console.log('error loading file: ' + e);
}
reader.readAsText(file);
},
_stringToCSV: function(e, scope) {
var self = scope;
var csvString = e.target.result.trim();
var inputRows = csvString.split('\n');
// total number of rows = inputRows - header
var numRows = inputRows.length - 1;
var newOutput = [];
// parses one row at a time...
d3.csv.parse(csvString, function(d) {
newOutput.push(d);
// ...so only setOutput when it has reached full size
if (newOutput.length === numRows) {
self._setOutput(newOutput);
}
}.bind(self));
},
// change output and fire lens-output-changed
_setOutput: function(data) {
var self = this;
self.output = data;
self.fire('lens-output-changed', self);
}
});
</script>
</polymer-element>