formstream 0.0.6 → 1.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/History.md +25 -0
- package/README.md +42 -80
- package/lib/formstream.js +132 -96
- package/package.json +22 -17
- package/.npmignore +0 -7
- package/LICENSE.txt +0 -21
- package/index.js +0 -1
package/History.md
CHANGED
|
@@ -1,4 +1,29 @@
|
|
|
1
1
|
|
|
2
|
+
1.1.0 / 2016-12-19
|
|
3
|
+
==================
|
|
4
|
+
|
|
5
|
+
* deps: upgrade mime to latest version (#9)
|
|
6
|
+
|
|
7
|
+
1.0.0 / 2014-11-04
|
|
8
|
+
==================
|
|
9
|
+
|
|
10
|
+
* fix(field): support stream.field(String, Number)
|
|
11
|
+
* chore: fix links
|
|
12
|
+
* chore: use npm scripts instead of Makefile
|
|
13
|
+
* fix test case on node@0.8
|
|
14
|
+
|
|
15
|
+
0.0.8 / 2014-01-17
|
|
16
|
+
==================
|
|
17
|
+
|
|
18
|
+
* destroy source stream when formstream destroy()
|
|
19
|
+
* add more test cases
|
|
20
|
+
|
|
21
|
+
0.0.7 / 2013-07-25
|
|
22
|
+
==================
|
|
23
|
+
|
|
24
|
+
* feature: always try to infer `Content-Length` (@xingrz)
|
|
25
|
+
* doc improve
|
|
26
|
+
|
|
2
27
|
0.0.6 / 2013-07-15
|
|
3
28
|
==================
|
|
4
29
|
|
package/README.md
CHANGED
|
@@ -1,7 +1,21 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
![
|
|
1
|
+
# formstream
|
|
2
|
+
|
|
3
|
+
[![NPM version][npm-image]][npm-url]
|
|
4
|
+
[![build status][travis-image]][travis-url]
|
|
5
|
+
[![Test coverage][coveralls-image]][coveralls-url]
|
|
6
|
+
[![David deps][david-image]][david-url]
|
|
7
|
+
[![npm download][download-image]][download-url]
|
|
8
|
+
|
|
9
|
+
[npm-image]: https://img.shields.io/npm/v/formstream.svg?style=flat-square
|
|
10
|
+
[npm-url]: https://npmjs.org/package/formstream
|
|
11
|
+
[travis-image]: https://img.shields.io/travis/node-modules/formstream.svg?style=flat-square
|
|
12
|
+
[travis-url]: https://travis-ci.org/node-modules/formstream
|
|
13
|
+
[coveralls-image]: https://img.shields.io/coveralls/node-modules/formstream.svg?style=flat-square
|
|
14
|
+
[coveralls-url]: https://coveralls.io/r/node-modules/formstream?branch=master
|
|
15
|
+
[david-image]: https://img.shields.io/david/node-modules/formstream.svg?style=flat-square
|
|
16
|
+
[david-url]: https://david-dm.org/node-modules/formstream
|
|
17
|
+
[download-image]: https://img.shields.io/npm/dm/formstream.svg?style=flat-square
|
|
18
|
+
[download-url]: https://npmjs.org/package/formstream
|
|
5
19
|
|
|
6
20
|
A [multipart/form-data](http://tools.ietf.org/html/rfc2388) encoded stream, helper for file upload.
|
|
7
21
|
|
|
@@ -45,49 +59,21 @@ var req = http.request(options, function (res) {
|
|
|
45
59
|
form.pipe(req);
|
|
46
60
|
```
|
|
47
61
|
|
|
48
|
-
###
|
|
49
|
-
|
|
50
|
-
If you know the `ReadStream` total size and you must to set `Content-Length`.
|
|
51
|
-
You may want to use `form.setTotalStreamSize(size)`.
|
|
62
|
+
### Chaining
|
|
52
63
|
|
|
53
64
|
```js
|
|
54
|
-
var formstream = require('formstream');
|
|
55
|
-
var http = require('http');
|
|
56
65
|
var fs = require('fs');
|
|
66
|
+
var formstream = require('formstream');
|
|
57
67
|
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
host: 'upload.cnodejs.net',
|
|
65
|
-
path: '/store',
|
|
66
|
-
headers: form.headers()
|
|
67
|
-
};
|
|
68
|
-
var req = http.request(options, function (res) {
|
|
69
|
-
console.log('Status: %s', res.statusCode);
|
|
70
|
-
res.on('data', function (data) {
|
|
71
|
-
console.log(data.toString());
|
|
72
|
-
});
|
|
73
|
-
});
|
|
74
|
-
form.pipe(req);
|
|
68
|
+
var filepath = './logo.png';
|
|
69
|
+
fs.stat(filepath, function (err, stat) {
|
|
70
|
+
formstream().field('status', 'share picture')
|
|
71
|
+
.field('access_token', 'your access token')
|
|
72
|
+
.file('pic', filepath, 'logo.png', stat.size)
|
|
73
|
+
.pipe(process.stdout); // your request stream
|
|
75
74
|
});
|
|
76
75
|
```
|
|
77
76
|
|
|
78
|
-
### Chaining
|
|
79
|
-
|
|
80
|
-
```js
|
|
81
|
-
var stat = require('fs').statSync;
|
|
82
|
-
var form = require('formstream')();
|
|
83
|
-
|
|
84
|
-
form.field('status', 'share picture')
|
|
85
|
-
.field('access_token', 'dk10f88bhza-39kgna.d91')
|
|
86
|
-
.file('pic', './logo.png', 'logo.png')
|
|
87
|
-
.setTotalStreamSize(stat('./logo.png').size)
|
|
88
|
-
.pipe(/* your request stream */);
|
|
89
|
-
```
|
|
90
|
-
|
|
91
77
|
## API Doc
|
|
92
78
|
|
|
93
79
|
### formstream()
|
|
@@ -96,7 +82,7 @@ Create a form instance.
|
|
|
96
82
|
|
|
97
83
|
#### Returns
|
|
98
84
|
|
|
99
|
-
|
|
85
|
+
Form - form instance
|
|
100
86
|
|
|
101
87
|
### FormStream#field(name, value)
|
|
102
88
|
|
|
@@ -109,9 +95,9 @@ Add a normal field to the form.
|
|
|
109
95
|
|
|
110
96
|
#### Returns
|
|
111
97
|
|
|
112
|
-
|
|
98
|
+
Form - form instance
|
|
113
99
|
|
|
114
|
-
### FormStream#file(name, filepath[, filename])
|
|
100
|
+
### FormStream#file(name, filepath[, filename][, filesize])
|
|
115
101
|
|
|
116
102
|
Add a local file to be uploaded to the form.
|
|
117
103
|
|
|
@@ -120,10 +106,11 @@ Add a local file to be uploaded to the form.
|
|
|
120
106
|
- **name** String - Name of file field
|
|
121
107
|
- **filepath** String - Local path of the file to be uploaded
|
|
122
108
|
- ***filename*** String - Optional. Name of the file (will be the base name of `filepath` if empty)
|
|
109
|
+
- ***filesize*** Number - Optional. Size of the file (will not generate `Content-Length` header if not specified)
|
|
123
110
|
|
|
124
111
|
#### Returns
|
|
125
112
|
|
|
126
|
-
|
|
113
|
+
Form - form instance
|
|
127
114
|
|
|
128
115
|
### FormStream#buffer(name, buffer, filename[, contentType])
|
|
129
116
|
|
|
@@ -138,9 +125,9 @@ Add a buffer as a file to upload.
|
|
|
138
125
|
|
|
139
126
|
#### Returns
|
|
140
127
|
|
|
141
|
-
|
|
128
|
+
Form - form instance
|
|
142
129
|
|
|
143
|
-
### FormStream#stream(name, stream, filename[, contentType])
|
|
130
|
+
### FormStream#stream(name, stream, filename[, contentType][, size])
|
|
144
131
|
|
|
145
132
|
Add a readable stream as a file to upload. Event 'error' will be emitted if an error occured.
|
|
146
133
|
|
|
@@ -150,38 +137,27 @@ Add a readable stream as a file to upload. Event 'error' will be emitted if an e
|
|
|
150
137
|
- **stream** [stream.Readable](http://nodejs.org/api/stream.html#stream_class_stream_readable) - A readable stream to be piped
|
|
151
138
|
- **filename** String - The file name that tells the remote server
|
|
152
139
|
- ***contentType*** String - Optional. Content-Type (aka. MIME Type) of content (will be infered with `filename` if empty)
|
|
140
|
+
- ***size*** Number - Optional. Size of the stream (will not generate `Content-Length` header if not specified)
|
|
153
141
|
|
|
154
142
|
#### Returns
|
|
155
143
|
|
|
156
|
-
|
|
144
|
+
Form - form instance
|
|
157
145
|
|
|
158
|
-
### FormStream#
|
|
146
|
+
### FormStream#headers([headers])
|
|
159
147
|
|
|
160
|
-
|
|
148
|
+
Get headers for the request.
|
|
161
149
|
|
|
162
150
|
#### Arguments
|
|
163
151
|
|
|
164
|
-
-
|
|
165
|
-
|
|
166
|
-
#### Returns
|
|
167
|
-
|
|
168
|
-
`form`
|
|
169
|
-
|
|
170
|
-
### FormStream#headers(headers)
|
|
171
|
-
|
|
172
|
-
Add headers to the form payload.
|
|
173
|
-
|
|
174
|
-
#### Arguments
|
|
175
|
-
|
|
176
|
-
- **headers** Object - An object contains headers you want to add
|
|
152
|
+
- ***headers*** Object - Additional headers
|
|
177
153
|
|
|
178
154
|
#### Example
|
|
179
155
|
|
|
180
156
|
```js
|
|
181
|
-
form.headers({
|
|
157
|
+
var headers = form.headers({
|
|
182
158
|
'Authorization': 'Bearer kei2akc92jmznvnkeh09sknzdk',
|
|
183
159
|
'Accept': 'application/vnd.github.v3.full+json'
|
|
184
|
-
})
|
|
160
|
+
});
|
|
185
161
|
```
|
|
186
162
|
|
|
187
163
|
#### Returns
|
|
@@ -204,26 +180,12 @@ Emitted when the stream has received no more 'data' events will happen.
|
|
|
204
180
|
|
|
205
181
|
See [Node.js Documentation](http://nodejs.org/api/stream.html#stream_event_end) for more.
|
|
206
182
|
|
|
207
|
-
## Authors
|
|
208
|
-
|
|
209
|
-
```bash
|
|
210
|
-
$ git summary
|
|
211
|
-
|
|
212
|
-
project : formstream
|
|
213
|
-
repo age : 9 months
|
|
214
|
-
active : 12 days
|
|
215
|
-
commits : 24
|
|
216
|
-
files : 14
|
|
217
|
-
authors :
|
|
218
|
-
19 fengmk2 79.2%
|
|
219
|
-
5 XiNGRZ 20.8%
|
|
220
|
-
```
|
|
221
|
-
|
|
222
183
|
## License
|
|
223
184
|
|
|
224
185
|
(The MIT License)
|
|
225
186
|
|
|
226
|
-
Copyright (c) 2012 -
|
|
187
|
+
Copyright (c) 2012 - 2014 fengmk2 <fengmk2@gmail.com>
|
|
188
|
+
Copyright(c) node-modules and other contributors.
|
|
227
189
|
|
|
228
190
|
Permission is hereby granted, free of charge, to any person obtaining
|
|
229
191
|
a copy of this software and associated documentation files (the
|
package/lib/formstream.js
CHANGED
|
@@ -1,8 +1,4 @@
|
|
|
1
|
-
|
|
2
|
-
* formstream - lib/formstream.js
|
|
3
|
-
* Copyright(c) 2012 - 2013 fengmk2 <fengmk2@gmail.com>
|
|
4
|
-
* MIT Licensed
|
|
5
|
-
*
|
|
1
|
+
/**
|
|
6
2
|
* Data format:
|
|
7
3
|
*
|
|
8
4
|
|
|
@@ -25,18 +21,15 @@ Content-Type: image/png\r\n
|
|
|
25
21
|
*
|
|
26
22
|
*/
|
|
27
23
|
|
|
28
|
-
|
|
24
|
+
'use strict';
|
|
29
25
|
|
|
30
|
-
/**
|
|
31
|
-
* Module dependencies.
|
|
32
|
-
*/
|
|
33
|
-
require('buffer-concat');
|
|
34
26
|
var Stream = require('stream');
|
|
35
27
|
var parseStream = require('pause-stream');
|
|
36
28
|
var util = require('util');
|
|
37
29
|
var mime = require('mime');
|
|
38
30
|
var path = require('path');
|
|
39
31
|
var fs = require('fs');
|
|
32
|
+
var destroy = require('destroy');
|
|
40
33
|
|
|
41
34
|
var PADDING = '--';
|
|
42
35
|
var NEW_LINE = '\r\n';
|
|
@@ -48,11 +41,14 @@ function FormStream() {
|
|
|
48
41
|
}
|
|
49
42
|
|
|
50
43
|
FormStream.super_.call(this);
|
|
44
|
+
|
|
51
45
|
this._boundary = this._generateBoundary();
|
|
52
46
|
this._streams = [];
|
|
53
|
-
this._fields = [];
|
|
54
47
|
this._buffers = [];
|
|
55
48
|
this._endData = new Buffer(PADDING + this._boundary + PADDING + NEW_LINE);
|
|
49
|
+
this._contentLength = 0;
|
|
50
|
+
this._isAllStreamSizeKnown = true;
|
|
51
|
+
this._knownStreamSize = 0;
|
|
56
52
|
}
|
|
57
53
|
|
|
58
54
|
util.inherits(FormStream, Stream);
|
|
@@ -70,37 +66,21 @@ FormStream.prototype._generateBoundary = function() {
|
|
|
70
66
|
return boundary;
|
|
71
67
|
};
|
|
72
68
|
|
|
73
|
-
/**
|
|
74
|
-
* Set total stream size.
|
|
75
|
-
*
|
|
76
|
-
* You know total stream data size and you want to set `Content-Length` in headers.
|
|
77
|
-
*/
|
|
78
69
|
FormStream.prototype.setTotalStreamSize = function (size) {
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
if (this._fieldsData) {
|
|
83
|
-
size += this._fieldsData.length;
|
|
70
|
+
// this method should not make any sense if the length of each stream is known.
|
|
71
|
+
if (this._isAllStreamSizeKnown) {
|
|
72
|
+
return this;
|
|
84
73
|
}
|
|
85
74
|
|
|
86
|
-
|
|
75
|
+
size = size || 0;
|
|
76
|
+
|
|
87
77
|
for (var i = 0; i < this._streams.length; i++) {
|
|
88
|
-
|
|
89
|
-
size += item[0].length;
|
|
78
|
+
size += this._streams[i][0].length;
|
|
90
79
|
size += NEW_LINE_BUFFER.length; // stream field end pedding size
|
|
91
80
|
}
|
|
92
81
|
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
var item = this._buffers[i];
|
|
96
|
-
size += item[0].length;
|
|
97
|
-
size += item[1].length;
|
|
98
|
-
size += NEW_LINE_BUFFER.length;
|
|
99
|
-
}
|
|
100
|
-
|
|
101
|
-
// end padding data size
|
|
102
|
-
size += this._endData.length;
|
|
103
|
-
this._contentLength = size;
|
|
82
|
+
this._knownStreamSize = size;
|
|
83
|
+
this._isAllStreamSizeKnown = true;
|
|
104
84
|
|
|
105
85
|
return this;
|
|
106
86
|
};
|
|
@@ -109,113 +89,155 @@ FormStream.prototype.headers = function (options) {
|
|
|
109
89
|
var headers = {
|
|
110
90
|
'Content-Type': 'multipart/form-data; boundary=' + this._boundary
|
|
111
91
|
};
|
|
112
|
-
|
|
92
|
+
|
|
93
|
+
// calculate total stream size
|
|
94
|
+
this._contentLength += this._knownStreamSize;
|
|
95
|
+
|
|
96
|
+
// calculate length of end padding
|
|
97
|
+
this._contentLength += this._endData.length;
|
|
98
|
+
|
|
99
|
+
if (this._isAllStreamSizeKnown) {
|
|
113
100
|
headers['Content-Length'] = String(this._contentLength);
|
|
114
101
|
}
|
|
102
|
+
|
|
115
103
|
if (options) {
|
|
116
104
|
for (var k in options) {
|
|
117
105
|
headers[k] = options[k];
|
|
118
106
|
}
|
|
119
107
|
}
|
|
108
|
+
|
|
120
109
|
return headers;
|
|
121
110
|
};
|
|
122
111
|
|
|
123
|
-
FormStream.prototype.file = function (name, filepath, filename) {
|
|
112
|
+
FormStream.prototype.file = function (name, filepath, filename, filesize) {
|
|
124
113
|
var mimeType = mime.lookup(filepath);
|
|
125
|
-
|
|
114
|
+
|
|
115
|
+
if (typeof filename === 'number' && !filesize) {
|
|
116
|
+
filesize = filename;
|
|
117
|
+
filename = path.basename(filepath);
|
|
118
|
+
} else if (!filename) {
|
|
126
119
|
filename = path.basename(filepath);
|
|
127
120
|
}
|
|
128
|
-
this.stream(name, fs.createReadStream(filepath), filename, mimeType);
|
|
129
121
|
|
|
130
|
-
|
|
122
|
+
var stream = fs.createReadStream(filepath);
|
|
123
|
+
|
|
124
|
+
return this.stream(name, stream, filename, mimeType, filesize);
|
|
131
125
|
};
|
|
132
126
|
|
|
127
|
+
/**
|
|
128
|
+
* Add a form field
|
|
129
|
+
* @param {String} name field name
|
|
130
|
+
* @param {String|Buffer} value field value
|
|
131
|
+
* @return {this}
|
|
132
|
+
*/
|
|
133
133
|
FormStream.prototype.field = function (name, value) {
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
134
|
+
if (!Buffer.isBuffer(value)) {
|
|
135
|
+
// field(String, Number)
|
|
136
|
+
// https://github.com/qiniu/nodejs-sdk/issues/123
|
|
137
|
+
if (typeof value === 'number') {
|
|
138
|
+
value = String(value);
|
|
139
|
+
}
|
|
140
|
+
value = new Buffer(value);
|
|
141
|
+
}
|
|
142
|
+
return this.buffer(name, value);
|
|
138
143
|
};
|
|
139
144
|
|
|
140
|
-
FormStream.prototype.stream = function (name, stream, filename, mimeType) {
|
|
141
|
-
|
|
142
|
-
|
|
145
|
+
FormStream.prototype.stream = function (name, stream, filename, mimeType, size) {
|
|
146
|
+
if (typeof mimeType === 'number' && !size) {
|
|
147
|
+
size = mimeType;
|
|
148
|
+
mimeType = mime.lookup(filename);
|
|
149
|
+
} else if (!mimeType) {
|
|
150
|
+
mimeType = mime.lookup(filename);
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
stream.once('error', this.emit.bind(this, 'error'));
|
|
154
|
+
// if form stream destroy, also destroy the source stream
|
|
155
|
+
this.once('destroy', function () {
|
|
156
|
+
destroy(stream);
|
|
157
|
+
});
|
|
158
|
+
|
|
159
|
+
var leading = this._leading({ name: name, filename: filename }, mimeType);
|
|
160
|
+
|
|
143
161
|
var ps = parseStream().pause();
|
|
144
162
|
stream.pipe(ps);
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
163
|
+
|
|
164
|
+
this._streams.push([leading, ps]);
|
|
165
|
+
|
|
166
|
+
// if the size of this stream is known, plus the total content-length;
|
|
167
|
+
// otherwise, content-length is unknown.
|
|
168
|
+
if (typeof size === 'number') {
|
|
169
|
+
this._knownStreamSize += leading.length;
|
|
170
|
+
this._knownStreamSize += size;
|
|
171
|
+
this._knownStreamSize += NEW_LINE_BUFFER.length;
|
|
172
|
+
} else {
|
|
173
|
+
this._isAllStreamSizeKnown = false;
|
|
174
|
+
}
|
|
175
|
+
|
|
149
176
|
process.nextTick(this.resume.bind(this));
|
|
150
177
|
|
|
151
178
|
return this;
|
|
152
179
|
};
|
|
153
180
|
|
|
154
181
|
FormStream.prototype.buffer = function (name, buffer, filename, mimeType) {
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
182
|
+
if (filename && !mimeType) {
|
|
183
|
+
mimeType = mime.lookup(filename);
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
var disposition = { name: name };
|
|
187
|
+
if (filename) {
|
|
188
|
+
disposition.filename = filename;
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
var leading = this._leading(disposition, mimeType);
|
|
192
|
+
|
|
193
|
+
this._buffers.push([leading, buffer]);
|
|
194
|
+
|
|
195
|
+
// plus buffer length to total content-length
|
|
196
|
+
this._contentLength += leading.length;
|
|
197
|
+
this._contentLength += buffer.length;
|
|
198
|
+
this._contentLength += NEW_LINE_BUFFER.length;
|
|
199
|
+
|
|
160
200
|
process.nextTick(this.resume.bind(this));
|
|
161
201
|
|
|
162
202
|
return this;
|
|
163
203
|
};
|
|
164
204
|
|
|
165
|
-
FormStream.prototype.
|
|
166
|
-
|
|
167
|
-
//
|
|
168
|
-
// --{boundary}--\r\n
|
|
169
|
-
this.emit('data', this._endData);
|
|
170
|
-
this.emit('end');
|
|
171
|
-
};
|
|
205
|
+
FormStream.prototype._leading = function (disposition, type) {
|
|
206
|
+
var leading = [PADDING + this._boundary];
|
|
172
207
|
|
|
173
|
-
|
|
174
|
-
if (!this._fields.length) {
|
|
175
|
-
return;
|
|
176
|
-
}
|
|
208
|
+
var disps = [];
|
|
177
209
|
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
lines += 'Content-Disposition: form-data; name="' + field[0] + '"' + NEW_LINE;
|
|
183
|
-
lines += NEW_LINE;
|
|
184
|
-
lines += field[1];
|
|
185
|
-
lines += NEW_LINE;
|
|
210
|
+
if (disposition) {
|
|
211
|
+
for (var k in disposition) {
|
|
212
|
+
disps.push(k + '="' + disposition[k] + '"');
|
|
213
|
+
}
|
|
186
214
|
}
|
|
187
|
-
this._fieldsData = new Buffer(lines);
|
|
188
|
-
this._fields = [];
|
|
189
|
-
};
|
|
190
215
|
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
if (
|
|
194
|
-
|
|
195
|
-
this._fieldsData = null;
|
|
196
|
-
this.emit('data', data);
|
|
216
|
+
leading.push('Content-Disposition: form-data; ' + disps.join('; '));
|
|
217
|
+
|
|
218
|
+
if (type) {
|
|
219
|
+
leading.push('Content-Type: ' + type);
|
|
197
220
|
}
|
|
221
|
+
|
|
222
|
+
leading.push('');
|
|
223
|
+
leading.push('');
|
|
224
|
+
|
|
225
|
+
return new Buffer(leading.join(NEW_LINE));
|
|
198
226
|
};
|
|
199
227
|
|
|
200
228
|
FormStream.prototype._emitBuffers = function () {
|
|
201
229
|
if (!this._buffers.length) {
|
|
202
230
|
return;
|
|
203
231
|
}
|
|
232
|
+
|
|
204
233
|
for (var i = 0; i < this._buffers.length; i++) {
|
|
205
234
|
var item = this._buffers[i];
|
|
206
|
-
this.emit('data', item[0]);
|
|
207
|
-
this.emit('data', item[1]);
|
|
235
|
+
this.emit('data', item[0]); // part leading
|
|
236
|
+
this.emit('data', item[1]); // part content
|
|
208
237
|
this.emit('data', NEW_LINE_BUFFER);
|
|
209
238
|
}
|
|
210
|
-
this._buffers = [];
|
|
211
|
-
};
|
|
212
239
|
|
|
213
|
-
|
|
214
|
-
var data = PADDING + this._boundary + NEW_LINE;
|
|
215
|
-
data += 'Content-Disposition: form-data; name="' + name +'"; filename="' + filename + '"' + NEW_LINE;
|
|
216
|
-
data += 'Content-Type: ' + mimeType + NEW_LINE;
|
|
217
|
-
data += NEW_LINE;
|
|
218
|
-
return new Buffer(data);
|
|
240
|
+
this._buffers = [];
|
|
219
241
|
};
|
|
220
242
|
|
|
221
243
|
FormStream.prototype._emitStream = function (item) {
|
|
@@ -234,24 +256,38 @@ FormStream.prototype._emitStream = function (item) {
|
|
|
234
256
|
stream.resume();
|
|
235
257
|
};
|
|
236
258
|
|
|
259
|
+
FormStream.prototype._emitEnd = function () {
|
|
260
|
+
// ending format:
|
|
261
|
+
//
|
|
262
|
+
// --{boundary}--\r\n
|
|
263
|
+
this.emit('data', this._endData);
|
|
264
|
+
this.emit('end');
|
|
265
|
+
};
|
|
266
|
+
|
|
237
267
|
FormStream.prototype.drain = function () {
|
|
238
|
-
this._emitFields();
|
|
239
268
|
this._emitBuffers();
|
|
269
|
+
|
|
240
270
|
var item = this._streams.shift();
|
|
241
271
|
if (item) {
|
|
242
272
|
this._emitStream(item);
|
|
243
273
|
} else {
|
|
244
|
-
// end
|
|
245
274
|
this._emitEnd();
|
|
246
275
|
}
|
|
276
|
+
|
|
247
277
|
return this;
|
|
248
278
|
};
|
|
249
279
|
|
|
250
280
|
FormStream.prototype.resume = function () {
|
|
251
281
|
this.paused = false;
|
|
282
|
+
|
|
252
283
|
if (!this._draining) {
|
|
253
284
|
this._draining = true;
|
|
254
285
|
this.drain();
|
|
255
286
|
}
|
|
287
|
+
|
|
256
288
|
return this;
|
|
257
289
|
};
|
|
290
|
+
|
|
291
|
+
FormStream.prototype.close = FormStream.prototype.destroy = function () {
|
|
292
|
+
this.emit('destroy');
|
|
293
|
+
};
|
package/package.json
CHANGED
|
@@ -1,16 +1,21 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "formstream",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "1.1.0",
|
|
4
4
|
"description": "A multipart/form-data encoded stream, helper for file upload.",
|
|
5
|
-
"main": "
|
|
5
|
+
"main": "lib/formstream.js",
|
|
6
|
+
"files": [
|
|
7
|
+
"lib"
|
|
8
|
+
],
|
|
6
9
|
"scripts": {
|
|
7
|
-
"test": "
|
|
8
|
-
"
|
|
9
|
-
"travis
|
|
10
|
+
"test": "mocha -R spec -t 5000 -r should test/*.test.js",
|
|
11
|
+
"test-cov": "istanbul cover node_modules/.bin/_mocha -- -t 5000 -r should test/*.test.js",
|
|
12
|
+
"test-travis": "istanbul cover node_modules/.bin/_mocha --report lcovonly -- -t 5000 -r should test/*.test.js",
|
|
13
|
+
"jshint": "jshint .",
|
|
14
|
+
"autod": "autod -w --prefix '^'"
|
|
10
15
|
},
|
|
11
16
|
"repository": {
|
|
12
17
|
"type": "git",
|
|
13
|
-
"url": "git://github.com/
|
|
18
|
+
"url": "git://github.com/node-modules/formstream.git"
|
|
14
19
|
},
|
|
15
20
|
"keywords": [
|
|
16
21
|
"form",
|
|
@@ -22,19 +27,19 @@
|
|
|
22
27
|
"request"
|
|
23
28
|
],
|
|
24
29
|
"dependencies": {
|
|
25
|
-
"
|
|
26
|
-
"
|
|
27
|
-
"pause-stream": "
|
|
30
|
+
"destroy": "^1.0.4",
|
|
31
|
+
"mime": "^1.3.4",
|
|
32
|
+
"pause-stream": "~0.0.11"
|
|
28
33
|
},
|
|
29
34
|
"devDependencies": {
|
|
30
|
-
"
|
|
31
|
-
"
|
|
32
|
-
"
|
|
33
|
-
"
|
|
34
|
-
"
|
|
35
|
-
"
|
|
36
|
-
"
|
|
37
|
-
"
|
|
35
|
+
"autod": "*",
|
|
36
|
+
"connect-multiparty": "1",
|
|
37
|
+
"express": "4",
|
|
38
|
+
"istanbul": "*",
|
|
39
|
+
"mocha": "*",
|
|
40
|
+
"pedding": "1",
|
|
41
|
+
"should": "4",
|
|
42
|
+
"urllib": "2"
|
|
38
43
|
},
|
|
39
44
|
"author": "fengmk2 <fengmk2@gmail.com> (http://fengmk2.github.com)",
|
|
40
45
|
"license": "MIT"
|
package/.npmignore
DELETED
package/LICENSE.txt
DELETED
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
This software is licensed under the MIT License.
|
|
2
|
-
|
|
3
|
-
Copyright (C) 2012 - 2013 by fengmk2 <fengmk2@gmail.com>
|
|
4
|
-
|
|
5
|
-
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
-
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
-
in the Software without restriction, including without limitation the rights
|
|
8
|
-
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
-
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
-
furnished to do so, subject to the following conditions:
|
|
11
|
-
|
|
12
|
-
The above copyright notice and this permission notice shall be included in
|
|
13
|
-
all copies or substantial portions of the Software.
|
|
14
|
-
|
|
15
|
-
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
-
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
-
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
-
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
-
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
-
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
|
21
|
-
THE SOFTWARE.
|
package/index.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
module.exports = require('./lib/formstream');
|