├── .editorconfig ├── .gitignore ├── .jscsrc ├── .jshintignore ├── .jshintrc ├── .npmrc ├── .travis.yml ├── LICENSE ├── README.md ├── example.js ├── index.js ├── package.json └── test.js /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | end_of_line = lf 5 | indent_style = space 6 | indent_size = 2 7 | charset = utf-8 8 | trim_trailing_whitespace = true 9 | insert_final_newline = true 10 | 11 | [*.md] 12 | trim_trailing_whitespace = false 13 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | coverage 3 | run.js 4 | -------------------------------------------------------------------------------- /.jscsrc: -------------------------------------------------------------------------------- 1 | { 2 | "excludeFiles": [ 3 | "**/node_modules/**", 4 | "coverage", 5 | "data" 6 | ], 7 | "requireLineFeedAtFileEnd": true, 8 | "disallowMultipleLineBreaks": true, 9 | "disallowEmptyBlocks": true, 10 | "disallowSpaceAfterObjectKeys": true, 11 | "disallowTrailingWhitespace": true, 12 | "requireCapitalizedConstructors": true, 13 | "requireSpacesInsideObjectBrackets": "all", 14 | "requireSpacesInsideArrayBrackets": "all", 15 | "validateLineBreaks": "LF", 16 | "requireSpaceBeforeBinaryOperators": [ "+", "-", "/", "*", "=", "==", "===", "!=", "!==" ], 17 | "requireSpaceAfterBinaryOperators": [ "+", "-", "/", "*", "=", "==", "===", "!=", "!==" ], 18 | "requireSpaceAfterKeywords": [ "if", "else", "for", "while", "do", "switch", "try", "catch" ], 19 | "requireSpaceBeforeBinaryOperators": [ "/", "*", "=", "==", "===", "!=", "!==", ">", ">=", "<", "<=" ], 20 | "requireSpaceAfterBinaryOperators": [ "+", "/", "*", ":", "=", "==", "===", "!=", "!==", ">", ">=", "<", "<=" ], 21 | "requireSpacesInConditionalExpression": true, 22 | "disallowSpaceAfterPrefixUnaryOperators": [ "++", "--", "+", "-", "~", "!" ], 23 | "disallowSpaceBeforePostfixUnaryOperators": [ "++", "--" ], 24 | "requireSpaceBeforeBinaryOperators": [ "+", "-", "/", "*", "=", "==", "===", "!=", "!==" ], 25 | "requireSpaceAfterBinaryOperators": [ "+", "-", "/", "*", "=", "==", "===", "!=", "!==" ], 26 | "disallowKeywordsOnNewLine": [ "else" ], 27 | "requireSpacesInFunctionExpression": { "beforeOpeningCurlyBrace": true } 28 | } 29 | -------------------------------------------------------------------------------- /.jshintignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | coverage 3 | -------------------------------------------------------------------------------- /.jshintrc: -------------------------------------------------------------------------------- 1 | { 2 | "boss": true, 3 | "curly": true, 4 | "eqeqeq": true, 5 | "eqnull": true, 6 | "expr": true, 7 | "immed": true, 8 | "noarg": true, 9 | "onevar": true, 10 | "quotmark": "single", 11 | "trailing": true, 12 | "undef": true, 13 | "unused": true, 14 | "node": true, 15 | "browser": false, 16 | "predef": [ 17 | "describe", 18 | "it", 19 | "before", 20 | "beforeEach", 21 | "after", 22 | "afterEach" 23 | ] 24 | } 25 | -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | package-lock=false 2 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: node_js 2 | node_js: 3 | - "6" 4 | - "5" 5 | - "4" 6 | - "iojs" 7 | script: npm test 8 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2015, WooThemes (https://woocommerce.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. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # WooCommerce API - Node.js Client 2 | 3 | A Node.js client for the WooCommerce REST API. Easily interact with the WooCommerce REST API using this library. 4 | 5 | **- 2019-07-29: This client is obsolete and will no longer receive updates, a new JavaScript library is available under the name of [`@woocommerce/woocommerce-rest-api`](https://github.com/woocommerce/woocommerce-rest-api-js-lib).** 6 | 7 | [![build status](https://secure.travis-ci.org/woocommerce/wc-api-node.svg)](http://travis-ci.org/woocommerce/wc-api-node) 8 | [![dependency status](https://david-dm.org/woocommerce/wc-api-node.svg)](https://david-dm.org/woocommerce/wc-api-node) 9 | [![npm version](https://img.shields.io/npm/v/woocommerce-api.svg)](https://www.npmjs.com/package/woocommerce-api) 10 | 11 | ## Installation 12 | 13 | ``` 14 | npm install --save woocommerce-api 15 | ``` 16 | 17 | ## Getting started 18 | 19 | Generate API credentials (Consumer Key & Consumer Secret) following this instructions 20 | . 21 | 22 | Check out the WooCommerce API endpoints and data that can be manipulated in . 23 | 24 | ## Setup 25 | 26 | Setup for the new WP REST API integration (WooCommerce 2.6 or later): 27 | 28 | ```js 29 | var WooCommerceAPI = require('woocommerce-api'); 30 | 31 | var WooCommerce = new WooCommerceAPI({ 32 | url: 'http://example.com', 33 | consumerKey: 'ck_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 34 | consumerSecret: 'cs_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 35 | wpAPI: true, 36 | version: 'wc/v1' 37 | }); 38 | ``` 39 | 40 | Setup for the old WooCommerce legacy API: 41 | 42 | ```js 43 | var WooCommerceAPI = require('woocommerce-api'); 44 | 45 | var WooCommerce = new WooCommerceAPI({ 46 | url: 'http://example.com', 47 | consumerKey: 'ck_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 48 | consumerSecret: 'cs_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 49 | version: 'v3' 50 | }); 51 | ``` 52 | 53 | ### Options 54 | 55 | | Option | Type | Required | Description | 56 | |-------------------|-----------|----------|----------------------------------------------------------------------------------------------------------| 57 | | `url` | `String` | yes | Your Store URL, example: http://woo.dev/ | 58 | | `consumerKey` | `String` | yes | Your API consumer key | 59 | | `consumerSecret` | `String` | yes | Your API consumer secret | 60 | | `wpAPI` | `Bool` | no | Allow requests to the WP REST API (WooCommerce 2.6 or later) | 61 | | `wpAPIPrefix` | `String` | no | Custom WP REST API URL prefix, used to support custom prefixes created with the `rest_url_prefix` filter | 62 | | `version` | `String` | no | API version, default is `v3` | 63 | | `verifySsl` | `Bool` | no | Verify SSL when connect, use this option as `false` when need to test with self-signed certificates | 64 | | `encoding` | `String` | no | Encoding, default is 'utf-8' | 65 | | `queryStringAuth` | `Bool` | no | When `true` and using under HTTPS force Basic Authentication as query string, default is `false` | 66 | | `port` | `string` | no | Provide support for URLs with ports, eg: `8080` | 67 | | `timeout` | `Integer` | no | Define the request timeout | 68 | | `agent` | `Agent` | no | User agent instance. | 69 | 70 | ## Methods 71 | 72 | | Params | Type | Description | 73 | |------------|------------|--------------------------------------------------------------| 74 | | `endpoint` | `String` | WooCommerce API endpoint, example: `customers` or `order/12` | 75 | | `data` | `Object` | JS object, will be converted to JSON | 76 | | `callback` | `Function` | Callback function. Returns `err`, `data` and `res` | 77 | 78 | ### GET 79 | 80 | - `.get(endpoint)` 81 | - `.get(endpoint, callback)` 82 | 83 | ### POST 84 | 85 | - `.post(endpoint, data)` 86 | - `.post(endpoint, data, callback)` 87 | 88 | ### PUT 89 | 90 | - `.put(endpoint, data)` 91 | - `.put(endpoint, data, callback)` 92 | 93 | ### DELETE 94 | 95 | - `.delete(endpoint)` 96 | - `.delete(endpoint, callback)` 97 | 98 | ### OPTIONS 99 | 100 | - `.options(endpoint)` 101 | - `.options(endpoint, callback)` 102 | 103 | ## Promified Methods 104 | 105 | Every method can be used in a promified way just adding `Async` to the method name. Like in: 106 | 107 | ```js 108 | WooCommerce.getAsync('products').then(function(result) { 109 | return JSON.parse(result.toJSON().body); 110 | }); 111 | ``` 112 | 113 | ## Release History 114 | 115 | - 2019-07-29 - v1.5.0 - Updated dependencies, and adds support for `agent`. 116 | - 2016-12-14 - v1.4.2 - Fixed WordPress 4.7 compatibility. 117 | - 2016-09-28 - v1.4.1 - Updated dependencies and updated/fixed oAuth1.0a. 118 | - 2016-06-30 - v1.4.0 - Added `wpAPIPrefix` option to allow custom WP REST API Url prefix and support for promified methods. 119 | - 2016-06-09 - v1.3.2 - Fixed oAuth signature for WP REST API. 120 | - 2016-06-08 - v1.3.1 - Fixed README.md. 121 | - 2016-06-03 - v1.3.0 - Added new `timeout` option and updated dependencies. 122 | - 2016-05-09 - v1.2.0 - Added support for WP REST API and added method to do HTTP OPTIONS requests. 123 | - 2016-03-18 - v1.1.1 - Added support for ports. 124 | - 2016-02-22 - v1.1.0 - Added `queryStringAuth` option to allow Basic Authentication as query string. 125 | - 2015-12-07 - v1.0.4 - Updated dependencies and fixed brackets when sorting query string. 126 | - 2015-12-07 - v1.0.3 - Added method to properly sort query strings when using oAuth. 127 | - 2015-07-11 - v1.0.2 - Fixed the examples on example.js and README.md. 128 | - 2015-07-11 - v1.0.1 - Added unit tests, improved the main class and added full description on README.md. 129 | - 2015-07-11 - v1.0.0 - Initial release. 130 | -------------------------------------------------------------------------------- /example.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | var WooCommerceAPI = require('./index.js'); // use require('woocommerce-api') 4 | 5 | // Initialize the WooCommerceAPI class 6 | var WooCommerce = new WooCommerceAPI({ 7 | url: 'http://example.com', // Your store url (required) 8 | // version: 'v3', // WooCommerce API version (optional) 9 | // verifySsl: true, // Use `false` when need test with self-signed certificates, default is `true` (optional) 10 | // encoding: 'utf8', // Encode, default is 'utf8' (optional) 11 | consumerKey: 'ck_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', // Your API consumer key (required) 12 | consumerSecret: 'cs_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX' // Your API consumer secret (required) 13 | }); 14 | 15 | // GET example 16 | WooCommerce.get('customers', function(err, data, res) { 17 | console.log(res); 18 | }); 19 | 20 | // POST example 21 | // WooCommerce.post('products', { 22 | // product: { 23 | // title: 'Premium Quality', 24 | // type: 'simple', 25 | // regular_price: '21.99' 26 | // } 27 | // }, function(err, data, res) { 28 | // console.log(res); 29 | // }); 30 | 31 | // PUT example 32 | // WooCommerce.put('orders/123', { 33 | // order: { 34 | // status: 'completed' 35 | // } 36 | // }, function(err, data, res) { 37 | // console.log(res); 38 | // }); 39 | 40 | // Delete example 41 | // WooCommerce.delete('coupons/123', function(err, data, res) { 42 | // console.log(res); 43 | // }); 44 | -------------------------------------------------------------------------------- /index.js: -------------------------------------------------------------------------------- 1 | 'use strict'; 2 | 3 | var request = require('request'); 4 | var OAuth = require('oauth-1.0a'); 5 | var createHmac = require('create-hmac'); 6 | var promise = require('bluebird'); 7 | var _url = require('url'); 8 | 9 | module.exports = WooCommerceAPI; 10 | 11 | /** 12 | * WooCommerce REST API wrapper 13 | * 14 | * @param {Object} opt 15 | */ 16 | function WooCommerceAPI(opt) { 17 | if (!(this instanceof WooCommerceAPI)) { 18 | return new WooCommerceAPI(opt); 19 | } 20 | 21 | opt = opt || {}; 22 | 23 | if (!(opt.url)) { 24 | throw new Error('url is required'); 25 | } 26 | 27 | if (!(opt.consumerKey)) { 28 | throw new Error('consumerKey is required'); 29 | } 30 | 31 | if (!(opt.consumerSecret)) { 32 | throw new Error('consumerSecret is required'); 33 | } 34 | 35 | this.classVersion = '1.5.0'; 36 | this._setDefaultsOptions(opt); 37 | } 38 | 39 | /** 40 | * Set default options 41 | * 42 | * @param {Object} opt 43 | */ 44 | WooCommerceAPI.prototype._setDefaultsOptions = function(opt) { 45 | this.url = opt.url; 46 | this.wpAPI = opt.wpAPI || false; 47 | this.wpAPIPrefix = opt.wpAPIPrefix || 'wp-json'; 48 | this.version = opt.version || 'v3'; 49 | this.isSsl = /^https/i.test(this.url); 50 | this.consumerKey = opt.consumerKey; 51 | this.consumerSecret = opt.consumerSecret; 52 | this.verifySsl = false === opt.verifySsl ? false : true; 53 | this.encoding = opt.encoding || 'utf8'; 54 | this.queryStringAuth = opt.queryStringAuth || false; 55 | this.port = opt.port || ''; 56 | this.timeout = opt.timeout; 57 | this.agent = opt.agent; 58 | }; 59 | 60 | /** 61 | * Normalize query string for oAuth 62 | * 63 | * @param {string} url 64 | * @return {string} 65 | */ 66 | WooCommerceAPI.prototype._normalizeQueryString = function(url) { 67 | // Exit if don't find query string 68 | if (-1 === url.indexOf('?')) { 69 | return url; 70 | } 71 | 72 | var query = _url.parse(url, true).query; 73 | var params = []; 74 | var queryString = ''; 75 | 76 | for (var p in query) { 77 | params.push(p); 78 | } 79 | params.sort(); 80 | 81 | for (var i in params) { 82 | if (queryString.length) { 83 | queryString += '&'; 84 | } 85 | 86 | queryString += encodeURIComponent(params[i]).replace(/%5B/g, '[') 87 | .replace(/%5D/g, ']'); 88 | queryString += '='; 89 | queryString += encodeURIComponent(query[params[i]]); 90 | } 91 | 92 | return url.split('?')[0] + '?' + queryString; 93 | }; 94 | 95 | /** 96 | * Get URL 97 | * 98 | * @param {String} endpoint 99 | * 100 | * @return {String} 101 | */ 102 | WooCommerceAPI.prototype._getUrl = function(endpoint) { 103 | var url = '/' === this.url.slice(-1) ? this.url : this.url + '/'; 104 | var api = this.wpAPI ? this.wpAPIPrefix + '/' : 'wc-api/'; 105 | 106 | url = url + api + this.version + '/' + endpoint; 107 | 108 | // Include port. 109 | if ('' !== this.port) { 110 | var hostname = _url.parse(url, true).hostname; 111 | url = url.replace(hostname, hostname + ':' + this.port); 112 | } 113 | 114 | if (!this.isSsl) { 115 | return this._normalizeQueryString(url); 116 | } 117 | 118 | return url; 119 | }; 120 | 121 | /** 122 | * Get OAuth 123 | * 124 | * @return {Object} 125 | */ 126 | WooCommerceAPI.prototype._getOAuth = function() { 127 | var data = { 128 | consumer: { 129 | key: this.consumerKey, 130 | secret: this.consumerSecret 131 | }, 132 | signature_method: 'HMAC-SHA256', 133 | hash_function: function(base_string, key) { 134 | return createHmac('sha256', key).update(base_string) 135 | .digest('base64'); 136 | } 137 | }; 138 | 139 | if (-1 < [ 'v1', 'v2' ].indexOf(this.version)) { 140 | data.last_ampersand = false; 141 | } 142 | 143 | return new OAuth(data); 144 | }; 145 | 146 | /** 147 | * Do requests 148 | * 149 | * @param {String} method 150 | * @param {String} endpoint 151 | * @param {Object} data 152 | * @param {Function} callback 153 | * 154 | * @return {Object} 155 | */ 156 | WooCommerceAPI.prototype._request = function(method, endpoint, data, callback) { 157 | var url = this._getUrl(endpoint); 158 | 159 | var params = { 160 | url: url, 161 | method: method, 162 | encoding: this.encoding, 163 | timeout: this.timeout, 164 | headers: { 165 | 'User-Agent': 'WooCommerce API Client-Node.js/' + this.classVersion, 166 | 'Accept': 'application/json' 167 | } 168 | }; 169 | 170 | // Allow a keep-alive (or other) agent 171 | if (this.agent) { 172 | params.agent = this.agent; 173 | } 174 | 175 | if (this.isSsl) { 176 | if (this.queryStringAuth) { 177 | params.qs = { 178 | consumer_key: this.consumerKey, 179 | consumer_secret: this.consumerSecret 180 | }; 181 | } else { 182 | params.auth = { 183 | user: this.consumerKey, 184 | pass: this.consumerSecret 185 | }; 186 | } 187 | 188 | if (!this.verifySsl) { 189 | params.strictSSL = false; 190 | } 191 | } else { 192 | params.qs = this._getOAuth().authorize({ 193 | url: url, 194 | method: method 195 | }); 196 | } 197 | 198 | if (data) { 199 | params.headers['Content-Type'] = 'application/json;charset=utf-8'; 200 | params.body = JSON.stringify(data); 201 | } 202 | 203 | if (!callback) { 204 | return request(params); 205 | } 206 | 207 | return request(params, callback); 208 | }; 209 | 210 | /** 211 | * GET requests 212 | * 213 | * @param {String} endpoint 214 | * @param {Function} callback 215 | * 216 | * @return {Object} 217 | */ 218 | WooCommerceAPI.prototype.get = function(endpoint, callback) { 219 | return this._request('GET', endpoint, null, callback); 220 | }; 221 | 222 | /** 223 | * POST requests 224 | * 225 | * @param {String} endpoint 226 | * @param {Object} data 227 | * @param {Function} callback 228 | * 229 | * @return {Object} 230 | */ 231 | WooCommerceAPI.prototype.post = function(endpoint, data, callback) { 232 | return this._request('POST', endpoint, data, callback); 233 | }; 234 | 235 | /** 236 | * PUT requests 237 | * 238 | * @param {String} endpoint 239 | * @param {Object} data 240 | * @param {Function} callback 241 | * 242 | * @return {Object} 243 | */ 244 | WooCommerceAPI.prototype.put = function(endpoint, data, callback) { 245 | return this._request('PUT', endpoint, data, callback); 246 | }; 247 | 248 | /** 249 | * DELETE requests 250 | * 251 | * @param {String} endpoint 252 | * @param {Function} callback 253 | * 254 | * @return {Object} 255 | */ 256 | WooCommerceAPI.prototype.delete = function(endpoint, callback) { 257 | return this._request('DELETE', endpoint, null, callback); 258 | }; 259 | 260 | /** 261 | * OPTIONS requests 262 | * 263 | * @param {String} endpoint 264 | * @param {Function} callback 265 | * 266 | * @return {Object} 267 | */ 268 | WooCommerceAPI.prototype.options = function(endpoint, callback) { 269 | return this._request('OPTIONS', endpoint, null, callback); 270 | }; 271 | 272 | /** 273 | * Promifying all requests exposing new methods 274 | * named [method]Async like in getAsync() 275 | */ 276 | promise.promisifyAll(WooCommerceAPI.prototype); 277 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "woocommerce-api", 3 | "description": "A Node.js wrapper for the WooCommerce REST API", 4 | "version": "1.5.0", 5 | "scripts": { 6 | "lint": "jshint .", 7 | "checkStyle": "jscs .", 8 | "pretest": "npm run-script lint && npm run-script checkStyle", 9 | "test": "istanbul cover ./node_modules/.bin/_mocha test.js", 10 | "posttest": "istanbul check-coverage --statements 85 --branches 70 --functions 100 --lines 90 && rm -rf coverage" 11 | }, 12 | "publishConfig": { 13 | "registry": "http://registry.npmjs.org" 14 | }, 15 | "author": "Claudio Sanches @ Automattic.com", 16 | "keywords": [ 17 | "woocommerce", 18 | "rest-api" 19 | ], 20 | "license": "MIT", 21 | "main": "index.js", 22 | "dependencies": { 23 | "bluebird": "3.5.5", 24 | "create-hmac": "1.1.7", 25 | "oauth-1.0a": "2.2.6", 26 | "request": "2.88.0" 27 | }, 28 | "devDependencies": { 29 | "chai": "^3.5.0", 30 | "istanbul": "^0.4.5", 31 | "jscs": "3.0.7", 32 | "jshint": "2.10.2", 33 | "mocha": "^3.1.0", 34 | "nock": "^8.0.0" 35 | }, 36 | "repository": { 37 | "type": "git", 38 | "url": "git@github.com:woocommerce/wc-api-node.git" 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /test.js: -------------------------------------------------------------------------------- 1 | var WooCommerce = require('./index.js'); 2 | var chai = require('chai'); 3 | var nock = require('nock'); 4 | var Agent = require('http').Agent; 5 | var HttpsAgent = require('https').Agent; 6 | var agent = new Agent(); 7 | var httpsAgent = new HttpsAgent(); 8 | 9 | describe('#Construct', function() { 10 | it('should throw an error if the url, consumerKey or consumerSecret are missing', function() { 11 | chai.expect(function() { 12 | new WooCommerce(); 13 | }).to.throw(Error); 14 | }); 15 | 16 | it('should set the default options', function() { 17 | var api = new WooCommerce({ 18 | url: 'http://test.dev', 19 | consumerKey: 'ck_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 20 | consumerSecret: 'cs_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 21 | wpAPI: true, 22 | version: 'wc/v1', 23 | agent: agent 24 | }); 25 | 26 | chai.expect(api.version).to.equal('wc/v1'); 27 | chai.expect(api.isSsl).to.be.false; 28 | chai.expect(api.verifySsl).to.be.true; 29 | chai.expect(api.encoding).to.equal('utf8'); 30 | chai.expect(api.agent).to.equal(agent); 31 | }); 32 | }); 33 | 34 | describe('#Requests', function() { 35 | beforeEach(function() { 36 | nock.cleanAll(); 37 | }); 38 | 39 | var api = new WooCommerce({ 40 | url: 'https://test.dev', 41 | consumerKey: 'ck_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 42 | consumerSecret: 'cs_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 43 | wpAPI: true, 44 | version: 'wc/v1', 45 | agent: httpsAgent 46 | }); 47 | 48 | it('should return full API url', function() { 49 | var endpoint = 'products'; 50 | var expected = 'https://test.dev/wp-json/wc/v1/products'; 51 | var url = api._getUrl(endpoint); 52 | 53 | chai.assert.equal(url, expected); 54 | }); 55 | 56 | it('should return full WP REST API url with a custom path', function() { 57 | var restApi = new WooCommerce({ 58 | url: 'https://test.dev', 59 | consumerKey: 'ck_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 60 | consumerSecret: 'cs_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 61 | wpAPI: true, 62 | wpAPIPrefix: 'wp-rest', 63 | version: 'wc/v1', 64 | agent: httpsAgent 65 | }); 66 | 67 | var endpoint = 'products'; 68 | var expected = 'https://test.dev/wp-rest/wc/v1/products'; 69 | var url = restApi._getUrl(endpoint); 70 | 71 | chai.assert.equal(url, expected); 72 | }); 73 | 74 | it('should return sorted by name query string', function() { 75 | var url = 'http://test.dev/wp-json/wc/v1/products?filter[q]=Woo+Album&fields=id&filter[limit]=1'; 76 | var expected = 'http://test.dev/wp-json/wc/v1/products?fields=id&filter[limit]=1&filter[q]=Woo%20Album'; 77 | var normalized = api._normalizeQueryString(url); 78 | 79 | chai.assert.equal(normalized, expected); 80 | }); 81 | 82 | it('should return content for basic auth', function(done) { 83 | nock('https://test.dev/wp-json/wc/v1').post('/orders', {}).reply(200, { 84 | ok: true 85 | }); 86 | 87 | api.post('orders', {}, function(err, data) { 88 | chai.expect(err).to.not.exist; 89 | chai.expect(data).be.a.string; 90 | done(); 91 | }); 92 | }); 93 | 94 | it('should return content for get requests', function(done) { 95 | nock('https://test.dev/wp-json/wc/v1').get('/orders').reply(200, { 96 | ok: true 97 | }); 98 | 99 | api.get('orders', function(err, data) { 100 | chai.expect(err).to.not.exist; 101 | chai.expect(data).be.a.string; 102 | done(); 103 | }); 104 | }); 105 | 106 | it('should return content for put requests', function(done) { 107 | nock('https://test.dev/wp-json/wc/v1').put('/orders', {}).reply(200, { 108 | ok: true 109 | }); 110 | 111 | api.put('orders', {}, function(err, data) { 112 | chai.expect(err).to.not.exist; 113 | chai.expect(data).be.a.string; 114 | done(); 115 | }); 116 | }); 117 | 118 | it('should return content for delete requests', function(done) { 119 | nock('https://test.dev/wp-json/wc/v1').delete('/orders').reply(200, { 120 | ok: true 121 | }); 122 | 123 | api.delete('orders', function(err, data) { 124 | chai.expect(err).to.not.exist; 125 | chai.expect(data).be.a.string; 126 | done(); 127 | }); 128 | }); 129 | 130 | it('should return content for options requests', function(done) { 131 | nock('https://test.dev/wp-json/wc/v1').intercept('/orders', 'OPTIONS').reply(400); 132 | 133 | api.options('orders', function(err, data) { 134 | chai.expect(err).to.not.exist; 135 | chai.expect(data).be.a.string; 136 | done(); 137 | }); 138 | }); 139 | 140 | it('should return a promise for getAsync requests', function(done) { 141 | nock('https://test.dev/wp-json/wc/v1').get('/orders').reply(200, { 142 | ok: true 143 | }); 144 | 145 | api.getAsync('orders').finally(function(data) { 146 | chai.expect(data).be.a.string; 147 | done(); 148 | }); 149 | }); 150 | 151 | it('should return a promise for postAsync requests', function(done) { 152 | nock('https://test.dev/wp-json/wc/v1').post('/orders', {}).reply(200, { 153 | ok: true 154 | }); 155 | 156 | api.postAsync('orders', {}).finally(function(data) { 157 | chai.expect(data).be.a.string; 158 | done(); 159 | }); 160 | }); 161 | 162 | it('should return a promise for putAsync requests', function(done) { 163 | nock('https://test.dev/wp-json/wc/v1').put('/orders', {}).reply(200, { 164 | ok: true 165 | }); 166 | 167 | api.putAsync('orders', {}).finally(function(data) { 168 | chai.expect(data).be.a.string; 169 | done(); 170 | }); 171 | }); 172 | 173 | it('should return a promise for deleteAsync requests', function(done) { 174 | nock('https://test.dev/wp-json/wc/v1').delete('/orders').reply(200, { 175 | ok: true 176 | }); 177 | 178 | api.deleteAsync('orders').finally(function(data) { 179 | chai.expect(data).be.a.string; 180 | done(); 181 | }); 182 | }); 183 | 184 | it('should return a promise for optionsAsync requests', function(done) { 185 | nock('https://test.dev/wp-json/wc/v1').intercept('/orders', 'OPTIONS').reply(400); 186 | 187 | api.optionsAsync('orders').finally(function(data) { 188 | chai.expect(data).be.a.string; 189 | done(); 190 | }); 191 | }); 192 | 193 | it('should return content for OAuth', function(done) { 194 | var oAuth = new WooCommerce({ 195 | url: 'http://test.dev', 196 | consumerKey: 'ck_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 197 | consumerSecret: 'cs_XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX', 198 | wpAPI: true, 199 | version: 'wc/v1' 200 | }); 201 | 202 | nock('http://test.dev/wp-json/wc/v1').filteringPath(/\?.*/, '?params').get('/orders?params').reply(200, { 203 | ok: true 204 | }); 205 | 206 | oAuth.get('orders', function(err, data) { 207 | chai.expect(err).to.not.exist; 208 | chai.expect(data).be.a.string; 209 | done(); 210 | }); 211 | }); 212 | }); 213 | --------------------------------------------------------------------------------