Skip to content

Commit b56c3a2

Browse files
committed
formatting querystring array params for visual recognition
Fixes #411
1 parent 989244c commit b56c3a2

2 files changed

Lines changed: 55 additions & 21 deletions

File tree

test/unit/test.visual_recognition.v3.js

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ const watson = require('../../index');
55
const nock = require('nock');
66
const fs = require('fs');
77
const omit = require('object.omit');
8+
const URL = require('url');
9+
const qs = require('querystring');
810

911
describe('visual_recognition', function() {
1012
const noop = function() {};
@@ -151,7 +153,7 @@ describe('visual_recognition', function() {
151153
assert.equal(req.formData.classifier_ids, undefined);
152154
});
153155

154-
it('should generate a valid payload', function() {
156+
it('should generate a valid payload with an image file', function() {
155157
const params = {
156158
images_file: fake_file,
157159
classifier_ids: ['foo', 'bar']
@@ -164,6 +166,22 @@ describe('visual_recognition', function() {
164166
const uploadedParameters = JSON.parse(req.formData.parameters.value);
165167
assert.deepEqual(uploadedParameters.classifier_ids, params.classifier_ids);
166168
});
169+
170+
it('should generate a valid payload with a url', function() {
171+
const params = {
172+
url: 'https://watson-test-resources.mybluemix.net/resources/obama.jpg',
173+
classifier_ids: ['foo', 'bar']
174+
};
175+
176+
const req = visual_recognition.classify(params, noop);
177+
assert.equal(req.method, 'GET');
178+
assert.equal(req.uri.pathname, URL.parse(service.url + classify_path).pathname);
179+
assert(req.uri.query);
180+
const query = qs.parse(req.uri.query);
181+
assert.equal(typeof query.classifier_ids, 'string'); // otherwise the next check can pass incorrectly (assert uses == !?)
182+
assert.equal(query.classifier_ids, params.classifier_ids.join(','), 'multiple classifiers should be comma-separated');
183+
assert.equal(typeof query.owners, 'string');
184+
});
167185
});
168186

169187
describe('listClassifiers()', function() {

visual-recognition/v3.js

Lines changed: 36 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -140,6 +140,22 @@ VisualRecognitionV3.prototype.serviceDefaults = {
140140
alchemy: true
141141
};
142142

143+
/**
144+
* Wrapper for requestFactory that ensures things are formatted the way the service likes
145+
*
146+
* @private
147+
* @param {Object} parameters
148+
* @param {Function} cb
149+
*/
150+
VisualRecognitionV3.prototype.request = function(parameters, cb) {
151+
const qs = parameters.options.qs;
152+
if (qs) {
153+
// array params are turned into a comma-separated string when in querystrings
154+
Object.keys(qs).forEach(k => Array.isArray(qs[k]) && (qs[k] = qs[k].join(',')));
155+
}
156+
return requestFactory(parameters, cb);
157+
};
158+
143159
/**
144160
* Grab the api key
145161
*
@@ -282,7 +298,7 @@ VisualRecognitionV3.prototype.classify = function(params, callback) {
282298
};
283299
}
284300

285-
return requestFactory(parameters, errorFormatter(callback));
301+
return this.request(parameters, errorFormatter(callback));
286302
};
287303

288304
/**
@@ -361,7 +377,7 @@ VisualRecognitionV3.prototype.detectFaces = function(params, callback) {
361377
};
362378
}
363379

364-
return requestFactory(parameters, errorFormatter(callback));
380+
return this.request(parameters, errorFormatter(callback));
365381
};
366382

367383
/**
@@ -450,7 +466,7 @@ VisualRecognitionV3.prototype.recognizeText = function(params, callback) {
450466
};
451467
}
452468

453-
return requestFactory(parameters, errorFormatter(callback));
469+
return this.request(parameters, errorFormatter(callback));
454470
};
455471

456472
/**
@@ -525,7 +541,7 @@ VisualRecognitionV3.prototype.createClassifier = function(params, callback) {
525541
requiredParams: ['name'],
526542
defaultOptions: this._options
527543
};
528-
return requestFactory(parameters, errorFormatter(callback));
544+
return this.request(parameters, errorFormatter(callback));
529545
};
530546

531547
/**
@@ -572,7 +588,7 @@ VisualRecognitionV3.prototype.retrainClassifier = function(params, callback) {
572588
requiredParams: [],
573589
defaultOptions: this._options
574590
};
575-
return requestFactory(parameters, errorFormatter(callback));
591+
return this.request(parameters, errorFormatter(callback));
576592
};
577593

578594
/**
@@ -607,7 +623,7 @@ VisualRecognitionV3.prototype.listClassifiers = function(params, callback) {
607623
},
608624
defaultOptions: this._options
609625
};
610-
return requestFactory(parameters, errorFormatter(callback));
626+
return this.request(parameters, errorFormatter(callback));
611627
};
612628

613629
/**
@@ -643,7 +659,7 @@ VisualRecognitionV3.prototype.getClassifier = function(params, callback) {
643659
requiredParams: ['classifier_id'],
644660
defaultOptions: this._options
645661
};
646-
return requestFactory(parameters, errorFormatter(callback));
662+
return this.request(parameters, errorFormatter(callback));
647663
};
648664

649665
/**
@@ -665,7 +681,7 @@ VisualRecognitionV3.prototype.deleteClassifier = function(params, callback) {
665681
requiredParams: ['classifier_id'],
666682
defaultOptions: this._options
667683
};
668-
return requestFactory(parameters, errorFormatter(callback));
684+
return this.request(parameters, errorFormatter(callback));
669685
};
670686

671687
// collections & similarity search
@@ -700,7 +716,7 @@ VisualRecognitionV3.prototype.createCollection = function(params, callback) {
700716
requiredParams: ['name'],
701717
defaultOptions: this._options
702718
};
703-
return requestFactory(parameters, errorFormatter(callback));
719+
return this.request(parameters, errorFormatter(callback));
704720
};
705721

706722
/**
@@ -733,7 +749,7 @@ VisualRecognitionV3.prototype.getCollection = function(params, callback) {
733749
requiredParams: ['collection_id'],
734750
defaultOptions: this._options
735751
};
736-
return requestFactory(parameters, errorFormatter(callback));
752+
return this.request(parameters, errorFormatter(callback));
737753
};
738754

739755
/**
@@ -766,7 +782,7 @@ VisualRecognitionV3.prototype.listCollections = function(params, callback) {
766782
},
767783
defaultOptions: this._options
768784
};
769-
return requestFactory(parameters, errorFormatter(callback));
785+
return this.request(parameters, errorFormatter(callback));
770786
};
771787

772788
/**
@@ -790,7 +806,7 @@ VisualRecognitionV3.prototype.deleteCollection = function(params, callback) {
790806
requiredParams: ['collection_id'],
791807
defaultOptions: this._options
792808
};
793-
return requestFactory(parameters, errorFormatter(callback));
809+
return this.request(parameters, errorFormatter(callback));
794810
};
795811

796812
/**
@@ -846,7 +862,7 @@ VisualRecognitionV3.prototype.addImage = function(params, callback) {
846862
requiredParams: ['collection_id', 'image_file'],
847863
defaultOptions: this._options
848864
};
849-
return requestFactory(parameters, errorFormatter(callback));
865+
return this.request(parameters, errorFormatter(callback));
850866
};
851867

852868
/**
@@ -879,7 +895,7 @@ VisualRecognitionV3.prototype.listImages = function(params, callback) {
879895
requiredParams: ['collection_id'],
880896
defaultOptions: this._options
881897
};
882-
return requestFactory(parameters, errorFormatter(callback));
898+
return this.request(parameters, errorFormatter(callback));
883899
};
884900

885901
/**
@@ -910,7 +926,7 @@ VisualRecognitionV3.prototype.getImage = function(params, callback) {
910926
requiredParams: ['collection_id', 'image_id'],
911927
defaultOptions: this._options
912928
};
913-
return requestFactory(parameters, errorFormatter(callback));
929+
return this.request(parameters, errorFormatter(callback));
914930
};
915931

916932
/**
@@ -935,7 +951,7 @@ VisualRecognitionV3.prototype.deleteImage = function(params, callback) {
935951
requiredParams: ['collection_id', 'image_id'],
936952
defaultOptions: this._options
937953
};
938-
return requestFactory(parameters, errorFormatter(callback));
954+
return this.request(parameters, errorFormatter(callback));
939955
};
940956

941957
/**
@@ -972,7 +988,7 @@ VisualRecognitionV3.prototype.setImageMetadata = function(params, callback) {
972988
requiredParams: ['collection_id', 'image_id', 'metadata'],
973989
defaultOptions: this._options
974990
};
975-
return requestFactory(parameters, errorFormatter(callback));
991+
return this.request(parameters, errorFormatter(callback));
976992
};
977993

978994
/**
@@ -1002,7 +1018,7 @@ VisualRecognitionV3.prototype.getImageMetadata = function(params, callback) {
10021018
requiredParams: ['collection_id', 'image_id'],
10031019
defaultOptions: this._options
10041020
};
1005-
return requestFactory(parameters, errorFormatter(callback));
1021+
return this.request(parameters, errorFormatter(callback));
10061022
};
10071023

10081024
/**
@@ -1027,7 +1043,7 @@ VisualRecognitionV3.prototype.deleteImageMetadata = function(params, callback) {
10271043
requiredParams: ['collection_id', 'image_id'],
10281044
defaultOptions: this._options
10291045
};
1030-
return requestFactory(parameters, errorFormatter(callback));
1046+
return this.request(parameters, errorFormatter(callback));
10311047
};
10321048

10331049
/**
@@ -1079,7 +1095,7 @@ VisualRecognitionV3.prototype.findSimilar = function(params, callback) {
10791095
requiredParams: ['collection_id', 'image_file'],
10801096
defaultOptions: this._options
10811097
};
1082-
return requestFactory(parameters, errorFormatter(callback));
1098+
return this.request(parameters, errorFormatter(callback));
10831099
};
10841100

10851101
module.exports = VisualRecognitionV3;

0 commit comments

Comments
 (0)