diff --git a/.gitignore b/.gitignore
index c564040..c727bb7 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,2 +1,3 @@
+node_modules
 .idea
-node_modules/
\ No newline at end of file
+.DS_Store
diff --git a/.travis.yml b/.travis.yml
new file mode 100644
index 0000000..06e77f9
--- /dev/null
+++ b/.travis.yml
@@ -0,0 +1,12 @@
+language: node_js
+node_js:
+- '5.1.0'
+install: 
+- 'npm install'
+- 'npm -g install mocha'
+script: 
+- 'mocha tests --bail --target=2.1'
+notifications:
+  email:
+    on_failure: change
+    on_success: change
\ No newline at end of file
diff --git a/LICENSE b/LICENSE
index 1c1b5ee..d955a86 100644
--- a/LICENSE
+++ b/LICENSE
@@ -1,326 +1,11 @@
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
 
-Apache Usergrid itself is licensed under the terms of the Apache License:
+    http://www.apache.org/licenses/LICENSE-2.0
 
-                                 Apache License
-                           Version 2.0, January 2004
-                        http://www.apache.org/licenses/
-
-   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
-
-   1. Definitions.
-
-      "License" shall mean the terms and conditions for use, reproduction,
-      and distribution as defined by Sections 1 through 9 of this document.
-
-      "Licensor" shall mean the copyright owner or entity authorized by
-      the copyright owner that is granting the License.
-
-      "Legal Entity" shall mean the union of the acting entity and all
-      other entities that control, are controlled by, or are under common
-      control with that entity. For the purposes of this definition,
-      "control" means (i) the power, direct or indirect, to cause the
-      direction or management of such entity, whether by contract or
-      otherwise, or (ii) ownership of fifty percent (50%) or more of the
-      outstanding shares, or (iii) beneficial ownership of such entity.
-
-      "You" (or "Your") shall mean an individual or Legal Entity
-      exercising permissions granted by this License.
-
-      "Source" form shall mean the preferred form for making modifications,
-      including but not limited to software source code, documentation
-      source, and configuration files.
-
-      "Object" form shall mean any form resulting from mechanical
-      transformation or translation of a Source form, including but
-      not limited to compiled object code, generated documentation,
-      and conversions to other media types.
-
-      "Work" shall mean the work of authorship, whether in Source or
-      Object form, made available under the License, as indicated by a
-      copyright notice that is included in or attached to the work
-      (an example is provided in the Appendix below).
-
-      "Derivative Works" shall mean any work, whether in Source or Object
-      form, that is based on (or derived from) the Work and for which the
-      editorial revisions, annotations, elaborations, or other modifications
-      represent, as a whole, an original work of authorship. For the purposes
-      of this License, Derivative Works shall not include works that remain
-      separable from, or merely link (or bind by name) to the interfaces of,
-      the Work and Derivative Works thereof.
-
-      "Contribution" shall mean any work of authorship, including
-      the original version of the Work and any modifications or additions
-      to that Work or Derivative Works thereof, that is intentionally
-      submitted to Licensor for inclusion in the Work by the copyright owner
-      or by an individual or Legal Entity authorized to submit on behalf of
-      the copyright owner. For the purposes of this definition, "submitted"
-      means any form of electronic, verbal, or written communication sent
-      to the Licensor or its representatives, including but not limited to
-      communication on electronic mailing lists, source code control systems,
-      and issue tracking systems that are managed by, or on behalf of, the
-      Licensor for the purpose of discussing and improving the Work, but
-      excluding communication that is conspicuously marked or otherwise
-      designated in writing by the copyright owner as "Not a Contribution."
-
-      "Contributor" shall mean Licensor and any individual or Legal Entity
-      on behalf of whom a Contribution has been received by Licensor and
-      subsequently incorporated within the Work.
-
-   2. Grant of Copyright License. Subject to the terms and conditions of
-      this License, each Contributor hereby grants to You a perpetual,
-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
-      copyright license to reproduce, prepare Derivative Works of,
-      publicly display, publicly perform, sublicense, and distribute the
-      Work and such Derivative Works in Source or Object form.
-
-   3. Grant of Patent License. Subject to the terms and conditions of
-      this License, each Contributor hereby grants to You a perpetual,
-      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
-      (except as stated in this section) patent license to make, have made,
-      use, offer to sell, sell, import, and otherwise transfer the Work,
-      where such license applies only to those patent claims licensable
-      by such Contributor that are necessarily infringed by their
-      Contribution(s) alone or by combination of their Contribution(s)
-      with the Work to which such Contribution(s) was submitted. If You
-      institute patent litigation against any entity (including a
-      cross-claim or counterclaim in a lawsuit) alleging that the Work
-      or a Contribution incorporated within the Work constitutes direct
-      or contributory patent infringement, then any patent licenses
-      granted to You under this License for that Work shall terminate
-      as of the date such litigation is filed.
-
-   4. Redistribution. You may reproduce and distribute copies of the
-      Work or Derivative Works thereof in any medium, with or without
-      modifications, and in Source or Object form, provided that You
-      meet the following conditions:
-
-      (a) You must give any other recipients of the Work or
-          Derivative Works a copy of this License; and
-
-      (b) You must cause any modified files to carry prominent notices
-          stating that You changed the files; and
-
-      (c) You must retain, in the Source form of any Derivative Works
-          that You distribute, all copyright, patent, trademark, and
-          attribution notices from the Source form of the Work,
-          excluding those notices that do not pertain to any part of
-          the Derivative Works; and
-
-      (d) If the Work includes a "NOTICE" text file as part of its
-          distribution, then any Derivative Works that You distribute must
-          include a readable copy of the attribution notices contained
-          within such NOTICE file, excluding those notices that do not
-          pertain to any part of the Derivative Works, in at least one
-          of the following places: within a NOTICE text file distributed
-          as part of the Derivative Works; within the Source form or
-          documentation, if provided along with the Derivative Works; or,
-          within a display generated by the Derivative Works, if and
-          wherever such third-party notices normally appear. The contents
-          of the NOTICE file are for informational purposes only and
-          do not modify the License. You may add Your own attribution
-          notices within Derivative Works that You distribute, alongside
-          or as an addendum to the NOTICE text from the Work, provided
-          that such additional attribution notices cannot be construed
-          as modifying the License.
-
-      You may add Your own copyright statement to Your modifications and
-      may provide additional or different license terms and conditions
-      for use, reproduction, or distribution of Your modifications, or
-      for any such Derivative Works as a whole, provided Your use,
-      reproduction, and distribution of the Work otherwise complies with
-      the conditions stated in this License.
-
-   5. Submission of Contributions. Unless You explicitly state otherwise,
-      any Contribution intentionally submitted for inclusion in the Work
-      by You to the Licensor shall be under the terms and conditions of
-      this License, without any additional terms or conditions.
-      Notwithstanding the above, nothing herein shall supersede or modify
-      the terms of any separate license agreement you may have executed
-      with Licensor regarding such Contributions.
-
-   6. Trademarks. This License does not grant permission to use the trade
-      names, trademarks, service marks, or product names of the Licensor,
-      except as required for reasonable and customary use in describing the
-      origin of the Work and reproducing the content of the NOTICE file.
-
-   7. Disclaimer of Warranty. Unless required by applicable law or
-      agreed to in writing, Licensor provides the Work (and each
-      Contributor provides its Contributions) on an "AS IS" BASIS,
-      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
-      implied, including, without limitation, any warranties or conditions
-      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
-      PARTICULAR PURPOSE. You are solely responsible for determining the
-      appropriateness of using or redistributing the Work and assume any
-      risks associated with Your exercise of permissions under this License.
-
-   8. Limitation of Liability. In no event and under no legal theory,
-      whether in tort (including negligence), contract, or otherwise,
-      unless required by applicable law (such as deliberate and grossly
-      negligent acts) or agreed to in writing, shall any Contributor be
-      liable to You for damages, including any direct, indirect, special,
-      incidental, or consequential damages of any character arising as a
-      result of this License or out of the use or inability to use the
-      Work (including but not limited to damages for loss of goodwill,
-      work stoppage, computer failure or malfunction, or any and all
-      other commercial damages or losses), even if such Contributor
-      has been advised of the possibility of such damages.
-
-   9. Accepting Warranty or Additional Liability. While redistributing
-      the Work or Derivative Works thereof, You may choose to offer,
-      and charge a fee for, acceptance of support, warranty, indemnity,
-      or other liability obligations and/or rights consistent with this
-      License. However, in accepting such obligations, You may act only
-      on Your own behalf and on Your sole responsibility, not on behalf
-      of any other Contributor, and only if You agree to indemnify,
-      defend, and hold each Contributor harmless for any liability
-      incurred by, or claims asserted against, such Contributor by reason
-      of your accepting any such warranty or additional liability.
-
-   END OF TERMS AND CONDITIONS
-
-   APPENDIX: How to apply the Apache License to your work.
-
-      To apply the Apache License to your work, attach the following
-      boilerplate notice, with the fields enclosed by brackets "[]"
-      replaced with your own identifying information. (Don't include
-      the brackets!)  The text should be enclosed in the appropriate
-      comment syntax for the file format. We also recommend that a
-      file or class name and description of purpose be included on the
-      same "printed page" as the copyright notice for easier
-      identification within third-party archives.
-
-   Copyright [yyyy] [name of copyright owner]
-
-   Licensed under the Apache License, Version 2.0 (the "License");
-   you may not use this file except in compliance with the License.
-   You may obtain a copy of the License at
-
-       http://www.apache.org/licenses/LICENSE-2.0
-
-   Unless required by applicable law or agreed to in writing, software
-   distributed under the License is distributed on an "AS IS" BASIS,
-   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-   See the License for the specific language governing permissions and
-   limitations under the License.
-
-------------------------------------------------------------------------------
-
-USERGRID SUBCOMPONENTS
-
-The Usergrid software includes a number of subcomponents with separate
-copyrights and license terms. Your use of the source code for these 
-subcomponents is subject to the terms and conditions of the following 
-licenses. 
-
-IOS SDK
--------
-For the SBJson component:
- 
- Copyright (c) Stig Brautaset. All rights reserved.
- 
- Redistribution and use in source and binary forms, with or without
- modification, are permitted provided that the following conditions are met:
- 
- * Redistributions of source code must retain the above copyright notice, this
-   list of conditions and the following disclaimer.
- 
- * Redistributions in binary form must reproduce the above copyright notice,
-   this list of conditions and the following disclaimer in the documentation
-   and/or other materials provided with the distribution.
- 
- * Neither the name of the author nor the names of its contributors may be used
-   to endorse or promote products derived from this software without specific
-   prior written permission.
- 
- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
- AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
- FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
- SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
- CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
- OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-
-For the SSKeychain component:
------------------------------
-
- Copyright (c) Sam Soffes, http://soff.es
-
- Permission is hereby granted, free of charge, to any person obtaining
- a copy of this software and associated documentation files (the
- "Software"), to deal in the Software without restriction, including
- without limitation the rights to use, copy, modify, merge, publish,
- distribute, sublicense, and/or sell copies of the Software, and to
- permit persons to whom the Software is furnished to do so, subject to
- the following conditions:
-
- The above copyright notice and this permission notice shall be
- included in all copies or substantial portions of the Software.
-
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-
-Other components:
------------------
-
-This product bundles angular.js
-Copyright(c) Google, Inc. Released under the MIT license.
-
-This product bundles angular-scenario.js, part of jQuery JavaScript Library
-which Includes Sizzle.js Copyright (c) jQuery Foundation, Inc. and others.
-Released under the MIT license.
-
-This product bundles Bootstrap Copyright (c) Twitter, Inc
-Licensed under the MIT license.
-
-The product bundles Intro.js (MIT licensed)
-Copyright (c) usabli.ca - A weekend project by Afshin Mehrabani (@afshinmeh)
-
-This product bundles jQuery
-Licensed under MIT license.
-
-This product bundles jQuery-UI
-Licensed under MIT license.
-
-This product bundles jQuery Sparklines (New BSD License)
-Copyright (c) Splunk Inc.
-
-This product bundles Mocha.
-All rights reserved. Licensed under MIT.
-Copyright (c) TJ Holowaychuk <tj@vision-media.ca>
-
-This product bundles NewtonSoft.Json under MIT license
-
-This product bundles NPM MD5 (BSD-3 licensed)
-Copyright (c) Paul Vorbach and Copyright (C), Jeff Mott.
-
-This product bundles NSubsttute under BSD license
-
-This product bundles SBJson, which is available under a "3-clause BSD" license.
-For details, see sdks/ios/UGAPI/SBJson/ .
-
-This product bundles Sphinx under BSD license
-
-This product bundles SSKeychain, which is available under a "MIT/X11" license.
-For details, see sdks/ios/UGAPI/SSKeychain/.
-
-This product bundles SSToolkit.
-Copyright (c) Sam Soffes. All rights reserved.
-These files can be located within the /sdks/ios package.
-
-This product bundles Entypo, CC by SA license
-
-This product bundles date.min.js, MIT license
-
-This product bundles jquery.ui.timepicker.min.js, MIT license
-
-This product bundles blanket_mocha.min.js, MIT license
-
-This product bundles FontAwesome, SIL Open Font License
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
\ No newline at end of file
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..65f8329
--- /dev/null
+++ b/README.md
@@ -0,0 +1,778 @@
+[![Codacy Badge](https://api.codacy.com/project/badge/grade/034bc34302b646bf932c7c0307e0e313)](https://www.codacy.com/app/brandonscript/usergrid-nodejs)
+[![Travis CI Badge](https://travis-ci.org/brandonscript/usergrid-nodejs.svg?branch=master)](https://travis-ci.org/brandonscript/usergrid-nodejs)
+[![npm version](https://badge.fury.io/js/usergrid.svg)](https://badge.fury.io/js/usergrid)
+
+# usergrid-nodejs
+Node.js SDK 2.0 for Usergrid 
+
+Version 2.0 of this SDK is currently a work in progress; documentation and implementation are subject to change.
+
+_**Note:** This Node.js SDK 2.0 for Usergrid is **not** backwards compatible with 0.1X versions of the SDK. If your application is dependent on the 0.1X set of Node.js APIs, you will need to continue using the 0.1X version (see below for installation instructions)._
+
+## Current Release
+
+- Pre-release: [2.0 Release Candidate 2](https://github.com/brandonscript/usergrid-nodejs/releases), available here or on npm
+- Stable: [0.10.11](https://github.com/apache/usergrid/tree/master/sdks/nodejs)
+ 
+## 2.X Bugs
+
+Please open an [issue](https://github.com/brandonscript/usergrid-nodejs/issues/new)
+
+## Known Issues
+
+- Native support for push notifications is slated for RC3. Workaround is to send a regular POST request to `'devices/<device_ID>/notifications'`
+- There is no clean way to require submodules (e.g. `UsergridClient` or `UsergridEntity`) modules without referencing the full path to `../lib/<class>`.
+- Any other functionality that is missing or expected, please open an issue.
+
+## Installation
+
+To install the latest **stable** 0.1X build:
+
+    npm install usergrid
+
+(Or add `"usergrid": "~0.10.11"` to your package.json)
+
+To install the 2.0 release candidates, install from [npm](https://www.npmjs.com/package/usergrid), specifying the version `~2.0.0-rc`:
+
+    npm install usergrid@~2.0.0-rc
+
+(Or add `"usergrid": "~2.0.0-rc"` to your package.json)
+
+If you want access to the latest development build (you will need to run `npm install` to keep it up to date):
+
+    npm install brandonscript/usergrid-nodejs
+
+## Usage
+
+_**Note:** This section is a work in progress. In its current release candidate state, this SDK is only recommended for developers familiar with Usergrid, Node.js, and ideally Mocha tests. It is not recommended for production applications. For additional advanced/comprehensive usage, see `/tests`._
+
+The Usergrid Node.js SDK is built on top of [request](https://github.com/request/request). As such, it behaves almost as a drop-in replacement. Where you would expect a standard error-first callback from request, the same is true of the Usergrid SDK methods. Where you would expect a response object as the second parameter in the callback, the same is true for the Usergrid SDK.
+
+
+### Initialization
+
+There are two different ways of initializing the Usergrid Node.js SDK: 
+
+1. The singleton pattern is both convenient and enables the developer to use a globally available and always-initialized shared instance of Usergrid. 
+
+	```js
+	var Usergrid = require('usergrid')
+	Usergrid.init({
+	    orgId: '<org-id>',
+	    appId: '<app-id>'
+	})
+	    
+	// or you can load from a config file; see config.sample.json
+	    
+	var Usergrid = require('usergrid')
+	Usergrid.init() // defaults to use config.json
+	```
+**Config File:**  Optionally, you can use a config file to provide the usergrid credentials for your app.  The usergrid module crawls your App file structure to find files named `usergrid.json` or a `config.json`.  If there are multiple files with one of these names present at different locations under the app, only one of them will be used and the others are ignored.  This may cause use of an unintended backend.  Please make sure you have only one of these files present in the root and subdirectories of your app.
+
+2. The instance pattern enables the developer to manage instances of the Usergrid client independently and in an isolated fashion. The primary use-case for this is when an application connects to multiple Usergrid targets.
+
+	```js
+	var UsergridClient = require('./node_modules/usergrid/lib/client')
+	var client = new UsergridClient(config)
+	```
+
+_**Note:** Examples in this readme assume you are using the `Usergrid` shared instance. If you've implemented the instance pattern instead, simply replace `Usergrid` with your client instance variable. See `/tests` for additional examples._
+
+## RESTful operations
+
+When making any RESTful call, a `type` parameter (or `path`) is always required. Whether you specify this as an argument, in an object as a parameter, or as part of a `UsergridQuery` object is up to you.
+
+### GET()
+
+To get entities in a collection:
+
+```js
+Usergrid.GET('collection', function(error, usergridResponse, entities) {
+    // entities is an array of UsergridEntity objects
+})
+```
+    
+To get a specific entity in a collection by uuid or name:
+
+```js
+Usergrid.GET('collection', '<uuid-or-name>', function(error, usergridResponse, entity) {
+    // entity, if found, is a UsergridEntity object
+})
+```
+    
+To get specific entities in a collection by passing a UsergridQuery object:
+
+```js
+var query = new UsergridQuery('cats')
+                             .gt('weight', 2.4)
+                             .contains('color', 'bl*')
+                             .not
+                             .eq('color', 'blue')
+                             .or
+                             .eq('color', 'orange')
+                             
+// this will build out the following query:
+// select * where weight > 2.4 and color contains 'bl*' and not color = 'blue' or color = 'orange'
+    
+Usergrid.GET(query, function(error, usergridResponse) {
+    // entities is an array of UsergridEntity objects matching the specified query
+})
+```
+    
+### POST() and PUT()
+
+POST and PUT requests both require a JSON body payload. You can pass either a standard JavaScript object or a `UsergridEntity` instance. While the former works in principle, best practise is to use a `UsergridEntity` wherever practical. When an entity has a uuid or name property and already exists on the server, use a PUT request to update it. If it does not, use POST to create it.
+
+To create a new entity in a collection (POST):
+
+```js
+var entity = new UsergridEntity({
+    type: 'restaurant',
+    restaurant: 'Dino's Deep Dish,
+    cuisine: 'pizza'
+})
+    
+// or
+    
+var entity = {
+    type: 'restaurant',
+    restaurant: 'Dino's Deep Dish,
+    cuisine: 'pizza'
+}
+    
+Usergrid.POST(entity, function(error, usergridResponse, entity) {
+    // entity should now have a uuid property and be created
+})
+    
+// you can also POST an array of entities:
+
+var entities = [
+    new UsergridEntity({
+        type: 'restaurant',
+        restaurant: 'Dino's Deep Dish,
+        cuisine: 'pizza'
+    }), 
+    new UsergridEntity({
+        type: 'restaurant',
+        restaurant: 'Pizza da Napoli',
+        cuisine: 'pizza'
+    })
+]
+    
+Usergrid.POST(entities, function(error, usergridResponse, entities) {
+    //
+})
+```
+    
+To update an entity in a collection (PUT request):
+
+```js
+var entity = new UsergridEntity({
+    type: 'restaurant',
+    restaurant: 'Pizza da Napoli',
+    cuisine: 'pizza'
+})
+    
+Usergrid.POST(entity, function(error, usergridResponse, entity) {
+    entity.owner = 'Mia Carrara'
+    Usergrid.PUT(entity, function(error, usergridResponse, entity) {
+        // entity now has the property 'owner'
+    })
+})
+    
+// or update a set of entities by passing a UsergridQuery object
+    
+var query = new UsergridQuery('restaurants')
+                             .eq('cuisine', 'italian')
+                             
+// this will build out the following query:
+// select * where cuisine = 'italian'
+    
+Usergrid.PUT(query, { keywords: ['pasta'] }, function(error, usergridResponse) {
+    /* the first 10 entities matching this query criteria will be updated:
+       e.g.:
+       [
+           {
+               "type": "restaurant",
+               "restaurant": "Il Tarazzo",
+               "cuisine": "italian",
+               "keywords": [
+                   "pasta"
+               ]
+           },
+           {
+               "type": "restaurant",
+               "restaurant": "Cono Sur Pizza & Pasta",
+               "cuisine": "italian",
+               "keywords": [
+                   "pasta"
+               ]
+           }
+        ]
+    */
+})
+```
+    
+### DELETE()
+
+DELETE requests require either a specific entity or a `UsergridQuery` object to be passed as an argument.
+    
+To delete a specific entity in a collection by uuid or name:
+
+```js
+Usergrid.DELETE('collection', '<uuid-or-name>', function(error, usergridResponse) {
+    // if successful, entity will now be deleted
+})
+```
+    
+To specific entities in a collection by passing a `UsergridQuery` object:
+
+```js
+var query = new UsergridQuery('cats')
+                             .eq('color', 'black')
+                             .or
+                             .eq('color', 'white')
+                             
+// this will build out the following query:
+// select * where color = 'black' or color = 'white'
+    
+Usergrid.DELETE(query, function(error, usergridResponse) {
+    // the first 10 entities matching this query criteria will be deleted
+})
+```
+
+## Entity operations and convenience methods
+
+`UsergridEntity` has a number of helper/convenience methods to make working with entities more convenient. If you are _not_ utilizing the `Usergrid` shared instance, you must pass an instance of `UsergridClient` as the first argument to any of these helper methods.
+
+### reload()
+
+Reloads the entity from the server
+
+```js
+entity.reload(function(error, usergridResponse) {
+    // entity is now reloaded from the server
+})
+```
+    
+### save()
+
+Saves (or creates) the entity on the server
+
+```js
+entity.aNewProperty = 'A new value'
+entity.save(function(error, usergridResponse) {
+    // entity is now updated on the server
+})
+```
+    
+### remove()
+
+Deletes the entity from the server
+
+```js
+entity.remove(function(error, usergridResponse) {
+    // entity is now deleted on the server and the local instance should be destroyed
+})
+```
+    
+## Authentication, current user, and authMode
+
+### appAuth and authenticateApp()
+
+`Usergrid` can use the app client ID and secret that were passed upon initialization and automatically retrieve an app-level token for these credentials.
+
+```js
+Usergrid.setAppAuth('<client-id>', '<client-secret>')
+Usergrid.authenticateApp(function(error, usergridResponse, token) {
+    // Usergrid.appAuth is created automatically when this call is successful
+})
+```
+
+### currentUser and authenticateUser()
+
+`Usergrid` has a special `currentUser` property. By default, when calling `authenticateUser()`, `.currentUser` will be set to this user if the authentication flow is successful.
+
+```js
+Usergrid.authenticateUser({
+    username: '<username>',
+    password: '<password>'
+}, function(error, usergridResponse, token) {
+    // Usergrid.currentUser is set to the authenticated user and the token is stored within that context
+})
+```
+    
+If you want to utilize authenticateUser without setting as the current user, simply pass a `false` boolean value as the second parameter:
+
+```js
+Usergrid.authenticateUser({
+    username: '<username>',
+    password: '<password>'
+}, false, function(error, usergridResponse, token) {
+    
+})
+```
+
+### authMode
+
+Auth-mode is used to determine what the `UsergridClient` will use for authorization.
+
+By default, `Usergrid.authMode` is set to `UsergridAuth.AUTH_MODE_USER`, whereby if a non-expired `UsergridUserAuth` exists in `UsergridClient.currentUser`, this token is used to authenticate all API calls.
+
+If instead `Usergrid.authMode` is set to `UsergridAuth.AUTH_MODE_NONE`, all API calls will be performed unauthenticated. 
+
+If instead `Usergrid.authMode` is set to `UsergridAuth.AUTH_MODE_APP`, all API calls will be performed using the client credentials token, _if_ they're available (i.e. `authenticateApp()` was performed at some point). 
+
+### usingAuth()
+
+At times it is desireable to have complete, granular control over the authentication context of an API call. To facilitate this, the passthrough function `.usingAuth()` allows you to pre-define the auth context of the next API call.
+
+```js
+// assume Usergrid.authMode = UsergridAuth.AUTH_MODE_NONE
+    
+Usergrid.usingAuth(Usergrid.appAuth).POST('roles/guest/permissions', {
+    permission: "get,post,put,delete:/**"
+}, function(error, usergridResponse) {
+    // here we've temporarily used the client credentials to modify permissions
+    // subsequent calls will not use this auth context
+})
+```
+    
+## User operations and convenience methods
+
+`UsergridUser` has a number of helper/convenience methods to make working with user entities more convenient. If you are _not_ utilizing the `Usergrid` shared instance, you must pass an instance of `UsergridClient` as the first argument to any of these helper methods.
+    
+### create()
+
+Creating a new user:
+
+```js
+var user = new UsergridUser({
+    username: 'username',
+    password: 'password'
+})
+    
+user.create(function(error, usergridResponse, user) {
+    // user has now been created and should have a valid uuid
+})
+```
+    
+### login()
+
+A simpler means of retrieving a user-level token:
+
+```js
+var user = new UsergridUser({
+    username: 'username',
+    password: 'password'
+})
+    
+user.login(function(error, usergridResponse, token) {
+    // user is now logged in
+})
+```
+
+### logout()
+
+Logs out the selected user. You can also use this convenience method on `Usergrid.currentUser`.
+
+```js
+user.logout(function(error, usergridResponse) {
+    // user is now logged out
+})
+```
+    
+### logoutAllSessions()
+
+Logs out all sessions for the selected user and destroys all active tokens. You can also use this convenience method on `Usergrid.currentUser`.
+
+```js
+user.logoutAllSessions(function(error, usergridResponse) {
+    // user is now logged out from everywhere
+})
+```
+    
+### resetPassword()
+
+Resets the password for the selected user.
+
+```js
+user.resetPassword({
+    oldPassword: '2cool4u',
+    newPassword: 'correct-horse-battery-staple',
+}, function(error, response, success) {
+    // if it was done correctly, the new password will be changed
+    // 'success' is a boolean value that indicates whether it was changed successfully
+})
+```
+    
+### UsergridUser.CheckAvailable()
+
+This is a class (static) method that allows you to check whether a username or email address is available or not.
+
+```js
+UsergridUser.CheckAvailable(client, {
+    email: 'email'
+}, function(err, response, exists) {
+   // 'exists' is a boolean value that indicates whether a user already exists
+})
+    
+UsergridUser.CheckAvailable(client, {
+    username: 'username'
+}, function(err, response, exists) {
+   
+})
+    
+UsergridUser.CheckAvailable(client, {
+    email: 'email',
+    username: 'username', // checks both email and username
+}, function(err, response, exists) {
+    // 'exists' returns true if either username or email exist
+})
+```
+    
+## Querying and filtering data
+
+### UsergridQuery initialization
+
+The `UsergridQuery` class allows you to build out complex query filters using the Usergrid [query syntax](http://docs.apigee.com/app-services/content/querying-your-data).
+
+The first parameter of the `UsergridQuery` builder pattern should be the collection (or type) you intend to query. You can either pass this as an argument, or as the first builder object:
+
+```js
+var query = new UsergridQuery('cats')
+// or
+var query = new UsergridQuery().type('cats')
+var query = new UsergridQuery().collection('cats')
+```
+
+You then can layer on additional queries:
+
+```js
+var query = new UsergridQuery('cats')
+            .gt('weight', 2.4)
+            .contains('color', 'bl*')
+            .not
+            .eq('color', 'white')
+            .or
+            .eq('color', 'orange') 
+```
+            
+You can also adjust the number of results returned:
+
+```js
+var query = new UsergridQuery('cats').eq('color', 'black').limit(100)
+// returns a maximum of 100 entiteis
+```
+    
+And sort the results:
+
+```js
+var query = new UsergridQuery('cats').eq('color', 'black').asc('name')
+// sorts by 'name', ascending
+```
+    
+And you can do geo-location queries:
+
+```js
+var query = new UsergridQuery('devices').locationWithin(<distanceInMeters>, <latitude>, <longitude>)
+```
+    
+### Using a query in a request
+
+Queries can be passed as parameters to GET, PUT, and DELETE requests:
+
+```js
+Usergrid.GET(query, function(error, usergridResponse, entities) {
+    //
+})
+    
+Usergrid.PUT(query, { aNewProperty: "A new value" }, function(error, usergridResponse, entities) {
+    //
+})
+    
+Usergrid.DELETE(query, function(error, usergridResponse, entities) {
+    //
+})
+```
+    
+While not a typical use case, sometimes it is useful to be able to create a query that works on multiple collections. Therefore, in each one of these RESTful calls, you can optionally pass a 'type' string as the first argument:
+
+```js
+Usergrid.GET('cats', query, function(error, usergridResponse, entities) {
+    //
+})
+```
+    
+### List of query builder objects
+
+`type('string')`
+
+> The collection name to query
+
+`collection('string')`
+
+> An alias for `type`
+
+`eq('key', 'value')` or `equal('key', 'value')`
+
+> Equal to (e.g. `where color = 'black'`)
+
+`contains('key', 'value')`
+
+> Contains a string (e.g.` where color contains 'bl*'`)
+
+`gt('key', 'value')` or `greaterThan('key', 'value')`
+
+> Greater than (e.g. `where weight > 2.4`)
+
+`gte('key', 'value')` or `greaterThanOrEqual('key', 'value')`
+
+> Greater than or equal to (e.g. `where weight >= 2.4`)
+
+`lt('key', 'value')` or `lessThan('key', 'value')`
+
+> Less than (e.g. `where weight < 2.4`)
+
+`lte('key', 'value')` or `lessThanOrEqual('key', 'value')`
+
+> Less than or equal to (e.g. `where weight <= 2.4`)
+
+`not`
+
+> Negates the next block in the builder pattern, e.g.:
+
+```js
+var query = new UsergridQuery('cats').not.eq('color', 'black')
+// select * from cats where not color = 'black'
+```
+
+`and`
+
+> Joins two queries by requiring both of them. `and` is also implied when joining two queries _without_ an operator. E.g.:
+
+```js
+var query = new UsergridQuery('cats').eq('color', 'black').eq('fur', 'longHair')
+// is identical to:
+var query = new UsergridQuery('cats').eq('color', 'black').and.eq('fur', 'longHair')  
+```
+
+`or`
+
+> Joins two queries by requiring only one of them. `or` is never implied. E.g.:
+
+```js
+var query = new UsergridQuery('cats').eq('color', 'black').or.eq('color', 'white')
+```
+    
+> When using `or` and `and` operators, `and` joins will take precedence over `or` joins. You can read more about query operators and precedence [here](http://docs.apigee.com/api-baas/content/supported-query-operators-data-types).
+
+`locationWithin(distanceInMeters, latitude, longitude)`
+
+> Returns entities which have a location within the specified radius. Arguments can be `float` or `int`.
+
+`asc('key')`
+
+> Sorts the results by the specified property, ascending
+
+`desc('key')`
+
+> Sorts the results by the specified property, descending
+
+`sort('key', 'order')`
+
+> Sorts the results by the specified property, in the specified order (`asc` or `desc`).
+ 
+`limit(int)`
+
+> The maximum number of entities to return
+
+`cursor('string')`
+
+> A pagination cursor string
+
+`fromString('query string')`
+
+> A special builder property that allows you to input a pre-defined query string. All other builder properties will be ignored when this property is defined. For example:
+    
+```js
+var query = new UsergridQuery().fromString("select * where color = 'black' order by name asc")
+```
+
+## UsergridResponse object
+
+`UsergridResponse` implements several Usergrid-specific enhancements to [request](https://github.com/request/request). Notably:
+
+### ok
+
+You can check `usergridResponse.ok`, a `bool` value, to see if the response was successful. Any status code < 400 returns true.
+
+```js
+Usergrid.GET('collection', function(error, usergridResponse, entities) {
+    if (usergridResponse.ok) {
+        // woo!
+    }
+})
+```
+    
+### entity, entities, user, users, first, last
+
+Depending on the call you make, you will receive either an array of UsergridEntity objects, or a single entity as the third parameter in the callback. If you're querying the `users` collection, these will also be `UsergridUser` objects, a subclass of `UsergridEntity`.
+
+- `.first` returns the first entity in an array of entities; `.entity` is an alias to `.first`. If there are no entities, both of these will be undefined.
+- `.last` returns the last entity in an array of entities; if there is only one entity in the array, this will be the same as `.first` _and_ `.entity`, and will be undefined if there are no entities in the response.
+- `.entities` will either be an array of entities in the response, or an empty array.
+- `.user` is a special alias for `.entity` for when querying the `users` collection. Instead of being a `UsergridEntity`, it will be its subclass, `UsergridUser`.
+- `.users` is the same as `.user`, though behaves as `.entities` does by returning either an array of UsergridUser objects or an empty array.
+
+Examples:
+
+```js
+Usergrid.GET('collection', function(error, usergridResponse, entities) {
+    // third param is an array of entities because no specific entity was referenced
+    // you can also access:
+    //     usergridResponse.entities
+    //     usergridResponse.first    
+    //     usergridResponse.entity (the first entity)      
+    //     usergridResponse.last		 
+})
+    
+Usergrid.GET('collection', '<uuid or name>', function(error, usergridResponse, entity) {
+    // third param is a single entity object
+    // you can also access:
+    //     usergridResponse.entity
+    //     usergridResponse.first  
+    //     usergridResponse.last                
+})
+    
+Usergrid.GET('users', function(error, usergridResponse, users) {
+    // third param is an array of users because no specific user was referenced
+    // you can also access:
+    //     usergridResponse.users
+    //     usergridResponse.user (the first user)          
+    //     usergridResponse.last 
+})
+    
+Usergrid.GET('users', '<uuid, username, or email>', function(error, usergridResponse, user) {
+    // third param is a single user object
+    // you can also access:
+    //     usergridResponse.user
+})
+```
+    
+## Connections
+
+Connections can be managed using `Usergrid.connect()`, `Usergrid.disconnect()`, and `Usergrid.getConnections()`, or entity convenience methods of the same name.
+
+### connect
+
+Create a connection between two entities:
+
+```js
+Usergrid.connect(entity1, 'relationship', entity2, function(error, usergridResponse) {
+    // entity1 now has an outbound connection to entity2
+})
+```
+    
+### getConnections
+
+Retrieve outbound connections:
+
+```js
+client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, 'relationship', function(error, usergridResponse, entities) {
+    // entities is an array of entities that entity1 is connected to via 'relationship'
+    // in this case, we'll see entity2 in the array
+})
+```
+    
+Retrieve inbound connections:
+
+```js
+client.getConnections(UsergridClient.Connections.DIRECTION_IN, entity2, 'relationship', function(error, usergridResponse, entities) {
+    // entities is an array of entities that connect to entity2 via 'relationship'
+    // in this case, we'll see entity1 in the array
+})```
+    
+### disconnect
+
+Delete a connection between two entities:
+
+```js
+Usergrid.disconnect(entity1, 'relationship', entity2, function(error, usergridResponse) {
+    // entity1's outbound connection to entity2 has been destroyed
+})
+```
+    
+## Assets
+
+Assets can be uploaded and downloaded either directly using `Usergrid.POST` or `Usergrid.PUT`, or via `UsergridEntity` convenience methods. Before uploading an asset, you will need to initialize a `UsergridAsset` instance.
+
+### UsergridAsset init
+
+Loading a file system image via `fs.readFile()`:
+
+```js
+var asset = new UsergridAsset('myImage')
+fs.readFile(_dirname + '/image.jpg', function(error, data) {
+    asset.data = data
+})
+```
+    
+Loading a file system image from a read stream (`fs.createReadStream()`):
+
+```js
+var asset = new UsergridAsset('myImage')
+fs.createReadStream(_dirname + '/image.jpg').pipe(asset).on('finish', function() {
+    // now contains Buffer stream at asset.data
+})
+```
+    
+You can also access `asset.contentType` and `asset.contentLength` once data has been loaded into a `UsergridAsset`.
+
+### .POST and .PUT
+
+POST binary data to a collection by creating a new entity:
+
+```js
+var asset = new UsergridAsset('myImage')
+fs.createReadStream(_dirname + '/image.jpg').pipe(asset).on('finish', function() {
+    client.POST('collection', asset, function(error, assetResponse, entityWithAsset) {
+        // asset is now uploaded to Usergrid
+    })
+})
+```
+
+PUT binary data to an existing entity via attachAsset():
+    
+```js
+var asset = new UsergridAsset('myImage')
+fs.createReadStream(_dirname + '/image.jpg').pipe(asset).on('finish', function() {
+    // assume entity already exists; attach it to the entity:
+    entity.attachAsset(asset)
+    client.PUT(entity, asset, function(error, assetResponse, entityWithAsset) {
+        // asset is now uploaded to Usergrid
+    })
+})
+```
+    
+### UsergridEntity convenience methods
+
+`entity.uploadAsset()` is a convenient way to upload an asset that is attached to an entity:
+
+```js
+var asset = new UsergridAsset('myImage')
+fs.createReadStream(_dirname + '/image.jpg').pipe(asset).on('finish', function() {
+    // assume entity already exists; attach it to the entity:
+    entity.attachAsset(asset)
+    entity.uploadAsset(function(error, assetResponse, entityWithAsset) {
+        // asset is now uploaded to Usergrid
+    })
+})
+```
+    
+`entity.downloadAsset()` allows you to download a binary asset:
+
+```js
+entity.uploadAsset(function(error, assetResponse, entityWithAsset) {
+    // access the asset via entityWithAsset.asset
+})```
diff --git a/changelog.md b/changelog.md
deleted file mode 100755
index c44ab04..0000000
--- a/changelog.md
+++ /dev/null
@@ -1,43 +0,0 @@
-##Change log
-
-
-###0.10.7
-- Fixed issue where token was appeneded even when no token was present
-- Updated tests
-
-
-###0.10.5
-
-- Added new class and methods for Groups
-- Added serialization / restore methods for entities and collections
-- Various bug fixes
-- Added function for getting user feed
-- Added function for creating user activities with an associated user entity
-- Added public facing helper method for signing up users
-
-###0.10.4
-
-- Added new functions for creating, getting, and deleting connections
-- Added test cases for said functions
-- Fixed change password error
-- Added getEntity method to get existing entity from server
-
-###0.10.3
-
-- Added set / get token methods to accomodate session storage
-- Added createUserActivity method to make creating activities for logged in user easier
-
-###0.10.2
-
-- Removed local caching of user object in client
-
-###0.10.1
-
-- Minor refactor of the SDK to bring congruity with the App services Javascript SDK
-
-###0.10.0
-- Complete refactor of the entire module
-
-- Added Mocha based test suite
-
-- Added full coverage of all sample code in the readme file
diff --git a/config.sample.json b/config.sample.json
new file mode 100644
index 0000000..4e6cfa9
--- /dev/null
+++ b/config.sample.json
@@ -0,0 +1,8 @@
+{
+    "appId": "yourAppId",
+    "authMode": "NONE",
+    "baseUrl": "https://api.usergrid.com",
+    "clientId": "yourClientId",
+    "clientSecret": "yourClientSecret",
+    "orgId": "yourOrgId"
+}
\ No newline at end of file
diff --git a/examples/api-proxy/README.md b/examples/api-proxy/README.md
new file mode 100644
index 0000000..db03d0a
--- /dev/null
+++ b/examples/api-proxy/README.md
@@ -0,0 +1,4 @@
+To use this example, rename the `usergrid.example.json` to `usergrid.json`.  
+This file is located at `examples/api-proxy/config`.
+
+**Note:** The usergrid module crawls your App file structure to find files named `usergrid.json` or a `config.json`.  If there are multiple files with one of these names present at different locations under the app, only one of them will be used and the others are ignored.  This may cause use of an unintended backend.  
diff --git a/examples/api-proxy/app.js b/examples/api-proxy/app.js
new file mode 100644
index 0000000..e0b85ec
--- /dev/null
+++ b/examples/api-proxy/app.js
@@ -0,0 +1,28 @@
+var express = require('express'),
+    app = express(),
+    Usergrid = require('usergrid')
+
+Usergrid.init()
+
+// Usergrid.setAppAuth(id, secret)
+// console.log(Usergrid.appAuth)
+Usergrid.authenticateApp(function(err, usergridResponse) {
+    if (usergridResponse.ok) {
+        console.log('app is now authenticated')
+    }
+})
+
+app.get('/:collection/:uuidOrName?', function(req, res) {
+    Usergrid.GET(req.params.collection, req.params.uuidOrName, function(error, usergridResponse, entities) {
+        res.json(entities);
+    })
+})
+
+// app.listen(process.env.port || 9000)
+
+/*
+
+1. Start the server using > node app.js
+2. Call the api at http://localhost:9000/cats/test
+
+*/
\ No newline at end of file
diff --git a/examples/api-proxy/config/usergrid.example.json b/examples/api-proxy/config/usergrid.example.json
new file mode 100644
index 0000000..36baab8
--- /dev/null
+++ b/examples/api-proxy/config/usergrid.example.json
@@ -0,0 +1,8 @@
+{
+    "appId": "sandbox",
+    "orgId": "brandon.apigee",
+    "authMode": "NONE",
+    "baseUrl": "https://api.usergrid.com",
+    "clientId": "YXA6GXSAACS2EeOYd20aP4G6Lw",
+    "clientSecret": "YXA66BeEvgNpJBwc4PAbvZZGTVS_SSw"
+}
\ No newline at end of file
diff --git a/examples/api-proxy/package.json b/examples/api-proxy/package.json
new file mode 100644
index 0000000..53deec5
--- /dev/null
+++ b/examples/api-proxy/package.json
@@ -0,0 +1,19 @@
+{
+    "dependencies": {
+        "async": "latest",
+        "express": "latest",
+        "usergrid": "r3mus/usergrid-nodejs",
+        "chance": "^0.8.0"
+    },
+    "description": "A sample API proxy built with Express and Usergrid",
+    "keywords": [],
+    "license": "MIT",
+    "main": "app.js",
+    "name": "usergrid-example-api-proxy",
+    "private": false,
+    "scripts": {
+        "start": "node app.js",
+        "test": "mocha tests"
+    },
+    "version": "2.0.0-rc.1"
+}
\ No newline at end of file
diff --git a/helpers/args.js b/helpers/args.js
new file mode 100644
index 0000000..6f221a5
--- /dev/null
+++ b/helpers/args.js
@@ -0,0 +1,21 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var _ = require('lodash')
+
+module.exports = function(args) {
+    return _.flattenDeep(Array.prototype.slice.call(args))
+}
\ No newline at end of file
diff --git a/helpers/build.js b/helpers/build.js
new file mode 100644
index 0000000..ca5ed43
--- /dev/null
+++ b/helpers/build.js
@@ -0,0 +1,479 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var urljoin = require('url-join'),
+    config = require('./config'),
+    helpers = require('./'),
+    UsergridQuery = require('../lib/query'),
+    UsergridEntity = require('../lib/entity'),
+    UsergridAuth = require('../lib/auth'),
+    UsergridAsset = require('../lib/asset'),
+    util = require('util'),
+    version = require('../package.json').version,
+    _ = require('lodash')
+
+var assignPrefabOptions = function(args) {
+    // if a preformatted options argument passed, assign it to options
+    if (_.isObject(args[0]) && !_.isFunction(args[0]) && _.has(this,"method")) {
+        _.assign(this, args[0])
+    }
+    return this
+}
+
+var setEntity = function(args) {
+    this.entity = _.first([this.entity, args[0]].filter(function(property) {
+        return (property instanceof UsergridEntity)
+    }))
+    if (this.entity !== undefined) {
+        this.type = this.entity.type
+    }
+    return this
+}
+
+var setAsset = function(args) {
+    this.asset = _.first([this.asset, _.get(this,'entity.asset'), args[1], args[0]].filter(function(property) {
+        return (property instanceof UsergridAsset)
+    }))
+    return this
+}
+
+var setUuidOrName = function(args) {
+    this.uuidOrName = _.first([
+        this.uuidOrName,
+        this.uuid,
+        this.name,
+        _.get(this,'entity.uuid'),
+        _.get(this,'body.uuid'),
+        _.get(this,'entity.name'),
+        _.get(this,'body.name'),
+        _.get(args,'2'),
+        _.get(args,'1')
+    ].filter(_.isString))
+    return this
+}
+
+var setPathOrType = function(args) {
+    var pathOrType = _.first([
+        this.type,
+        _.get(args,'0._type'),
+        _.get(this,'entity.type'),
+        _.get(this,'body.type'),
+        _.get(this,'body.0.type'),
+        _.isArray(args) ? args[0] : undefined
+    ].filter(_.isString))
+    this[(/\//.test(pathOrType)) ? 'path' : 'type'] = pathOrType
+    return this
+}
+
+var setQs = function(args) {
+    if (this.path) {
+        this.qs = _.first([this.qs, args[2], args[1], args[0]].filter(_.isPlainObject))
+    }
+    return this
+}
+
+var setQuery = function(args) {
+    this.query = _.first([this.query, args[0]].filter(function(property) {
+        return (property instanceof UsergridQuery)
+    }))
+    return this
+}
+
+var setBody = function(args) {
+    this.body = _.first([this.entity, this.body, args[2], args[1], args[0]].filter(function(property) {
+        return _.isObject(property) && !_.isFunction(property) && !(property instanceof UsergridQuery) && !(property instanceof UsergridAsset)
+    }))
+    if (this.body === undefined && this.asset === undefined) {
+        throw new Error(util.format('"body" is required when making a %s request', this.method))
+    }
+    return this
+}
+
+module.exports = {
+    uri: function(client, options) {
+        return urljoin(
+            client.baseUrl,
+            client.orgId,
+            client.appId,
+            options.path || options.type,
+            options.method !== "POST" ? _.first([
+                options.uuidOrName,
+                options.uuid,
+                options.name,
+                _.get(options,'entity.uuid'),
+                _.get(options,'entity.name'),
+                ""
+            ].filter(_.isString)) : ""
+        )
+    },
+    headers: function(client, options) {
+        var headers = {
+            'User-Agent': util.format("usergrid-nodejs/v%s", version)
+        }
+
+        _.assign(headers, options.headers)
+
+        var token
+        var clientTempAuth = _.get(client,"tempAuth")
+        if( !_.isUndefined(clientTempAuth) ) {
+            if( clientTempAuth !== UsergridAuth.NO_AUTH && clientTempAuth.isValid ) {
+                token = client.tempAuth.token;
+            }
+            client.tempAuth = undefined
+        } else {
+            var clientAuthMode = _.get(client,"authMode");
+            if( _.get(client,"currentUser.auth.isValid") && clientAuthMode === UsergridAuth.AUTH_MODE_USER ) {
+                token = client.currentUser.auth.token;
+            } else if( _.get(client,"appAuth.isValid") && clientAuthMode === UsergridAuth.AUTH_MODE_APP ) {
+                token = client.appAuth.token;
+            }
+        }
+
+        if (token) {
+            _.assign(headers, {
+                authorization: util.format("Bearer %s", token)
+            })
+        }
+
+        return headers
+    },
+    userLoginBody: function(options) {
+        var body = {
+            grant_type: 'password',
+            password: options.password
+        }
+        if (options.tokenTtl) {
+            body.ttl = options.tokenTtl
+        }
+        body[(options.username) ? "username" : "email"] = (options.username) ? options.username : options.email
+        return body
+    },
+    appLoginBody: function(options) {
+        var body = {
+            grant_type: 'client_credentials',
+            client_id: options.clientId,
+            client_secret: options.clientSecret
+        }
+        if (options.tokenTtl) {
+            body.ttl = options.tokenTtl
+        }
+        return body
+    },
+    GET: function(client, args) {
+
+        /* GET supports the following constructor patterns:
+
+        client.GET('type', 'uuidOrName', optionalCallback)
+        client.GET('type', optionalCallback)
+        client.GET(query, optionalCallback)
+        client.GET({
+            query: query, // takes precedence
+            type: type, // required if query not defined
+            uuid: uuid, // will be set to uuidOrName on init (priority)
+            name: name, // will be set to uuidOrName on init (if no uuid specified)
+            uuidOrName: uuidOrName // the definitive key for name or uuid
+        }, optionalCallback)
+
+        */
+
+        var options = {
+            client: client,
+            method: 'GET',
+            callback: helpers.cb(args)
+        }
+        assignPrefabOptions.call(options, args)
+        setEntity.call(options, args)
+        setUuidOrName.call(options, args)
+        setPathOrType.call(options, args)
+        setQs.call(options, args)
+        setQuery.call(options, args)
+        return options
+    },
+    PUT: function(client, args) {
+
+        /* PUT supports the following constructor patterns:
+
+        client.PUT('type', 'uuidOrName', bodyObject, optionalCallback)
+        client.PUT('type', bodyObject, optionalCallback) // if no uuid, will create a new record
+        client.PUT(bodyObjectOrEntity, optionalCallback) // if no uuid, will create a new record; must include type
+        client.PUT(query, bodyObjectOrEntity, optionalCallback) // will update all entities matching query
+        client.PUT(entity, optionalCallback)
+        client.PUT({
+            *entity = alias to body*
+            query: query, // takes precedence over type/body
+            type: type, // required if query not defined
+            body: bodyObject or bodyObjectOrEntity, // if includes type, type will be inferred from body
+            *uuid, name* = alias to uuidOrName*
+            uuidOrName: uuidOrName // the definitive key for name or uuid
+        }, optionalCallback)
+
+        */
+
+        var options = {
+            client: client,
+            method: 'PUT',
+            callback: helpers.cb(args)
+        }
+        assignPrefabOptions.call(options, args)
+        setEntity.call(options, args)
+        setAsset.call(options, args)
+        setBody.call(options, args)
+        setUuidOrName.call(options, args)
+        setPathOrType.call(options, args)
+        setQuery.call(options, args)
+        return options
+    },
+    POST: function(client, args) {
+
+        /* POST supports the following constructor patterns:
+
+        client.POST('type', bodyObjectOrArray, optionalCallback)
+        client.POST(bodyObjectOrArray, optionalCallback) // must include type in body
+        client.POST(entityOrEntities, optionalCallback)
+        client.POST({
+            *entity, entities = alias to body*
+            type: type, // required
+            body: bodyObjectOrArray or entityOrEntities, // if the first entity includes type, type will be inferred from body
+        }, optionalCallback)
+
+        */
+
+        var options = {
+            client: client,
+            method: 'POST',
+            callback: helpers.cb(args)
+        }
+        assignPrefabOptions.call(options, args)
+        setEntity.call(options, args)
+        setAsset.call(options, args)
+        setBody.call(options, args)
+        setPathOrType.call(options, args)
+        return options
+    },
+    DELETE: function(client, args) {
+
+        /* DELETE supports the following constructor patterns:
+
+        client.DELETE('type', 'uuidOrName', optionalCallback)
+        client.DELETE(entity, optionalCallback) // must include type in body
+        client.DELETE(query, optionalCallback)
+        client.DELETE({
+            *uuid, name* = alias to uuidOrName*
+            uuidOrName: uuidOrName,
+            type: type, // required if query not defined
+            query: query // takes precedence over type/uuid
+        }, optionalCallback)
+
+        */
+
+        var options = {
+            client: client,
+            method: 'DELETE',
+            callback: helpers.cb(args)
+        }
+        assignPrefabOptions.call(options, args)
+        setEntity.call(options, args)
+        setUuidOrName.call(options, args)
+        setPathOrType.call(options, args)
+        setQs.call(options, args)
+        setQuery.call(options, args)
+        return options
+    },
+    connection: function(client, method, args) {
+
+        /* connect supports the following constructor patterns:
+
+        client.connect(entity, "relationship", toEntity);
+        // POST entity.type/entity.uuid/"relationship"/toEntity.uuid
+
+        client.connect("type", <uuidOrName>, "relationship", <toUuid>);
+        // POST type/uuidOrName/relationship/toUuid
+
+        client.connect("type", <uuidOrName>, "relationship", "toType", "toName");
+        // POST type/uuidOrName/relationship/toType/toName
+
+        client.connect({
+            entity: { // or UsergridEntity
+                type: "type", 
+                uuidOrName: <uuidOrName>
+            },
+            relationship: "likes",
+            to: { // or UsergridEntity
+                "type": "(required if not using uuid)",
+                "uuidOrName": <uuidOrName>,
+                "name": "alias to uuidOrName" // if uuid not specified, requires "type"
+                "uuid": "alias to uuidOrName" 
+            }
+        );
+
+        disconnect supports the identical patters, but uses DELETE instead of POST; it is therefore a reference to this function
+
+        */
+
+        var options = {
+            client: client,
+            method: method,
+            entity: {},
+            to: {},
+            callback: helpers.cb(args)
+        }
+
+        assignPrefabOptions.call(options, args)
+
+        // handle DELETE using "from" preposition
+        if (_.isObject(options.from)) {
+            options.to = options.from
+        }
+
+        // if an entity object or UsergridEntity instance is the first argument (source)
+        if (_.isObject(args[0]) && !_.isFunction(args[0]) && _.isString(args[1])) {
+            _.assign(options.entity, args[0])
+            options.relationship = _.first([options.relationship, args[1]].filter(_.isString))
+        }
+
+        // if an entity object or UsergridEntity instance is the third argument (target)
+        if (_.isObject(args[2]) && !_.isFunction(args[2])) {
+            _.assign(options.to, args[2])
+        }
+
+        options.entity.uuidOrName = _.first([options.entity.uuidOrName, options.entity.uuid, options.entity.name, args[1]].filter(_.isString))
+        if (!options.entity.type) {
+            options.entity.type = _.first([options.entity.type, args[0]].filter(_.isString))
+        }
+        options.relationship = _.first([options.relationship, args[2]].filter(_.isString))
+
+        if (_.isString(args[3]) && !_.isUuid(args[3]) && _.isString(args[4])) {
+            options.to.type = args[3]
+        } else if (_.isString(args[2]) && !_.isUuid(args[2]) && _.isString(args[3]) && _.isObject(args[0]) && !_.isFunction(args[0])) {
+            options.to.type = args[2]
+        }
+
+        options.to.uuidOrName = _.first([options.to.uuidOrName, options.to.uuid, options.to.name, args[4], args[3], args[2]].filter(function(property) {
+            return (_.isString(options.to.type) && _.isString(property) || _.isUuid(property))
+        }))
+
+        if (!_.isString(options.entity.uuidOrName)) {
+            throw new Error('source entity "uuidOrName" is required when connecting or disconnecting entities')
+        }
+
+        if (!_.isString(options.to.uuidOrName)) {
+            throw new Error('target entity "uuidOrName" is required when connecting or disconnecting entities')
+        }
+
+        if (!_.isString(options.to.type) && !_.isUuid(options.to.uuidOrName)) {
+            throw new Error('target "type" (collection name) parameter is required connecting or disconnecting entities by name')
+        }
+
+        options.uri = urljoin(
+            config.baseUrl,
+            client.orgId,
+            client.appId,
+            _.isString(options.entity.type) ? options.entity.type : "",
+            _.isString(options.entity.uuidOrName) ? options.entity.uuidOrName : "",
+            options.relationship,
+            _.isString(options.to.type) ? options.to.type : "",
+            _.isString(options.to.uuidOrName) ? options.to.uuidOrName : ""
+        )
+
+        return options
+    },
+    getConnections: function(client, args) {
+        /* getConnections supports the following constructor patterns:
+
+        client.getConnections(direction, entity, "relationship");
+        // GET OUT: /entity.type/entity.uuid/connections/relationship
+        // GET IN: /entity.type/entity.uuid/connecting/relationship
+
+        client.getConnections(direction, "type", "<uuidOrName>", "relationship");
+        // GET OUT: /type/uuidOrName/connections/relationship
+        // GET IN: /type/uuidOrName/connecting/relationship
+
+        client.getConnections({
+            type: "type", // or inferred, if second argument is an entity
+            uuidOrName: "<uuidOrName>" // if entity not specified
+            relationship: "relationship",
+            direction: OUT or IN
+        );
+        // GET OUT: /entity.type/entity.uuid/connections/relationship
+        // GET IN: /entity.type/entity.uuid/connecting/relationship
+
+        */
+
+        var options = {
+            client: client,
+            method: 'GET',
+            callback: helpers.cb(args)
+        }
+
+        assignPrefabOptions.call(options, args)
+        if (_.isObject(args[1]) && !_.isFunction(args[1])) {
+            _.assign(options, args[1])
+        }
+
+        options.direction = _.first([options.direction, args[0]].filter(function(property) {
+            return (property === "IN" || property === "OUT")
+        }))
+
+        options.relationship = _.first([options.relationship, args[3], args[2]].filter(_.isString))
+        options.uuidOrName = _.first([options.uuidOrName, options.uuid, options.name, args[2]].filter(_.isString))
+        options.type = _.first([options.type, args[1]].filter(_.isString))
+
+        if (!_.isString(options.type)) {
+            throw new Error('"type" (collection name) parameter is required when retrieving connections')
+        }
+
+        if (!_.isString(options.uuidOrName)) {
+            throw new Error('target entity "uuidOrName" is required when retrieving connections')
+        }
+
+        options.uri = urljoin(
+            config.baseUrl,
+            client.orgId,
+            client.appId,
+            _.isString(options.type) ? options.type : "",
+            _.isString(options.uuidOrName) ? options.uuidOrName : "",
+            options.direction === "IN" ? "connecting" : "connections",
+            options.relationship
+        )
+
+        return options
+    },
+    qs: function(options) {
+        return (options.query instanceof UsergridQuery) ? {
+            ql: options.query._ql || undefined,
+            limit: options.query._limit,
+            cursor: options.query._cursor
+        } : options.qs
+    },
+    formData: function(options) {
+        if (_.get(options,'asset.data')) {
+            var formData = {}
+            formData.file = {
+                value: options.asset.data,
+                options: {
+                    filename: _.get(options,'asset.filename') || UsergridAsset.DEFAULT_FILE_NAME,
+                    contentType: _.get(options,'asset.contentType') || 'application/octet-stream'
+                }
+            } 
+            if (_.has(options,'asset.name')) {
+                formData.name = options.asset.name
+            }
+            return formData
+        } else {
+            return undefined
+        }
+    }
+}
\ No newline at end of file
diff --git a/helpers/cb.js b/helpers/cb.js
new file mode 100644
index 0000000..e26076d
--- /dev/null
+++ b/helpers/cb.js
@@ -0,0 +1,24 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var _ = require('lodash')
+
+module.exports = function() {
+    var args = _.flattenDeep(Array.prototype.slice.call(arguments)).reverse()
+    var emptyFunc = function() {}
+    return _.first(_.flattenDeep([args, _.get(args,'0.callback'), emptyFunc]).filter(_.isFunction))
+
+}
\ No newline at end of file
diff --git a/helpers/client.js b/helpers/client.js
new file mode 100644
index 0000000..a9273de
--- /dev/null
+++ b/helpers/client.js
@@ -0,0 +1,48 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var Usergrid = require('../usergrid'),
+    _ = require('lodash')
+
+
+module.exports = {
+    validate: function(args) {
+        var UsergridClient = require('../lib/client')
+        var client
+        if (args instanceof UsergridClient) {
+            client = args
+        } else if (args[0] instanceof UsergridClient) {
+            client = args[0]
+        } else if (Usergrid.isInitialized) {
+            client = Usergrid
+        } else {
+            throw new Error("this method requires either the Usergrid shared instance to be initialized or a UsergridClient instance as the first argument")
+        } 
+        return client
+    },
+    configureTempAuth: function(auth) {
+        var UsergridAuth = require('../lib/auth')
+        if (_.isString(auth) && auth !== UsergridAuth.NO_AUTH) {
+            return new UsergridAuth(auth)
+        } else if (!auth || auth === UsergridAuth.NO_AUTH) {
+            return UsergridAuth.NO_AUTH
+        } else if (auth instanceof UsergridAuth) {
+            return auth
+        } else {
+            return undefined
+        }
+    }
+}
\ No newline at end of file
diff --git a/helpers/config.js b/helpers/config.js
new file mode 100644
index 0000000..ee6e0b6
--- /dev/null
+++ b/helpers/config.js
@@ -0,0 +1,52 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var util = require('util'),
+    path = require('path'),
+    file = require("file"),
+    _ = require('lodash'),
+    appRoot = path.dirname(require.main.filename)
+
+if (/mocha$/i.test(process.argv[1])) {
+    var target = (_.last(process.argv)).startsWith('--target=') ? _.last(process.argv).replace(/--target=/, '') : '2.1'
+    var config = require('../tests/config.test.json')[target]
+    if (config && target) {
+        config.target = target
+    } else {
+        throw new Error(util.format("Could not load target '%s' from /tests/config.test.json", target))
+    }
+    module.exports = config
+} else {
+    try {
+        file.walkSync(appRoot, function(start, dirs, names) {
+            if (_.includes(names, "config.json") || _.includes(names, "usergrid.json")) {
+                var name = _.first(names.filter(function(name) {
+                    return name === "config.json" || name === "usergrid.json"
+                }).sort().reverse())
+                var configPath = util.format("%s/%s", start, name)
+                module.exports = require(configPath)
+                if (module.exports.orgId === undefined || module.exports.appId === undefined) {
+                    console.log(util.format("Config file '%s' is not a valid Usergrid configuration file", configPath))
+                    module.exports = {}
+                } else {
+                    console.log(util.format("Using config file '%s'", configPath))
+                }
+            }
+        })
+    } catch (e) {
+
+    }
+}
\ No newline at end of file
diff --git a/helpers/index.js b/helpers/index.js
new file mode 100644
index 0000000..6a46b6d
--- /dev/null
+++ b/helpers/index.js
@@ -0,0 +1,40 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var args = require('./args'),
+    client = require('./client'),
+    cb = require('./cb'),
+    build = require('./build'),
+    query = require('./query'),
+    config = require('./config'),
+    time = require('./time'),
+    mutability = require('./mutability'),
+    user = require('./user'),
+    _ = require('lodash')
+
+// by mixing this in here, lodash-uuid is available everywhere lodash is used.
+_.mixin(require('lodash-uuid'))
+
+module.exports = _.assign(module.exports, {
+    args: args,
+    client: client,
+    cb: cb,
+    build: build,
+    query: query,
+    config: config,
+    time: time,
+    user: user
+}, mutability)
\ No newline at end of file
diff --git a/helpers/mutability.js b/helpers/mutability.js
new file mode 100644
index 0000000..0ad058b
--- /dev/null
+++ b/helpers/mutability.js
@@ -0,0 +1,55 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var _ = require('lodash')
+
+module.exports = {
+    setReadOnly: function(obj, key) {
+        if (_.isArray(key)) {
+            return key.forEach(function(k) {
+                module.exports.setReadOnly(obj, k)
+            })
+        } else if (_.isPlainObject(obj[key])) {
+            return Object.freeze(obj[key])
+        } else if (_.isPlainObject(obj) && key === undefined) {
+            return Object.freeze(obj)
+        } else if (_.has(obj,key)) {
+            return Object.defineProperty(obj, key, {
+                writable: false
+            })
+        } else {
+            return obj
+        }
+    },
+    setWritable: function(obj, key) {
+        if (_.isArray(key)) {
+            return key.forEach(function(k) {
+                module.exports.setWritable(obj, k)
+            })
+        // Note that once Object.freeze is called on an object, it cannot be unfrozen, so we need to clone it
+        } else if (_.isPlainObject(obj[key])) {
+            return _.clone(obj[key])
+        } else if (_.isPlainObject(obj) && key === undefined) {
+            return _.clone(obj)
+        } else if (_.has(obj,key)) {
+            return Object.defineProperty(obj, key, {
+                writable: true
+            })
+        } else {
+            return obj
+        }
+    }
+}
\ No newline at end of file
diff --git a/helpers/query.js b/helpers/query.js
new file mode 100644
index 0000000..f019545
--- /dev/null
+++ b/helpers/query.js
@@ -0,0 +1,24 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var util = require('util'),
+    _ = require('lodash')
+
+module.exports = {
+    useQuotesIfRequired: function(value) {
+        return (_.isFinite(value) || _.isUuid(value) || _.isBoolean(value) || _.isObject(value) && !_.isFunction(value) || _.isArray(value)) ? value : util.format("'%s'", value)
+    }
+}
\ No newline at end of file
diff --git a/helpers/time.js b/helpers/time.js
new file mode 100644
index 0000000..d3452b1
--- /dev/null
+++ b/helpers/time.js
@@ -0,0 +1,21 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+module.exports = {
+    expiry: function(expires_in) {
+        return Date.now() + ((expires_in ? expires_in - 5 : 0) * 1000)
+    }
+}
\ No newline at end of file
diff --git a/helpers/user.js b/helpers/user.js
new file mode 100644
index 0000000..45dcde4
--- /dev/null
+++ b/helpers/user.js
@@ -0,0 +1,23 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var _ = require('lodash')
+
+module.exports = {
+    uniqueId: function(user) {
+        return _.first([user.uuid, user.username, user.email].filter(_.isString))
+    }
+}
\ No newline at end of file
diff --git a/lib/appAuth.js b/lib/appAuth.js
new file mode 100644
index 0000000..740002e
--- /dev/null
+++ b/lib/appAuth.js
@@ -0,0 +1,41 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var UsergridAuth = require('./auth'),
+    helpers = require('../helpers'),
+    util = require('util'),
+    _ = require('lodash')
+
+var UsergridAppAuth = function() {
+    var self = this
+    var args = _.flattenDeep(helpers.args(arguments))
+    if (_.isPlainObject(args[0])) {
+        self.clientId = args[0].clientId
+        self.clientSecret = args[0].clientSecret
+        self.tokenTtl = args[0].tokenTtl
+    } else {
+        self.clientId = args[0]
+        self.clientSecret = args[1]
+        self.tokenTtl = args[2]
+    }
+    UsergridAuth.call(self)
+    _.assign(self, UsergridAuth)
+    return self
+}
+
+util.inherits(UsergridAppAuth, UsergridAuth)
+
+module.exports = UsergridAppAuth
\ No newline at end of file
diff --git a/lib/asset.js b/lib/asset.js
new file mode 100644
index 0000000..a054075
--- /dev/null
+++ b/lib/asset.js
@@ -0,0 +1,86 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var fileType = require('file-type'),
+    helpers = require('../helpers'),
+    stream = require('stream'),
+    util = require('util'),
+    _ = require('lodash')
+
+var UsergridAsset = function() {
+    var self = this
+    var args = helpers.args(arguments)
+
+    var __contentType
+    var __binaryData = []
+
+    if (args.length === 0) {
+        throw new Error('A UsergridAsset object cannot be initialized without passing one or more arguments')
+    }
+
+    if (_.isPlainObject(args[0])) {
+        _.assign(self, args[0])
+    } else {
+        self.filename = _.isString(args[0]) ? args[0] : undefined
+        self.data = _.first(args.filter(Buffer.isBuffer)) || []
+        self.originalLocation = _.first([args[2], args[1]].filter(function(property) {
+            return _.isString(property)
+        }))
+
+        self.contentType = _.isString(args[3]) ? args[3] : undefined
+
+        stream.PassThrough.call(self)
+        self._write = function(chunk, encoding, done) {
+            __binaryData.push(chunk)
+            done()
+        }
+        self.on('finish', function() {
+            self.data = Buffer.concat(__binaryData)
+        })
+    }
+
+    Object.defineProperty(self, 'contentLength', {
+        get: function() {
+            return (self.data) ? self.data.byteLength : 0
+        }
+    })
+
+    Object.defineProperty(self, 'contentType', {
+        get: function() {
+            if (__contentType) {
+                return __contentType
+            } else if (Buffer.isBuffer(self.data)) {
+                __contentType = fileType(self.data) != null ? fileType(self.data).mime : undefined
+                return __contentType
+            }
+        },
+        set: function(contentType) {
+            if (contentType) {
+                __contentType = contentType
+            } else if (Buffer.isBuffer(self.data)) {
+                __contentType = fileType(self.data) != null ? fileType(self.data).mime : undefined
+            }
+        }
+    })
+
+    return self
+}
+
+util.inherits(UsergridAsset, stream.PassThrough)
+
+
+module.exports = UsergridAsset
+module.exports.DEFAULT_FILE_NAME = 'file'
\ No newline at end of file
diff --git a/lib/auth.js b/lib/auth.js
new file mode 100644
index 0000000..06ef684
--- /dev/null
+++ b/lib/auth.js
@@ -0,0 +1,79 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var UsergridAuth = function(token, expiry) {
+    var self = this
+
+    self.token = token
+    self.expiry = expiry || 0
+
+    var usingToken = (token) ? true : false
+
+    Object.defineProperty(self, "hasToken", {
+        get: function() {
+            return (self.token) ? true : false
+        },
+        configurable: true
+    })
+
+    Object.defineProperty(self, "isExpired", {
+        get: function() {
+            return (usingToken) ? false : (Date.now() >= self.expiry)
+        },
+        configurable: true
+    })
+
+    Object.defineProperty(self, "isValid", {
+        get: function() {
+            return (!self.isExpired && self.hasToken)
+        },
+        configurable: true
+    })
+
+    Object.defineProperty(self, 'tokenTtl', {
+        configurable: true,
+        writable: true
+    })
+
+    return self
+}
+
+UsergridAuth.prototype = {
+    destroy: function() {
+        this.token = undefined
+        this.expiry = 0
+        this.tokenTtl = undefined
+    }
+}
+
+module.exports = UsergridAuth
+
+Object.defineProperty(module.exports, 'AUTH_MODE_APP', {
+    enumerable: false,
+    get: function() { return "APP" }
+})
+Object.defineProperty(module.exports, 'AUTH_MODE_USER', {
+    enumerable: false,
+    get: function() { return "USER" }
+})
+Object.defineProperty(module.exports, 'AUTH_MODE_NONE', {
+    enumerable: false,
+    get: function() { return "NONE" }
+})
+Object.defineProperty(module.exports, 'NO_AUTH', {
+    enumerable: false,
+    get: function() { return "NO_AUTH" }
+})
\ No newline at end of file
diff --git a/lib/client.js b/lib/client.js
new file mode 100644
index 0000000..3f26d0f
--- /dev/null
+++ b/lib/client.js
@@ -0,0 +1,170 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var helpers = require('../helpers'),
+    UsergridRequest = require('./request'),
+    UsergridAuth = require('./auth'),
+    UsergridAppAuth = require('./appAuth'),
+    _ = require('lodash')
+
+var defaultOptions = {
+    baseUrl: 'https://api.usergrid.com',
+    authMode: UsergridAuth.AUTH_MODE_USER
+}
+
+var UsergridClient = function(options) {
+    var self = this
+
+    var __appAuth
+    self.tempAuth = undefined
+    self.isSharedInstance = false
+
+    if (arguments.length === 2) {
+        self.orgId = arguments[0]
+        self.appId = arguments[1]
+    }
+
+    _.defaults(self, options, helpers.config, defaultOptions)
+
+    if (!self.orgId || !self.appId) {
+        throw new Error('"orgId" and "appId" parameters are required when instantiating UsergridClient')
+    }
+
+    Object.defineProperty(self, 'test', {
+        enumerable: false
+    })
+
+    Object.defineProperty(self, 'clientId', {
+        enumerable: false
+    })
+
+    Object.defineProperty(self, 'clientSecret', {
+        enumerable: false
+    })
+
+    Object.defineProperty(self, 'appAuth', {
+        get: function() {
+            return __appAuth
+        },
+        set: function(options) {
+            if (options instanceof UsergridAppAuth) {
+                __appAuth = options
+            } else if( _.isUndefined(options) ) {
+                __appAuth = undefined
+            } else {
+                __appAuth = new UsergridAppAuth(options)
+            }
+        }
+    })
+
+    // if client ID and secret are defined on initialization, initialize appAuth
+    if (self.clientId && self.clientSecret) {
+        self.setAppAuth(self.clientId, self.clientSecret)
+    }
+    return self
+}
+
+UsergridClient.prototype = {
+    GET: function() {
+        return new UsergridRequest(helpers.build.GET(this, helpers.args(arguments)))
+    },
+    PUT: function() {
+        return new UsergridRequest(helpers.build.PUT(this, helpers.args(arguments)))
+    },
+    POST: function() {
+        return new UsergridRequest(helpers.build.POST(this, helpers.args(arguments)))
+    },
+    DELETE: function() {
+        return new UsergridRequest(helpers.build.DELETE(this, helpers.args(arguments)))
+    },
+    connect: function() {
+        return new UsergridRequest(helpers.build.connection(this, 'POST', helpers.args(arguments)))
+    },
+    disconnect: function() {
+        return new UsergridRequest(helpers.build.connection(this, 'DELETE', helpers.args(arguments)))
+    },
+    getConnections: function() {        
+        return new UsergridRequest(helpers.build.getConnections(this, helpers.args(arguments)))
+    },
+    setAppAuth: function() {
+        this.appAuth = new UsergridAppAuth(helpers.args(arguments))
+    },
+    authenticateApp: function(options) {
+        var self = this
+        var callback = helpers.cb(helpers.args(arguments))
+        // console.log(self.appAuth)//, self.appAuth, new UsergridAppAuth(options), new UsergridAppAuth(self.clientId, self.clientSecret))
+        var auth = _.first([options, self.appAuth, new UsergridAppAuth(options), new UsergridAppAuth(self.clientId, self.clientSecret)].filter(function(p) {
+            return p instanceof UsergridAppAuth
+        }))
+
+        if (!(auth instanceof UsergridAppAuth)) {
+            throw new Error('App auth context was not defined when attempting to call .authenticateApp()')
+        } else if (!auth.clientId || !auth.clientSecret) {
+            throw new Error('authenticateApp() failed because clientId or clientSecret are missing')
+        }
+
+        return new UsergridRequest({
+            client: self,
+            path: 'token',
+            method: 'POST',
+            body: helpers.build.appLoginBody(auth)
+        }, function(error, usergridResponse, body) {
+            if (usergridResponse.ok) {
+                if (!self.appAuth) {
+                    self.appAuth = auth
+                }
+                self.appAuth.token = body.access_token
+                self.appAuth.expiry = helpers.time.expiry(body.expires_in)
+                self.appAuth.tokenTtl = body.expires_in
+            }
+            callback(error, usergridResponse, body.access_token)
+        })
+    },
+    authenticateUser: function(options) {
+        var self = this
+        var args = helpers.args(arguments)
+        var callback = helpers.cb(args)
+        var setAsCurrentUser = (_.last(args.filter(_.isBoolean))) !== undefined ? _.last(args.filter(_.isBoolean)) : true
+        var UsergridUser = require('./user')
+        var currentUser = new UsergridUser(options)
+        currentUser.login(self, function(error, usergridResponse, token) {
+            if (usergridResponse.ok && setAsCurrentUser) {
+                self.currentUser = currentUser
+            }
+            callback(error, usergridResponse, token)
+        })
+    },
+    usingAuth: function(auth) {
+        this.tempAuth = helpers.client.configureTempAuth(auth)
+        return this
+    }
+}
+
+module.exports = UsergridClient
+Object.defineProperty(module.exports, 'Connections', {
+    enumerable: false,
+    writable: true,
+    configurable: true
+})
+module.exports.Connections = {}
+Object.defineProperty(module.exports.Connections, 'DIRECTION_IN', {
+    enumerable: false,
+    get: function() { return "IN" }
+})
+Object.defineProperty(module.exports.Connections, 'DIRECTION_OUT', {
+    enumerable: false,
+    get: function() { return "OUT" }
+})
\ No newline at end of file
diff --git a/lib/entity.js b/lib/entity.js
new file mode 100644
index 0000000..b1452a6
--- /dev/null
+++ b/lib/entity.js
@@ -0,0 +1,225 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var UsergridRequest = require('./request'),
+    UsergridAsset = require('./asset'),
+    helpers = require('../helpers'),
+    _ = require('lodash')
+
+function updateEntityFromRemote(usergridResponse) {
+    helpers.setWritable(this, ['uuid', 'name', 'type', 'created'])
+    _.assign(this, usergridResponse.entity)
+    helpers.setReadOnly(this, ['uuid', 'name', 'type', 'created'])
+}
+
+var UsergridEntity = function() {
+    var self = this
+    var args = helpers.args(arguments)
+
+    if (args.length === 0) {
+        throw new Error('A UsergridEntity object cannot be initialized without passing one or more arguments')
+    }
+
+    var firstArg = args[0]
+    if (_.isPlainObject(firstArg) || firstArg instanceof UsergridEntity ) {
+        _.assign(self, args[0]);
+    } else {
+        if( !self.type ) {
+            self.type = _.isString(args[0]) ? args[0] : undefined;
+        }
+        if( !self.name ) {
+            self.name = _.isString(args[1]) ? args[1] : undefined;
+        }
+    }
+
+    if (!_.isString(self.type)) {
+        throw new Error('"type" (or "collection") parameter is required when initializing a UsergridEntity object')
+    }
+
+    Object.defineProperty(self, 'tempAuth', {
+        enumerable: false,
+        configurable: true,
+        writable: true
+    })
+
+    Object.defineProperty(self, 'asset', {
+        enumerable: false,
+        configurable: true,
+        writable: true
+    })
+
+    Object.defineProperty(self, 'isUser', {
+        get: function() {
+            return (self.type.toLowerCase() === 'user')
+        }
+    })
+
+    Object.defineProperty(self, 'hasAsset', {
+        get: function() {
+            return _.has(self,'file-metadata')
+        }
+    })
+
+    helpers.setReadOnly(self, ['uuid', 'name', 'type', 'created'])
+
+    return self
+}
+
+UsergridEntity.prototype = {
+    putProperty: function(key, value) {
+        this[key] = value
+    },
+    putProperties: function(obj) {
+        _.assign(this, obj)
+    },
+    removeProperty: function(key) {
+        this.removeProperties([key])
+    },
+    removeProperties: function(keys) {
+        var self = this
+        keys.forEach(function(key) {
+            delete self[key]
+        })
+    },
+    insert: function(key, value, idx) {
+        if (!_.isArray(this[key])) {
+            this[key] = this[key] ? [this[key]] : []
+        }
+        this[key].splice.apply(this[key], [idx, 0].concat(value))
+    },
+    append: function(key, value) {
+        this.insert(key, value, Number.MAX_SAFE_INTEGER)
+    },
+    prepend: function(key, value) {
+        this.insert(key, value, 0)
+    },
+    pop: function(key) {
+        if (_.isArray(this[key])) {
+            this[key].pop()
+        }
+    },
+    shift: function(key) {
+        if (_.isArray(this[key])) {
+            this[key].shift()
+        }
+    },
+    reload: function() {
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        client.tempAuth = this.tempAuth
+        this.tempAuth = undefined
+        var callback = helpers.cb(args)
+        client.GET(this, function(error, usergridResponse) {
+            updateEntityFromRemote.call(this, usergridResponse)
+            callback(error, usergridResponse, this)
+        }.bind(this))
+    },
+    save: function() {
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        client.tempAuth = this.tempAuth
+        this.tempAuth = undefined
+        var callback = helpers.cb(args)
+        client.PUT(this, function(error, usergridResponse) {
+            updateEntityFromRemote.call(this, usergridResponse)
+            callback(error, usergridResponse, this)
+        }.bind(this))
+    },
+    remove: function() {
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        client.tempAuth = this.tempAuth
+        this.tempAuth = undefined
+        var callback = helpers.cb(args)
+        client.DELETE(this, function(error, usergridResponse) {
+            callback(error, usergridResponse, this)
+        }.bind(this))
+    },
+    attachAsset: function(asset) {
+        this.asset = asset
+    },
+    uploadAsset: function() {
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        var callback = helpers.cb(args)
+        client.POST(this, this.asset, function(error, usergridResponse) {
+            updateEntityFromRemote.call(this, usergridResponse)
+            callback(error, usergridResponse, this)
+        }.bind(this))
+    },
+    downloadAsset: function() {
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        var callback = helpers.cb(args)
+        var self = this
+
+        if (_.has(self,'asset.contentType')) {
+            var options = {
+                client: client,
+                entity: self,
+                type: this.type,
+                method: 'GET',
+                encoding: null,
+                headers: {
+                    "Accept": self.asset.contentType || _.first(args.filter(_.isString))
+                }
+            }
+            options.uri = helpers.build.uri(client, options)
+            return new UsergridRequest(options, function(error, usergridResponse) {
+                if (usergridResponse.ok) {
+                    self.attachAsset(new UsergridAsset(new Buffer(usergridResponse.body)))
+                }
+                callback(error, usergridResponse, self)
+            })
+        } else {
+            callback({
+                name: "asset_not_found",
+                description: "The specified entity does not have a valid asset attached"
+            })
+        }
+    },
+    connect: function() {
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        client.tempAuth = this.tempAuth
+        this.tempAuth = undefined
+        args[0] = this
+        return client.connect.apply(client, args)
+    },
+    disconnect: function() {
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        client.tempAuth = this.tempAuth
+        this.tempAuth = undefined
+        args[0] = this
+        return client.disconnect.apply(client, args)
+    },
+    getConnections: function() {
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        client.tempAuth = this.tempAuth
+        this.tempAuth = undefined
+        args.shift()
+        args.splice(1, 0, this)
+        return client.getConnections.apply(client, args)
+    },
+    usingAuth: function(auth) {
+        this.tempAuth = helpers.client.configureTempAuth(auth)
+        return this
+    }
+}
+
+module.exports = UsergridEntity
\ No newline at end of file
diff --git a/lib/query.js b/lib/query.js
new file mode 100644
index 0000000..9cbfd5c
--- /dev/null
+++ b/lib/query.js
@@ -0,0 +1,153 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var helpers = require('../helpers'),
+    util = require('util'),
+    _ = require('lodash')
+
+var UsergridQuery = function(type) {
+
+    var self = this
+
+    var query = '',
+        queryString,
+        sort,
+        __nextIsNot = false
+
+    // builder pattern
+    _.assign(self, {
+        type: function(value) {
+            self._type = value
+            return self
+        },
+        collection: function(value) {
+            self._type = value
+            return self
+        },
+        limit: function(value) {
+            self._limit = value
+            return self
+        },
+        cursor: function(value) {
+            self._cursor = value
+            return self
+        },
+        eq: function(key, value) {
+            query = self.andJoin(util.format('%s = %s', key, helpers.query.useQuotesIfRequired(value)))
+            return self
+        },
+        equal: this.eq,
+        gt: function(key, value) {
+            query = self.andJoin(util.format('%s > %s', key, helpers.query.useQuotesIfRequired(value)))
+            return self
+        },
+        greaterThan: this.gt,
+        gte: function(key, value) {
+            query = self.andJoin(util.format('%s >= %s', key, helpers.query.useQuotesIfRequired(value)))
+            return self
+        },
+        greaterThanOrEqual: this.gte,
+        lt: function(key, value) {
+            query = self.andJoin(util.format('%s < %s', key, helpers.query.useQuotesIfRequired(value)))
+            return self
+        },
+        lessThan: this.lt,
+        lte: function(key, value) {
+            query = self.andJoin(util.format('%s <= %s', key, helpers.query.useQuotesIfRequired(value)))
+            return self
+        },
+        lessThanOrEqual: this.lte,
+        contains: function(key, value) {
+            query = self.andJoin(util.format('%s contains %s', key, helpers.query.useQuotesIfRequired(value)))
+            return self
+        },
+        locationWithin: function(distanceInMeters, lat, lng) {
+            query = self.andJoin(util.format('location within %s of %s, %s', distanceInMeters, lat, lng))
+            return self
+        },
+        asc: function(key) {
+            self.sort(key, 'asc')
+            return self
+        },
+        desc: function(key) {
+            self.sort(key, 'desc')
+            return self
+        },
+        sort: function(key, order) {
+            sort = (key && order) ? util.format(' order by %s %s', key, order) : ''
+            return self
+        },
+        fromString: function(string) {
+            queryString = string
+            return self
+        },
+        andJoin: function(append) {
+            if (__nextIsNot) {
+                append = util.format("not %s", append)
+                __nextIsNot = false
+            }
+            if (!append) {
+                return query
+            } else if (query.length === 0) {
+                return append
+            } else {
+                return (_.endsWith(query, 'and') || _.endsWith(query, 'or')) ? util.format('%s %s', query, append) : util.format('%s and %s', query, append)
+            }
+        },
+        orJoin: function() {
+            return (query.length > 0 && !_.endsWith(query, 'or')) ? util.format('%s or', query) : query
+        }
+    })
+
+    // required properties
+    self._type = self._type || type
+
+    // public accessors
+    Object.defineProperty(self, '_ql', {
+        get: function() {
+            if (queryString !== undefined) {
+                return queryString
+            } else {
+                return util.format('select * %s %s', ((query.length > 0) ? 'where ' + (query || '') : ''),((sort !== undefined) ? sort : '')).trim()
+            }
+        }
+    })
+
+    Object.defineProperty(self, 'and', {
+        get: function() {
+            query = self.andJoin('')
+            return self
+        }
+    })
+
+    Object.defineProperty(self, 'or', {
+        get: function() {
+            query = self.orJoin()
+            return self
+        }
+    })
+
+    Object.defineProperty(self, 'not', {
+        get: function() {
+            __nextIsNot = true
+            return self
+        }
+    })
+
+    return self
+}
+
+module.exports = UsergridQuery
\ No newline at end of file
diff --git a/lib/request.js b/lib/request.js
new file mode 100644
index 0000000..77c88a5
--- /dev/null
+++ b/lib/request.js
@@ -0,0 +1,53 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var request = require('request'),
+    helpers = require('../helpers'),
+    UsergridResponse = require('../lib/response'),
+    _ = require('lodash')
+
+var UsergridRequest = function(options) {
+    var client = helpers.client.validate(options.client)
+    var callback = helpers.cb(helpers.args(arguments))
+
+    if (!_.isString(options.type) && !_.isString(options.path) && !_.isString(options.uri)) {
+        throw new Error('one of "type" (collection name), "path", or "uri" parameters are required when initializing a UsergridRequest')
+    }
+
+    if (!_.includes(['GET', 'PUT', 'POST', 'DELETE'], options.method)) {
+        throw new Error('"method" parameter is required when initializing a UsergridRequest')
+    }
+
+    var uri = options.uri || helpers.build.uri(client, options)
+    var formData = helpers.build.formData(options)
+    var body = ((formData !== undefined) ? undefined : options.body)
+
+    request(uri, {
+        headers: helpers.build.headers(client, options),
+        body: body,
+        encoding: options.encoding || null,
+        json: true,
+        method: options.method,
+        qs: helpers.build.qs(options),
+        formData: formData
+    }, function(error, response) {
+        var usergridResponse = new UsergridResponse(response)
+        var returnBody = _.first([usergridResponse.user, usergridResponse.users, usergridResponse.entity, usergridResponse.entities, usergridResponse.body].filter(_.isObject))
+        callback(error || usergridResponse.error, usergridResponse, returnBody)
+    })
+}
+
+module.exports = UsergridRequest
\ No newline at end of file
diff --git a/lib/response.js b/lib/response.js
new file mode 100644
index 0000000..9be05e0
--- /dev/null
+++ b/lib/response.js
@@ -0,0 +1,87 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var UsergridQuery = require('./query'),
+    UsergridResponseError = require('./responseError'),
+    helpers = require('../helpers'),
+    _ = require('lodash')
+
+var UsergridResponse = function(response) {
+    var self = this
+    self.ok = false
+    if (!response) {
+        return
+    } else if (response.statusCode < 400) {
+        self.ok = true
+        var UsergridEntity = require('./entity.js'),
+            UsergridUser = require('./user.js')
+        
+        _.assign(self, response)
+
+        if (_.has(response,'body.entities')) {
+            var entities = response.body.entities.map(function(en) {
+                var entity = new UsergridEntity(en)
+                if (entity.isUser) {
+                    entity = new UsergridUser(entity)
+                }
+                return entity
+            })
+            _.assign(self, {
+                metadata: _.cloneDeep(response.body),
+                entities: entities
+            })
+            delete self.metadata.entities
+            self.first = _.first(entities) || undefined
+            self.entity = self.first
+            self.last = _.last(entities) || undefined   
+            if (_.get(self,'metadata.path') === '/users') {
+                self.user = self.first
+                self.users = self.entities
+            }
+
+            Object.defineProperty(self, 'hasNextPage', {
+                get: function() {
+                    return _.has(self,'metadata.cursor')
+                }
+            })
+
+            helpers.setReadOnly(self.metadata)
+        }
+    } else {
+        _.assign(self, response, {
+            error: new UsergridResponseError(response.body)
+        })
+    }
+    return self;
+}
+
+UsergridResponse.prototype = {
+    loadNextPage: function() {
+        var args = helpers.args(arguments)
+        var callback = helpers.cb(args)
+        if (!this.metadata.cursor) {
+            callback()
+        }
+        var client = helpers.client.validate(args)
+        var type = _.last(_.get(this,'metadata.path').split('/'))
+        var limit = _.first(_.get(this,'metadata.params.limit'))
+        var ql =  _.first(_.get(this,'metadata.params.ql'))
+        var query = new UsergridQuery(type).fromString(ql).cursor(this.metadata.cursor).limit(limit)
+        return client.GET(query, callback)
+    }
+}
+
+module.exports = UsergridResponse
\ No newline at end of file
diff --git a/lib/responseError.js b/lib/responseError.js
new file mode 100644
index 0000000..4471bbd
--- /dev/null
+++ b/lib/responseError.js
@@ -0,0 +1,29 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var _ = require('lodash')
+
+var UsergridResponseError = function(responseErrorObject) {
+    if (_.get(responseErrorObject,'error') === false) {
+        return
+    }
+    this.name = responseErrorObject.error
+    this.description = responseErrorObject.error_description || responseErrorObject.description
+    this.exception = responseErrorObject.exception
+    return this
+}
+
+module.exports = UsergridResponseError
\ No newline at end of file
diff --git a/lib/user.js b/lib/user.js
new file mode 100644
index 0000000..90506b4
--- /dev/null
+++ b/lib/user.js
@@ -0,0 +1,159 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var UsergridEntity = require('./entity'),
+    UsergridQuery = require('./query'),
+    UsergridUserAuth = require('./userAuth'),
+    UsergridRequest = require('./request'),
+    UsergridClient = require('../lib/client'),
+    helpers = require('../helpers'),
+    util = require('util'),
+    _ = require('lodash')
+
+var UsergridUser = function(obj) {
+
+    if (!_.has(obj,'email') && !_.has(obj,'username')) {
+        // This is not a user entity
+        throw new Error('"email" or "username" property is required when initializing a UsergridUser object')
+    }
+
+    var self = this
+    self.type = "user"
+
+    _.assign(self, obj, UsergridEntity)
+    UsergridEntity.call(self, self)
+
+    helpers.setWritable(self, 'name')
+    return self
+}
+
+var CheckAvailable = function() {
+    var self = this
+    var args = helpers.args(arguments)
+    var client = helpers.client.validate(args)
+    if (args[0] instanceof UsergridClient) {
+        args.shift()
+    }
+    var callback = helpers.cb(args)
+    var checkQuery
+
+    if (args[0].username && args[0].email) {
+        checkQuery = new UsergridQuery('users').eq('username', args[0].username).or.eq('email', args[0].email)
+    } else if (args[0].username) {
+        checkQuery = new UsergridQuery('users').eq('username', args[0].username)
+    } else if (args[0].email) {
+        checkQuery = new UsergridQuery('users').eq('email', args[0].email)
+    } else {
+        throw new Error("'username' or 'email' property is required when checking for available users")
+    }
+
+    client.GET(checkQuery, function(error, usergridResponse) {
+        callback(error, usergridResponse, (usergridResponse.entities.length > 0))
+    }.bind(self))
+}
+
+UsergridUser.prototype = {
+    create: function() {
+        var self = this
+        var args = helpers.args(arguments)
+        var client = helpers.client.validate(args)
+        var callback = helpers.cb(args)
+        client.POST(self, function(error, usergridResponse) {
+            delete self.password
+            _.assign(self, usergridResponse.user)
+            callback(error, usergridResponse, usergridResponse.user)
+        }.bind(self))
+    },
+    login: function() {
+        var self = this
+        var args = helpers.args(arguments)
+        var callback = helpers.cb(args)
+        return new UsergridRequest({
+            client: helpers.client.validate(args),
+            path: 'token',
+            method: 'POST',
+            body: helpers.build.userLoginBody(self)
+        }, function(error, usergridResponse, body) {
+            delete self.password
+            if (usergridResponse.ok) {
+                self.auth = new UsergridUserAuth(body.user)
+                self.auth.token = body.access_token
+                self.auth.expiry = helpers.time.expiry(body.expires_in)
+                self.auth.tokenTtl = body.expires_in
+            }
+            callback(error, usergridResponse, body.access_token)
+        })
+    },
+    logout: function() {
+        var self = this
+        var args = helpers.args(arguments)
+        var callback = helpers.cb(args)
+        if (!self.auth || !self.auth.isValid) {
+            return callback({
+                name: 'no_valid_token',
+                description: 'this user does not have a valid token'
+            })
+        }
+
+        var revokeAll = _.first(args.filter(_.isBoolean)) || false
+
+        return new UsergridRequest({
+            client: helpers.client.validate(args),
+            path: util.format("users/%s/revoketoken%s", helpers.user.uniqueId(self), (revokeAll) ? "s" : ""),
+            method: 'PUT',
+            qs: (!revokeAll) ? {
+                token: self.auth.token
+            } : undefined
+        }, function(error, usergridResponse) {
+            self.auth.destroy()
+            callback(error, usergridResponse, usergridResponse.ok)
+        })
+    },
+    logoutAllSessions: function() {
+        var args = helpers.args(arguments)
+        args = _.concat([helpers.client.validate(args), true], args)
+        return this.logout.apply(this, args)
+    },
+    resetPassword: function() {
+        var self = this
+        var args = helpers.args(arguments)
+        var callback = helpers.cb(args)
+        var client = helpers.client.validate(args)
+        if (args[0] instanceof UsergridClient) {
+            args.shift()
+        }
+        var body = {
+            oldpassword: _.isPlainObject(args[0]) ? args[0].oldPassword : _.isString(args[0]) ? args[0] : undefined,
+            newpassword: _.isPlainObject(args[0]) ? args[0].newPassword : _.isString(args[1]) ? args[1] : undefined
+        }
+        if (!body.oldpassword || !body.newpassword) {
+            throw new Error('"oldPassword" and "newPassword" properties are required when resetting a user password')
+        }
+        return new UsergridRequest({
+            client: client,
+            path: util.format('users/%s/password', helpers.user.uniqueId(self)),
+            method: 'PUT',
+            body: body
+        }, function(error, usergridResponse) {
+            callback(error, usergridResponse, usergridResponse.ok)
+        })
+    }
+}
+
+util.inherits(UsergridUser, UsergridEntity)
+
+module.exports = UsergridUser
+module.exports.CheckAvailable = CheckAvailable
\ No newline at end of file
diff --git a/lib/userAuth.js b/lib/userAuth.js
new file mode 100644
index 0000000..5c61e5c
--- /dev/null
+++ b/lib/userAuth.js
@@ -0,0 +1,41 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var UsergridAuth = require('./auth'),
+    helpers = require('../helpers'),
+    util = require('util'),
+    _ = require('lodash')
+
+var UsergridUserAuth = function(options) {
+    var self = this
+    var args = _.flattenDeep(helpers.args(arguments))
+    if (_.isPlainObject(args[0])) {
+        options = args[0]
+    }
+    self.username = options.username || args[0]
+    self.email = options.email
+    if (options.password || args[1]) {
+        self.password = options.password || args[1]
+    }
+    self.tokenTtl = options.tokenTtl || args[2]
+    UsergridAuth.call(self)
+    _.assign(self, UsergridAuth)
+    return self
+}
+
+util.inherits(UsergridUserAuth, UsergridAuth)
+
+module.exports = UsergridUserAuth
\ No newline at end of file
diff --git a/package.json b/package.json
index 2d2579d..22011d9 100644
--- a/package.json
+++ b/package.json
@@ -1,43 +1,42 @@
 {
-  "name": "usergrid",
-  "version": "0.10.8",
-  "description": "A Node.js module for making API calls to App Services (Usergrid) from within Node.js",
-  "main": "./lib/usergrid.js",
+  "author": "Brandon Shelley",
+  "contributors": [{
+    "name": "Brandon Shelley",
+    "email": "brandon@codeblooded.io"
+  }, {
+    "name": "Robert Walsh",
+    "email": "rjwalsh1985@gmail.com"
+  }],
   "dependencies": {
-    "request": "2.12.x",
-    "inflection": "1.3.x"
+    "async": "latest",
+    "file": "latest",
+    "file-type": "^3.4.0",
+    "lodash": "~4.0",
+    "lodash-inflection": "latest",
+    "lodash-uuid": "latest",
+    "read-chunk": "^1.0.1",
+    "request": "latest",
+    "url-join": "latest",
+    "validator": "^4.5.0"
   },
+  "description": "The official Node.js SDK for Usergrid",
   "devDependencies": {
-    "mocha": "1.7.x",
-    "should": "1.2.1"
-  },
-  "scripts": {
-    "test": "mocha",
-    "start": "node example/server.js"
+    "chance": "^0.8.0",
+    "mocha": "latest",
+    "should": "latest"
   },
   "repository": {
     "type": "git",
-    "url": "git://github.com/apigee/usergrid-node-module.git"
+    "url": "git://github.com/brandonscript/usergrid-nodejs.git"
   },
-  "bugs": {
-    "url": "http://github.com/apigee/usergrid-node-module.git/issues"
+  "keywords": [],
+  "license": "Apache 2.0",
+  "main": "usergrid.js",
+  "name": "usergrid",
+  "private": false,
+  "scripts": {
+    "start": "node usergrid.js",
+    "test": "mocha tests"
   },
-  "keywords": [
-    "Node",
-    "Usergrid",
-    "Apigee",
-    "API"
-  ],
-  "tags": [
-    "usergrid",
-    "API",
-    "Apigee"
-  ],
-  "author": {
-    "name": "Rod Simpson",
-    "email": "rod@rodsimpson.com",
-    "url" : "http://rodsimpson.com"
-  },
-  "license": "Apache 2.0"
+  "version": "2.0.0-rc.2"
 }
-
diff --git a/readme.md b/readme.md
deleted file mode 100755
index 474d506..0000000
--- a/readme.md
+++ /dev/null
@@ -1,720 +0,0 @@
-# Usergrid Node.js SDK
-
-##Version
-
-Current Version: **0.10.8**
-
-See change log:
-
-<https://github.com/apache/usergrid-nodejs/blob/master/changelog.md>
-
-
-##Comments / Questions
-Please feel free to send comments or questions:
-
-	twitter: @rockerston
-	email: rockerston at apache.org
-
-Or just open github issues.  I truly want to know what you think, and will address all suggestions / comments / concerns.
-
-Thank you!
-
-Rod
-
-
-##Overview
-This Node.js module, which simplifies the process of making API calls to App Services from within Node.js, is available as an open-source project on github.  We welcome your contributions and suggestions. The repository is located here:
-
-<https://github.com/apache/usergrid-nodejs>
-
-
-##Client side Javascript
-Want to make calls to Usergrid client-side? No problem - just head over to the Usergrid Javascript SDK:
-
-<https://github.com/apache/usergrid-javascript>
-
-The syntax for this Node module and the Javascript SDK are almost exactly the same so you can easily transition between them.
-
-
-##Installing
-Use npm:
-
-	$ npm install usergrid
-
-
-##Getting started
-Include the module:
-
-	var usergrid = require('usergrid');
-
-Then create a new client:
-
-	var client = new usergrid.client({
-		orgName:'yourorgname',
-		appName:'sandbox',
-		logging: true, //optional - turn on logging, off by default
-	});
-
-The preceding example shows how to use the "Sandbox" testing app, which does not require any authentication.  The "Sandbox" comes with all new App Services accounts.
-
-If you are ready to use authentication, then create your client this way:
-
-	var client = new usergrid.client({
-		orgName:'yourorgname',
-		appName:'yourappname',
-		authType:usergrid.AUTH_CLIENT_ID,
-		clientId:'<your client id>',
-		clientSecret:'<your client secret>',
-		logging: false, //optional - turn on logging, off by default
-		buildCurl: false //optional - turn on curl commands, off by default
-	});
-
-The last two items are optional. The **logging** option will enable console.log output from the client.  The **buildCurl** option will cause cURL equivalent commands of all calls to the API to be displayed in the console.log output.
-
-You are now ready to use the usergrid handle to make calls against the API.
-
-
-##About the samples
-All of the samples provided in this readme file come from unit tests in the test.js which is located in the root of this project.
-
-
-To run the test file, first do the following:
-
-1. Change the org-name and app-name to point to your Usergrid organization account.  
-2. Change the client secret and client id
-
-Then run the code:
-
-	$ node test.js
-
-The samples in this file will show you the many ways you can use this module.
-
-
-##Entities and Collections
-Usergrid stores its data as "Entities" in "Collections".  Entities are essentially JSON objects and Collections are just like folders for storing these objects. You can learn more about Entities and Collections in the App Services docs:
-
-<http://usergrid.apache.org/docs/introduction/data-model.html>
-
-
-##Entities
-This module provides an easy way to make new entities. Here is a simple example that shows how to create a new object of type "dogs":
-
-	var options = {
-		type:'dogs',
-		name:'Dino'
-	}
-	client.createEntity(options, function (err, dog) {
-		if (err) {
-			//error - dog not created
-		} else {
-			//success -dog is created
-
-			//once the dog is created, you can set single properties:
-			dog.set('breed','Dinosaur');
-
-			//or a JSON object:
-			var data = {
-				master:'Fred',
-				state:'hungry'
-			}
-			//set is additive, so previously set properties are not overwritten
-			dog.set(data);
-
-			//finally, call save on the object to save it back to the database
-			dog.save(function(err){
-				if (err){
-					//error - dog not saved
-				} else {
-					//success - new dog is saved
-				}
-			});
-		}
-	});
-
-**note:** all calls to the API will be executed asynchronously, so it is important that you use a callback.
-
-
-You can also refresh the object from the database if needed (in case the data has been updated by a different client or device):
-
-	//call fetch to refresh the data from the server
-	dog.fetch(function(err){
-		if (err){
-			// error - dog not refreshed from database;
-		} else {
-			//dog has been refreshed from the database
-			//will only work if the UUID for the entity is in the dog object
-			//success - dog entity refreshed from database;
-		}
-	});
-
-To remove the entity from the database:
-
-	//the destroy method will delete the entity from the database
-	dog.destroy(function(err){
-		if (err){
-			//error - dog not removed from database
-		} else {
-			//success - dog removed from database (no real dogs were harmed!)
-			dog = null; //no real dogs were harmed!
-		}
-	});
-
-To set properties on the entity, use the set() method:
-
-	//once the dog is created, you can set single properties:
-	dog.set('breed','Dinosaur');
-
-	//or a JSON object:
-	var data = {
-		master:'Fred',
-		state:'hungry'
-	}
-	//set is additive, so previously set properties are not overwritten
-	dog.set(data);
-
-**Note:** These properties are now set locally, but make sure you call the .save() method on the entity to save them back to the database!
-
-To get a single property from the entity, use the get method:
-
-	var breed = dog.get('breed');
-
-or
-
-	var state = dog.get('state');
-
-or, to get a JSON object with all properties, don't pass a key
-
-	var props = dog.get();
-
-Based on the set statements above, our JSON object should look like this:
-
-	{
-		name:'Dino',
-		type:'dogs',
-		breed:'Dinosaur',
-		master:'Fred',
-		state:'hungry'
-	}
-
-**Wait!** But what if my entity already exists on the server?
-
-During a client.createEntity call, there are two ways that you can choose to handle this situation.  The question is, what should the client do if an entity with the same name, username, or uuid already exists on the server?
-
-  	1. Give you back an error.
-  	2. Give you back the pre-existing entity.
-
-If you want to get back an error when the entity already exists, then simply call the client.createEntity function as above. If there is a collision, you will get back a 400  However, if you want the existing entity to be returned, then set the getOnExist flag to true:
-
-	var options = {
-		type:'dogs',
-		name:'Dino',
-		getOnExist:true
-	}
-	client.createEntity(options, function (err, dog) {
-		if (err) {
-			//error - dog not created
-		} else {
-			//success -dog is created or returned, depending on if it already exists or not
-
-
-Alternatively, if you know that you only want to retrieve an existing entity, use the getEntity method:
-
-	var options = {
-		type:'users',
-		username:'marty'
-	}
-	client.getEntity(options, function(err, existingUser){
-		if (err){
-			//error - existing user not retrieved
-		} else {
-			//success - existing user was retrieved
-
-			var username = existingUser.get('username');
-		}
-	});
-
-
-##The Collection object
-The Collection object models Collections in the database.  Once you start programming your app, you will likely find that this is the most useful method of interacting with the database.  Creating a collection will automatically populate the object with entities from the collection. The following example shows how to create a Collection object, then how to use entities once the Collection has been populated with entities from the server:
-
-	//options object needs to have the type (which is the collection type)
-	var options = {
-		type:'dogs',
-		qs:{ql:'order by index'}
-	}
-
-	client.createCollection(options, function (err, dogs) {
-		if (err) {
-			//error - could not make collection
-		} else {
-
-			//success - new Collection worked
-
-			//we got the dogs, now display the Entities:
-			while(dogs.hasNextEntity()) {
-				//get a reference to the dog
-				dog = dogs.getNextEntity();
-				var name = dog.get('name');
-				notice('dog is called ' + name);
-			}
-
-			//success - looped through dogs
-
-		}
-	});
-
-
-You can also add a new entity of the same type to the collection:
-
-	//create a new dog and add it to the collection
-	var options = {
-		name:'extra-dog',
-		fur:'shedding'
-	}
-	//just pass the options to the addEntity method
-	//to the collection and it is saved automatically
-	dogs.addEntity(options, function(err, dog, data) {
-		if (err) {
-			//error - extra dog not saved or added to collection
-		} else {
-			//success - extra dog saved and added to collection
-		}
-	});
-
-
-##Collection iteration and paging
-The Collection object works in Pages of data.  This means that at any given time, the Collection object will have one page of data loaded.  You can iterate across all the entities in the current page of data by using the following pattern:
-
-	//we got the dogs, now display the Entities:
-	while(dogs.hasNextEntity()) {
-		//get a reference to the dog
-		dog = dogs.getNextEntity();
-		var name = dog.get('name');
-		notice('dog is called ' + name);
-	}
-
-To get the next page of data from the server, use the following pattern:
-
-	if (dogs.hasNextPage()) {
-		//there is a next page, so get it from the server
-		dogs.getNextPage(function(err){
-			if (err) {
-				//error - could not get next page of dogs
-			} else {
-				//success - got next page of dogs
-				//we got the dogs, now display the Entities:
-				while(dogs.hasNextEntity()) {
-					//get a reference to the dog
-					dog = dogs.getNextEntity();
-					var name = dog.get('name');
-					notice('dog is called ' + name);
-				}
-				//success - looped through dogs
-			}
-		});
-	}
-
-You can use the same pattern to get a previous page of data:
-
-	if (dogs.hasPreviousPage()) {
-		//there is a previous page, so get it from the server
-		dogs.getPreviousPage(function(err){
-			if(err) {
-				//error - could not get previous page of dogs
-			} else {
-				//success - got next page of dogs
-				//we got the dogs, now display the Entities:
-				while(dogs.hasNextEntity()) {
-					//get a reference to the dog
-					dog = dogs.getNextEntity();
-					var name = dog.get('name');
-					notice('dog is called ' + name);
-				}
-				//success - looped through dogs
-			}
-		});
-	}
-
-By default, the database will return 10 entities per page.  You can change that amount by setting a limit:
-
-
-	var options = {
-		type:'dogs',
-		qs:{limit:50} //limit statement set to 50
-	}
-
-	client.createCollection(options, function (err, dogs) {
-		if (err) {
-			//error - could not get all dogs
-		} else {
-			//success - got at most 50 dogs
-		}
-	}
-
-Several other convenience methods exist to make working with pages of data easier:
-
-* getFirstEntity - gets the first entity of a page
-* getLastEntity - gets the last entity of a page
-* resetEntityPointer - sets the internal pointer back to the first element of the page
-* getEntityByUUID - returns the entity if it is in the current page
-
-
-###Custom Queries
-A custom query allows you to tell the API that you want your results filtered or altered in some way.  To specify that the query results should be ordered by creation date, add the qs parameter to the options object:
-
-	var options = {
-		type:'dogs',
-		qs:{ql:'order by created DESC'}
-	};
-
-You may find that you need to change the query on an existing object.  Simply access the qs property directly:
-
-	dogs.qs = {ql:'order by created DESC'};
-
-
-If you also wanted to get more entities in the result set than the default 10, say 100, you can specify a query similar to the following (the limit can be a maximum of 999):
-
-	dogs.qs = {ql:'order by created DESC',limit:'100'};
-
-**Note**: there are many cases where expanding the result set is useful.  But be careful - the more results you get back in a single call, the longer it will take to transmit the data back to your app.
-
-Another common requirement is to limit the results to a specific query.  For example, to get all brown dogs, use the following syntax:
-
-	dogs.qs = {ql:"select * where color='brown'"};
-
-You can also limit the results returned such that only the fields you specify are returned:
-
-	dogs.qs = {'ql':"select name, age where color='brown'"};
-
-**Note:** in the two preceding examples that we put single quotes around 'brown', so it will be searched as a string.
-
-You can find more information on custom queries here:
-
-<http://usergrid.apache.org/docs/data-queries/querying-your-data.html>
-
-
-##Modeling users with the Entity object
-There is no specific User object in the module.  Instead, you simply need to use the Entity object, specifying a type of "users".  Here is an example:
-
-	//type is 'users', set additional paramaters as needed
-	var options = {
-		type:'users',
-		username:'marty',
-		password:'mysecurepassword',
-		name:'Marty McFly',
-		city:'Hill Valley'
-	}
-
-  	client.createEntity(options, function (err, marty) {
-		if (err){
-			//error - user not saved
-		} else {
-			//success - user saved
-		}
-	});
-
-
-If the user is modified, just call save on the user again:
-
-	//add properties cumulatively
-	marty.set('state', 'California');
-	marty.set("girlfriend","Jennifer");
-	marty.save(function(err){
-		if (err){
-			//error - user not updated
-		} else {
-			//success - user updated
-		}
-	});
-
-To refresh the user's information in the database:
-
-	marty.fetch(function(err){
-		if (err){
-			//error - not refreshed
-		} else {
-			//success - user refreshed
-		}
-	});
-
-If you no longer need the object, call the delete() method and the object will be deleted from database:
-
-	marty.destroy(function(err){
-		if (err){
-			//error - user not deleted from database
-		} else {
-			//success - user deleted from database
-			marty = null; //blow away the local object
-		}
-	});
-
-
-###Making connections
-Connections are a way to connect to entities with some verb.  This is called an entity relationship.  For example, if you have a user entity with username of marty, and a dog entity with a name of einstein, then using our RESTful API, you could make a call like this:
-
-	POST users/marty/likes/dogs/einstein
-
-This creates a one-way connection between marty and einstein, where marty "likes" einstein.
-
-Complete documentation on the entity relationships API can be found here:
-
-<http://usergrid.apache.org/docs/entity-connections/connecting-entities.html>
-
-The following code shows you how to create this connection, and then verify that the connection has been made:
-
-	marty.connect('likes', dog, function (err, data) {
-		if (err) {
-			// error - connection not created
-		} else {
-
-			//call succeeded, so pull the connections back down
-			marty.getConnections('likes', function (err, data) {
-				if (err) {
-						//error - could not get connections
-				} else {
-					//verify that connection exists
-					if (marty.likes.ralphy) {
-						//success - connection exists
-					} else {
-						//error - connection does not exist
-					}
-				}
-			});
-		}
-	});
-
-You can also remove connections, by using the disconnect method:
-
-	marty.disconnect('likes', dog, function (err, data) {
-		if (err) {
-			//error - connection not deleted
-		} else {
-
-			//call succeeded, so pull the connections back down
-			marty.getConnections('likes', function (err, data) {
-				if (err) {
-					//error - error getting connections
-				} else {
-					//verify that connection exists
-					if (marty.likes.einstein) {
-						//error - connection still exists
-					} else {
-						//success - connection deleted
-					}
-				}
-			});
-		}
-	});
-
-
-###To log a user in
-Up to this point, we have shown how you can use the client secret / client id combination to authenticate your calls against the API.  For a server-side Node.js app, this may be all you need.  However, if you do find that your app requires that you authenticate an individual user, you have several options.
-
-The first is to use client-side authentication with Ajax.  If you want to opt for this method, take a look at our Javascript SDK.  The syntax for usage is the same as this Node.js module, so it will be easy to pick up:
-
-<https://github.com/apache/usergrid-javascript>
-
-The other method is to log the user in server-side. When you log a user in, the API will return an OAuth token for you to use for calls to the API on the user's behalf.  Once that token is returned, you can either make a new client just for the user, or change the auth method on the existing client.  These methods are described below:
-
-
-	username = 'marty';
-	password = 'mysecurepassword';
-	client.login(username, password,
-		function (err) {
-			if (err) {
-				//error - could not log user in
-			} else {
-				//success - user has been logged in
-
-				//the login call will return an OAuth token, which is saved
-				//in the client object for later use.  Access it this way:
-				var token = client.token;
-
-				//then make a new client just for the app user, then use this
-				//client to make calls against the API
-				var appUserClient = new usergrid.client({
-					orgName:'yourorgname',
-					appName:'yourappname',
-					authType:usergrid.AUTH_APP_USER,
-					token:token
-				});
-
-				//alternitavely, you can change the authtype of the client:
-				client.authType = usergrid.AUTH_APP_USER;
-
-				//Then make calls against the API.  For example, you can
-				//get the user entity this way:
-				client.getLoggedInUser(function(err, data, user) {
-					if(err) {
-						//error - could not get logged in user
-					} else {
-						//success - got logged in user
-
-						//you can then get info from the user entity object:
-						var username = user.get('username');
-
-						//to log the user out, call the logout() method
-						appUserClient.logout();
-						client.logout();
-
-						//verify the logout worked
-						if (client.isLoggedIn()) {
-							//error - logout failed
-						} else {
-							//success - user has been logged out
-						}
-
-						//since we don't need to App User level calls anymore,
-						//set the authtype back to client:
-						client.authType = usergrid.AUTH_CLIENT_ID;
-
-						runner(step, marty);
-					}
-				});
-
-			}
-		}
-	);
-
-
-To recap, once a user has been logged in, and an OAuth token has been acquired, use one of the two methods to make calls to the API:
-
-1. Use the same client object and change auth types before each call
-
-2. Grab the token and make a new client object specifically for user calls.
-
-Either method will work.
-
-
-###To log a user out
-To log the user out, call:
-
-	client.logout();
-
-Or, if you made a new client object specifically for the app user:
-
-	appUserClient.logout();
-
-This destroys the token and user object in the client object, effectively logging the user out.
-
-##Groups
-This module provides an easy way to make new groups. They follow the same syntax as Entities
-
-##Making generic calls
-If you find that you need to make calls to the API that fall outside of the scope of the Entity and Collection objects, you can use the following format to make any REST calls against the API:
-
-	client.request(options, callback);
-
-This format allows you to make almost any call against the App Services (Usergrid) API. For example, to get a list of users:
-
-	var options = {
-		method:'GET',
-		endpoint:'users'
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			//error - GET failed
-		} else {
-			//data will contain raw results from API call
-			//success - GET worked
-		}
-	});
-
-Or, to create a new user:
-
-	var options = {
-		method:'POST',
-		endpoint:'users',
-		body:{ username:'fred', password:'secret' }
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			//error - POST failed
-		} else {
-			//data will contain raw results from API call
-			//success - POST worked
-		}
-	});
-
-Or, to update the new user:
-
-	var options = {
-		method:'PUT',
-		endpoint:'users/fred',
-		body:{ newkey:'newvalue' }
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			//error - PUT failed
-		} else {
-			//data will contain raw results from API call
-			//success - PUT worked
-		}
-	});
-
-Or to delete the new user:
-
-	var options = {
-		method:'DELETE',
-		endpoint:'users/fred'
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			//error - DELETE failed
-		} else {
-			//data will contain raw results from API call
-			//success - DELETE worked
-		}
-	});
-
-The Options Object for the client.request fuction:
-
-* `method` - http method (GET, POST, PUT, or DELETE), defaults to GET
-* `qs` - object containing querystring values to be appended to the uri
-* `body` - object containing entity body for POST and PUT requests
-* `endpoint` - API endpoint, for example "users/fred"
-* `mQuery` - boolean, set to true if running management query, defaults to false
-* `buildCurl` - boolean, set to true if you want to see equivalent curl commands in console.log, defaults to false
-
-You can make any call to the API using the format above.  However, in practice using the higher level Entity and Collection objects will make life easier as they take care of much of the heavy lifting.
-
-
-###cURL
-[cURL](http://curl.haxx.se/) is an excellent way to make calls directly against the API. As mentioned in the **Getting started** section of this guide, one of the parameters you can add to the new client options object is **buildCurl**:
-
-	var client = new Usergrid.Client({
-		orgName:'yourorgname',
-		appName:'sandbox',
-		logging: true, //optional - turn on logging, off by default
-		buildCurl: true //optional - turn on curl commands, off by default
-	});
-
-If you set this parameter to true, the SDK will build equivalent curl commands and send them to the console.log window.
-
-More information on cURL can be found here:
-
-<http://curl.haxx.se/>
-
-## Contributing
-We welcome your enhancements!
-
-Like [Usergrid](https://github.com/apache/usergrid-nodejs), the Usergrid Javascript SDK is open source and licensed under the Apache License, Version 2.0.
-
-1. Fork it
-2. Create your feature branch (`git checkout -b my-new-feature`)
-3. Commit your changes (`git commit -am 'Added some feature'`)
-4. Push your changes to the upstream branch (`git push origin my-new-feature`)
-5. Create new Pull Request (make sure you describe what you did and why your mod is needed)
-
-
-Licensed under the Apache License, Version 2.0 (the "License");
-you may not use this file except in compliance with the License.
-You may obtain a copy of the License at
-
-<http://www.apache.org/licenses/LICENSE-2.0>
-
-Unless required by applicable law or agreed to in writing, software
-distributed under the License is distributed on an "AS IS" BASIS,
-WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-See the License for the specific language governing permissions and
-limitations under the License.
\ No newline at end of file
diff --git a/test.js b/test.js
deleted file mode 100755
index 354f8cb..0000000
--- a/test.js
+++ /dev/null
@@ -1,1077 +0,0 @@
-//
-// Licensed to the Apache Software Foundation (ASF) under one or more
-// contributor license agreements.  See the NOTICE file distributed with
-// this work for additional information regarding copyright ownership.
-// The ASF licenses this file to You under the Apache License, Version 2.0
-// (the "License"); you may not use this file except in compliance with
-// the License.  You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-//
-
-/**
-* Test suite for all the examples in the readme
-*
-* NOTE: No, this test suite doesn't use the traditional format for
-* a test suite.  This is because the goal is to require as little
-* alteration as possible during the copy / paste operation from this test
-* suite to the readme file.
-*
-* @author rod simpson (rod@apigee.com)
-*/
-
-
-var usergrid = require('./lib/usergrid');
-
-var logSuccess = true;
-var successCount = 0;
-var logError = true;
-var errorCount = 0;
-var logNotice = true;
-var _unique = new Date().getTime();
-var _username = 'marty'+_unique;
-var _email = 'marty'+_unique+'@timetravel.com';
-var _password = 'password2';
-var _newpassword = 'password3';
-
-var client = new usergrid.client({
-	orgName:'yourorgname',
-	appName:'sandbox',
-	logging: true, //optional - turn on logging, off by default
-	buildCurl: true //optional - turn on curl commands, off by default
-});
-
-
-//call the runner function to start the process
-client.logout();
-runner(0);
-
-function runner(step, arg, arg2){
-	step++;
-	switch(step)
-	{
-		case 1:
-			notice('-----running step '+step+': DELETE user from DB to prep test');
-			clearUser(step);
-			break;
-		case 2:
-			notice('-----running step '+step+': GET test');
-			testGET(step);
-			break;
-		case 3:
-			notice('-----running step '+step+': POST test');
-			testPOST(step);
-			break;
-		case 4:
-			notice('-----running step '+step+': PUT test');
-			testPUT(step);
-			break;
-		case 5:
-			notice('-----running step '+step+': DELETE test');
-			testDELETE(step);
-			break;
-		case 6:
-			notice('-----running step '+step+': prepare database - remove all dogs (no real dogs harmed here!!)');
-			cleanupAllDogs(step);
-			break;
-		case 7:
-			notice('-----running step '+step+': make a new dog');
-			makeNewDog(step);
-			break;
-		case 8:
-			notice('-----running step '+step+': update our dog');
-			updateDog(step, arg);
-			break;
-		case 9:
-			notice('-----running step '+step+': refresh our dog');
-			refreshDog(step, arg);
-			break;
-		case 10:
-			notice('-----running step '+step+': remove our dog from database (no real dogs harmed here!!)');
-			removeDogFromDatabase(step, arg);
-			break;
-		case 11:
-			notice('-----running step '+step+': make lots of dogs!');
-			makeSampleData(step, arg);
-			break;
-		case 12:
-			notice('-----running step '+step+': make a dogs collection and show each dog');
-			testDogsCollection(step);
-			break;
-		case 13:
-			notice('-----running step '+step+': get the next page of the dogs collection and show each dog');
-			getNextDogsPage(step, arg);
-			break;
-		case 14:
-			notice('-----running step '+step+': get the previous page of the dogs collection and show each dog');
-			getPreviousDogsPage(step, arg);
-			break;
-		case 15:
-			notice('-----running step '+step+': remove all dogs from the database (no real dogs harmed here!!)');
-			cleanupAllDogs(step);
-			break;
-		case 16:
-			notice('-----running step '+step+': prepare database (remove existing user if present)');
-			prepareDatabaseForNewUser(step);
-			break;
-		case 17:
-			notice('-----running step '+step+': create a new user');
-			createUser(step);
-			break;
-		case 18:
-			notice('-----running step '+step+': update the user');
-			updateUser(step, arg);
-			break;
-		case 19:
-			notice('-----running step '+step+': get the existing user');
-			getExistingUser(step, arg);
-			break;
-		case 20:
-			notice('-----running step '+step+': refresh the user from the database');
-			refreshUser(step, arg);
-			break;
-		case 21:
-			notice('-----running step '+step+': log user in');
-			loginUser(step, arg);
-			break;
-		case 22:
-			notice('-----running step '+step+': change users password');
-			changeUsersPassword(step, arg);
-			break;
-		case 23:
-			notice('-----running step '+step+': log user out');
-			logoutUser(step, arg);
-			break;
-		case 24:
-			notice('-----running step '+step+': relogin user');
-			reloginUser(step, arg);
-			break;
-		case 25:
-			notice('-----running step '+step+': logged in user creates dog');
-			createDog(step, arg);
-			break;
-		case 26:
-			notice('-----running step '+step+': logged in user likes dog');
-			userLikesDog(step, arg, arg2);
-			break;
-		case 27:
-			notice('-----running step '+step+': logged in user removes likes connection to dog');
-			removeUserLikesDog(step, arg, arg2);
-			break;
-		case 28:
-			notice('-----running step '+step+': user removes dog');
-			removeDog(step, arg, arg2);
-			break;
-		case 29:
-			notice('-----running step '+step+': log the user out');
-			logoutUser(step, arg);
-			break;
-		case 30:
-			notice('-----running step '+step+': remove the user from the database');
-			destroyUser(step, arg);
-			break;
-		case 31:
-			notice('-----running step '+step+': try to create existing entity');
-			createExistingEntity(step, arg);
-			break;
-		case 32:
-			notice('-----running step '+step+': try to create new entity with no name');
-			createNewEntityNoName(step, arg);
-			break;
-		case 33:
-			notice('-----running step '+step+': clean up users');
-      cleanUpUsers(step, arg);
-			break;
-		case 34:
-			notice('-----running step '+step+': clean up dogs');
-      cleanUpDogs(step, arg);
-			break;
-		case 35:
-			notice('-----running step '+step+': create counter');
-      counterCreate(step, arg);
-			break;
-		case 36:
-			notice('-----running step '+step+': reset counter');
-      counterReset(step, arg);
-			break;
-		case 37:
-			notice('-----running step '+step+': increment counter');
-      counterIncrement(step, arg);
-			break;
-		case 38:
-			notice('-----running step '+step+': decrement counter');
-      counterDecrement(step, arg);
-			break;
-		case 34:
-			notice('-----running step '+step+': fetch counter data');
-      counterFetch(step, arg);
-			break;
-		default:
-			notice('-----test complete!-----');
-			notice('Success count= ' + successCount);
-			notice('Error count= ' + errorCount);
-			notice('-----thank you for playing!-----');
-	}
-}
-
-//logging functions
-function success(message){
-	successCount++;
-	if (logSuccess) {
-		console.log('SUCCESS: ' + message);
-	}
-}
-
-function error(message){
-	errorCount++
-	if (logError) {
-		console.log('ERROR: ' + message);
-	}
-}
-
-function notice(message){
-	if (logNotice) {
-		console.log('NOTICE: ' + message);
-	}
-}
-
-//tests
-function clearUser(step) {
-  var options = {
-    method:'DELETE',
-    endpoint:'users/fred'
-  };
-  client.request(options, function (err, data) {
-    //data will contain raw results from API call
-    success('User cleared from DB');
-    runner(step);
-  });
-}
-
-function testGET(step) {
-	var options = {
-		method:'GET',
-		endpoint:'users'
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			error('GET failed');
-		} else {
-			//data will contain raw results from API call
-			success('GET worked');
-			runner(step);
-		}
-	});
-}
-
-function testPOST(step) {
-	var options = {
-		method:'POST',
-		endpoint:'users',
-		body:{ username:'fred', password:'secret' }
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			error('POST failed');
-		} else {
-			//data will contain raw results from API call
-			success('POST worked');
-			runner(step);
-		}
-	});
-}
-
-function testPUT(step) {
-	var options = {
-		method:'PUT',
-		endpoint:'users/fred',
-		body:{ newkey:'newvalue' }
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			error('PUT failed');
-		} else {
-			//data will contain raw results from API call
-			success('PUT worked');
-			runner(step);
-		}
-	});
-}
-
-function testDELETE(step) {
-	var options = {
-		method:'DELETE',
-		endpoint:'users/fred'
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			error('DELETE failed');
-		} else {
-			//data will contain raw results from API call
-			success('DELETE worked');
-			runner(step);
-		}
-	});
-}
-
-function makeNewDog(step) {
-
-	var options = {
-		type:'dogs',
-		name:'Ralph'+_unique
-	}
-
-	client.createEntity(options, function (err, dog) {
-		if (err) {
-			error('dog not created');
-		} else {
-			success('dog is created');
-
-			//once the dog is created, you can set single properties:
-			dog.set('breed','Dinosaur');
-
-			//the set function can also take a JSON object:
-			var data = {
-				master:'Fred',
-				state:'hungry'
-			}
-			//set is additive, so previously set properties are not overwritten
-			dog.set(data);
-
-			//finally, call save on the object to save it back to the database
-			dog.save(function(err){
-				if (err){
-					error('dog not saved');
-				} else {
-					success('new dog is saved');
-					runner(step, dog);
-				}
-			});
-		}
-	});
-
-}
-
-function updateDog(step, dog) {
-
-	//change a property in the object
-	dog.set("state", "fed");
-	//and save back to the database
-	dog.save(function(err){
-		if (err){
-			error('dog not saved');
-		} else {
-			success('dog is saved');
-			runner(step, dog);
-		}
-	});
-
-}
-
-function refreshDog(step, dog){
-
-	//call fetch to refresh the data from the server
-	dog.fetch(function(err){
-		if (err){
-			error('dog not refreshed from database');
-		} else {
-			//dog has been refreshed from the database
-			//will only work if the UUID for the entity is in the dog object
-			success('dog entity refreshed from database');
-			runner(step, dog);
-		}
-	});
-
-}
-
-function removeDogFromDatabase(step, dog){
-
-	//the destroy method will delete the entity from the database
-	dog.destroy(function(err){
-		if (err){
-			error('dog not removed from database');
-		} else {
-			success('dog removed from database'); // no real dogs were harmed!
-			dog = null; //no real dogs were harmed!
-			runner(step, 1);
-		}
-	});
-
-}
-
-function makeSampleData(step, i) {
-	notice('making dog '+i);
-
-	var options = {
-		type:'dogs',
-		name:'dog'+_unique+i,
-		index:i
-	}
-
-	client.createEntity(options, function (err, dog) {
-		if (err) {
-			error('dog ' + i + ' not created');
-		} else {
-			if (i >= 30) {
-				//data made, ready to go
-				success('all dogs made');
-				runner(step);
-			} else {
-				success('dog ' + i + ' made');
-				//keep making dogs
-				makeSampleData(step, ++i);
-			}
-		}
-	});
-}
-
-function testDogsCollection(step) {
-
-	var options = {
-		type:'dogs',
-		qs:{ql:'order by index'}
-	}
-
-	client.createCollection(options, function (err, dogs) {
-		if (err) {
-			error('could not make collection');
-		} else {
-
-			success('new Collection created');
-
-			//we got the dogs, now display the Entities:
-			while(dogs.hasNextEntity()) {
-				//get a reference to the dog
-				dog = dogs.getNextEntity();
-				var name = dog.get('name');
-				notice('dog is called ' + name);
-			}
-
-			success('looped through dogs');
-
-			//create a new dog and add it to the collection
-			var options = {
-				name:'extra-dog',
-				fur:'shedding'
-			}
-			//just pass the options to the addEntity method
-			//to the collection and it is saved automatically
-			dogs.addEntity(options, function(err, dog, data) {
-				if (err) {
-					error('extra dog not saved or added to collection');
-				} else {
-					success('extra dog saved and added to collection');
-					runner(step, dogs);
-				}
-			});
-		}
-	});
-
-}
-
-function getNextDogsPage(step, dogs) {
-
-	if (dogs.hasNextPage()) {
-		//there is a next page, so get it from the server
-		dogs.getNextPage(function(err){
-			if (err) {
-				error('could not get next page of dogs');
-			} else {
-				success('got next page of dogs');
-				//we got the next page of data, so do something with it:
-				var i = 11;
-				while(dogs.hasNextEntity()) {
-					//get a reference to the dog
-					var dog = dogs.getNextEntity();
-					var index = dog.get('index');
-					if(i !== index) {
-						error('wrong dog loaded: wanted' + i + ', got ' + index);
-					}
-					notice('got dog ' + i);
-					i++
-				}
-				success('looped through dogs')
-				runner(step, dogs);
-			}
-		});
-	} else {
-		getPreviousDogsPage(dogs);
-	}
-
-}
-
-function getPreviousDogsPage(step, dogs) {
-
-	if (dogs.hasPreviousPage()) {
-		//there is a previous page, so get it from the server
-		dogs.getPreviousPage(function(err){
-			if(err) {
-				error('could not get previous page of dogs');
-			} else {
-				success('got next page of dogs');
-				//we got the previous page of data, so do something with it:
-				var i = 1;
-				while(dogs.hasNextEntity()) {
-					//get a reference to the dog
-					var dog = dogs.getNextEntity();
-					var index = dog.get('index');
-					if(i !== index) {
-						error('wrong dog loaded: wanted' + i + ', got ' + index);
-					}
-					notice('got dog ' + i);
-					i++
-				}
-				success('looped through dogs');
-				runner(step);
-			}
-		});
-	} else {
-		getAllDogs();
-	}
-}
-
-function cleanupAllDogs(step){
-
-	var options = {
-		type:'dogs',
-		qs:{limit:50} //limit statement set to 50
-	}
-
-	client.createCollection(options, function (err, dogs) {
-		if (err) {
-			error('could not get all dogs');
-		} else {
-			success('got at most 50 dogs');
-			//we got 50 dogs, now display the Entities:
-			while(dogs.hasNextEntity()) {
-				//get a reference to the dog
-				var dog = dogs.getNextEntity();
-				var name = dog.get('name');
-				notice('dog is called ' + name);
-			}
-			dogs.resetEntityPointer();
-			//do doggy cleanup
-			while(dogs.hasNextEntity()) {
-				//get a reference to the dog
-				var dog = dogs.getNextEntity();
-				var dogname = dog.get('name');
-				notice('removing dog ' + dogname + ' from database');
-				dog.destroy(function(err, data) {
-					if (err) {
-						error('dog not removed');
-					} else {
-						success('dog removed');
-					}
-				});
-			}
-
-			//no need to wait around for dogs to be removed, so go on to next test
-			runner(step);
-		}
-	});
-}
-
-
-function prepareDatabaseForNewUser(step) {
-	var options = {
-		method:'DELETE',
-		endpoint:'users/',
-    qs:{ql:"select * where username ='marty*'"}
-	};
-	client.request(options, function (err, data) {
-		if (err) {
-			notice('database ready - no user to delete');
-		runner(step);
-		} else {
-			//data will contain raw results from API call
-			success('database ready - user deleted worked');
-			runner(step);
-		}
-	});
-}
-
-function createUser(step) {
-	client.signup(_username, _password, _email, 'Marty McFly',
-		function (err, marty) {
-			if (err){
-				error('user not created');
-				runner(step, marty);
-			} else {
-				success('user created');
-				runner(step, marty);
-			}
-		}
-	);
-}
-
-function updateUser(step, marty) {
-
-	//add properties cumulatively
-	marty.set('state', 'California');
-	marty.set("girlfriend","Jennifer");
-	marty.save(function(err){
-		if (err){
-			error('user not updated');
-		} else {
-			success('user updated');
-			runner(step, marty);
-		}
-	});
-
-}
-
-function getExistingUser(step, marty) {
-
-	var options = {
-		type:'users',
-		username:_username
-	}
-	client.getEntity(options, function(err, existingUser){
-		if (err){
-			error('existing user not retrieved');
-		} else {
-			success('existing user was retrieved');
-
-			var username = existingUser.get('username');
-			if (username === _username){
-				success('got existing user username');
-			} else {
-				error('could not get existing user username');
-			}
-			runner(step, marty);
-		}
-	});
-
-}
-
-
-function refreshUser(step, marty) {
-
-	marty.fetch(function(err){
-		if (err){
-			error('not refreshed');
-		} else {
-			success('user refreshed');
-			runner(step, marty);
-		}
-	});
-
-}
-
-function loginUser(step, marty) {
-	username = _username;
-	password = _password;
-	client.login(username, password,
-		function (err) {
-			if (err) {
-				error('could not log user in');
-			} else {
-				success('user has been logged in');
-
-				//the login call will return an OAuth token, which is saved
-				//in the client object for later use.  Access it this way:
-				var token = client.token;
-
-				//then make a new client just for the app user, then use this
-				//client to make calls against the API
-				var appUserClient = new usergrid.client({
-					orgName:'yourorgname',
-					appName:'yourappname',
-					authType:usergrid.AUTH_APP_USER,
-					token:token
-				});
-
-				//alternitavely, you can change the authtype of the client:
-				client.authType = usergrid.AUTH_APP_USER;
-
-				//Then make calls against the API.  For example, you can
-				//get the user entity this way:
-				client.getLoggedInUser(function(err, data, user) {
-					if(err) {
-						error('could not get logged in user');
-					} else {
-						success('got logged in user');
-
-						//you can then get info from the user entity object:
-						var username = user.get('username');
-						notice('logged in user was: ' + username);
-
-						runner(step, user);
-					}
-				});
-
-			}
-		}
-	);
-}
-
-function changeUsersPassword(step, marty) {
-
-	marty.set('oldpassword', _password);
-	marty.set('newpassword', _newpassword);
-	marty.save(function(err){
-		if (err){
-			error('user password not updated');
-		} else {
-			success('user password updated');
-			runner(step, marty);
-		}
-	});
-
-}
-
-function logoutUser(step, marty) {
-
-	//to log the user out, call the logout() method
-	client.logout();
-
-	//verify the logout worked
-	if (client.isLoggedIn()) {
-		error('logout failed');
-	} else {
-		success('user has been logged out');
-	}
-
-	runner(step, marty);
-}
-
-function reloginUser(step, marty) {
-
-	username = _username
-	password = _newpassword;
-	client.login(username, password,
-		function (err) {
-		if (err) {
-			error('could not relog user in');
-		} else {
-			success('user has been re-logged in');
-			runner(step, marty);
-		}
-		}
-	);
-}
-
-
-
-//TODO: currently, this code assumes permissions have been set to support user actions.  need to add code to show how to add new role and permission programatically
-//
-//first create a new permission on the default role:
-//POST "https://api.usergrid.com/yourorgname/yourappname/roles/default/permissions" -d '{"permission":"get,post,put,delete:/dogs/**"}'
-//then after user actions, delete the permission on the default role:
-//DELETE "https://api.usergrid.com/yourorgname/yourappname/roles/default/permissions?permission=get%2Cpost%2Cput%2Cdelete%3A%2Fdogs%2F**"
-
-
-function createDog(step, marty) {
-  //see if marty can create a new dog now that he is logged in
-
-	var options = {
-		type:'dogs',
-		name:'einstein',
-		breed:'mutt'
-	}
-
-	client.createEntity(options, function (err, dog) {
-		if (err) {
-			error('POST new dog by logged in user failed');
-		} else {
-			success('POST new dog by logged in user succeeded');
-			runner(step, marty, dog);
-		}
-	});
-
-}
-
-function userLikesDog(step, marty, dog) {
-
-	marty.connect('likes', dog, function (err, data) {
-		if (err) {
-			error('connection not created');
-			runner(step, marty);
-		} else {
-
-			//call succeeded, so pull the connections back down
-			marty.getConnections('likes', function (err, data) {
-				if (err) {
-						error('could not get connections');
-				} else {
-					//verify that connection exists
-					if (marty.likes.einstein) {
-						success('connection exists');
-					} else {
-						error('connection does not exist');
-					}
-
-					runner(step, marty, dog);
-				}
-			});
-		}
-	});
-
-}
-
-function removeUserLikesDog(step, marty, dog) {
-
-	marty.disconnect('likes', dog, function (err, data) {
-		if (err) {
-			error('connection not deleted');
-			runner(step, marty);
-		} else {
-
-			//call succeeded, so pull the connections back down
-			marty.getConnections('likes', function (err, data) {
-				if (err) {
-					error('error getting connections');
-				} else {
-					//verify that connection exists
-					if (marty.likes.einstein) {
-						error('connection still exists');
-					} else {
-						success('connection deleted');
-					}
-
-					runner(step, marty, dog);
-				}
-			});
-		}
-	});
-
-}
-
-function removeDog(step, marty, dog) {
-
-	//now delete the dog from the database
-	dog.destroy(function(err, data) {
-		if (err) {
-			error('dog not removed');
-		} else {
-			success('dog removed');
-		}
-	});
-	runner(step, marty);
-}
-
-function destroyUser(step, marty) {
-
-	marty.destroy(function(err){
-		if (err){
-			error('user not deleted from database');
-		} else {
-			success('user deleted from database');
-			marty = null; //blow away the local object
-			runner(step);
-		}
-	});
-
-}
-
-function createExistingEntity(step, marty) {
-
-	var options = {
-		type:'dogs',
-		name:'einstein'
-	}
-
-	client.createEntity(options, function (err, dog) {
-		if (err) {
-			error('Create new entity to use for existing entity failed');
-		} else {
-			success('Create new entity to use for existing entity succeeded');
-
-			var uuid = dog.get('uuid');
-			//now create new entity, but use same entity name of einstein.  This means that
-			//the original einstein entity now exists.  Thus, the new einstein entity should
-			//be the same as the original + any data differences from the options var:
-
-			options = {
-				type:'dogs',
-				name:'einstein',
-				breed:'mutt'
-			}
-			client.createEntity(options, function (err, newdog) {
-				if (err) {
-					error('Create new entity to use for existing entity failed');
-				} else {
-					success('Create new entity to use for existing entity succeeded');
-
-					var newuuid = newdog.get('uuid');
-					if (newuuid === uuid) {
-						success('UUIDs of new and old entities match');
-					} else {
-						error('UUIDs of new and old entities do not match');
-					}
-
-					var breed = newdog.get('breed');
-					if (breed === 'mutt') {
-						success('attribute sucesfully set on new entity');
-					} else {
-						error('attribute not sucesfully set on new entity');
-					}
-
-					newdog.destroy(function(err){
-						if (err){
-							error('existing entity not deleted from database');
-						} else {
-							success('existing entity deleted from database');
-							dog = null; //blow away the local object
-							newdog = null; //blow away the local object
-							runner(step);
-						}
-					});
-
-				}
-			});
-		}
-	});
-
-}
-
-function createNewEntityNoName(step, marty) {
-
-	var options = {
-   type:"something",
-   othervalue:"something else"
-	}
-
-	client.createEntity(options, function (err, entity) {
-		if (err) {
-			error('Create new entity with no name failed');
-		} else {
-			success('Create new entity with no name succeeded');
-
-      entity.destroy();
-      runner(step);
-		}
-	});
-
-}
-
-function cleanUpUsers(step){
-
-  var options = {
-    type:'users',
-    qs:{limit:50} //limit statement set to 50
-  }
-
-  client.createCollection(options, function (err, users) {
-    if (err) {
-      error('could not get all users');
-    } else {
-      success('got users');
-      //do doggy cleanup
-      while(users.hasNextEntity()) {
-        //get a reference to the dog
-        var user = users.getNextEntity();
-        var username = user.get('name');
-        notice('removing dog ' + username + ' from database');
-        user.destroy(function(err, data) {
-          if (err) {
-            error('user not removed');
-          } else {
-            success('user removed');
-          }
-        });
-      }
-
-      runner(step);
-    }
-  });
-
-}
-
-function cleanUpDogs(step){
-
-    var options = {
-      type:'dogs',
-      qs:{limit:50} //limit statement set to 50
-    }
-
-    client.createCollection(options, function (err, dogs) {
-      if (err) {
-        error('could not get all dogs');
-      } else {
-        success('got at most 50 dogs');
-        //we got 50 dogs, now display the Entities:
-        while(dogs.hasNextEntity()) {
-          //get a reference to the dog
-          var dog = dogs.getNextEntity();
-          var name = dog.get('name');
-          notice('dog is called ' + name);
-        }
-        dogs.resetEntityPointer();
-        //do doggy cleanup
-        while(dogs.hasNextEntity()) {
-          //get a reference to the dog
-          var dog = dogs.getNextEntity();
-          var dogname = dog.get('name');
-          notice('removing dog ' + dogname + ' from database');
-          dog.destroy(function(err, data) {
-            if (err) {
-              error('dog not removed');
-            } else {
-              success('dog removed');
-            }
-          });
-        }
-
-        //no need to wait around for dogs to be removed, so go on to next test
-        runner(step);
-      }
-    });
-  }
-//var counter;
-function counterCreate(step){
-	var counter = new usergrid.counter({client:client, data:{category:'mocha_test', timestamp:0, name:"test", counters:{test:0,test_counter:0}}}, function(err, data){
-        if (err) {
-          error('counter not removed');
-        } else {
-          success('counter created');
-        }
-	});
-	runner(step, counter);
-}
-function counterReset(step, counter){
-	counter.reset({name:'test'}, function(err, data){
-        if (err) {
-          error('counter not reset');
-        } else {
-          success('counter reset');
-        }
-		runner(step, counter);
-	});
-}
-function counterIncrement(step, counter){
-	counter.increment({name:'test', value:1}, function(err, data){
-        if (err) {
-          error('counter not incremented');
-        } else {
-          success('counter incremented');
-        }
-		runner(step, counter);
-	});
-}
-function counterDecrement(step, counter){
-	counter.decrement({name:'test', value:1}, function(err, data){
-        if (err) {
-          error('counter not decremented');
-        } else {
-          success('counter decremented');
-        }
-		runner(step, counter);
-	});
-}
-function counterFetch(step, counter){
-	counter.getData({resolution:'all', counters:['test', 'test_counter']}, function(err, data){
-        if (err) {
-          error('counter not fetched');
-        } else {
-          success('counter fetched');
-        }
-		runner(step, counter);
-	});
-}
diff --git a/test/client.js b/test/client.js
deleted file mode 100755
index 70f8d85..0000000
--- a/test/client.js
+++ /dev/null
@@ -1,183 +0,0 @@
-//
-// Licensed to the Apache Software Foundation (ASF) under one or more
-// contributor license agreements.  See the NOTICE file distributed with
-// this work for additional information regarding copyright ownership.
-// The ASF licenses this file to You under the Apache License, Version 2.0
-// (the "License"); you may not use this file except in compliance with
-// the License.  You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-//
-
-
-/**
-* Test suite for Client object
-*
-* @author rod simpson (rod@apigee.com)
-*/
-//require('assert');
-require('should');
-var usergrid = require('../lib/usergrid.js');
-
-//first set up the client
-var myclient = new usergrid.client(
-  {
-    orgName:"1hotrod"
-  , appName:"sandbox"
-  , authType:"CLIENT_ID"
-  , clientId:"b3U6y6hRJufDEeGW9hIxOwbREg"
-  , clientSecret:"b3U6X__fN2l9vd1HVi1kM9nJvgc-h5k"
-  }
-);
-
-describe('Standard Requests', function(){
-  describe('DELETE Method', function(){
-    it('should DELETE without error', function(done){
-      myclient.request(
-        { method:"DELETE"
-        , endpoint:"users/aaaaaa"
-        } ,done);
-    });
-  });
-  describe('cURL DELETE Method', function(){
-    it('should create a valid cURL calll for the DELETE without error', function(){
-      var options = {
-        method:"DELETE"
-        , uri:"https://api.usergrid.com/1hotrod/sandbox/users/aaaaaa"
-      }
-      var curl = myclient.buildCurlCall(options);
-      curl.should.equal('curl -X DELETE https://api.usergrid.com/1hotrod/sandbox/users/aaaaaa');
-    });
-  });
-
-
-  describe('POST Method', function(){
-    it('should POST without error', function(done){
-      myclient.request(
-        { method:"POST"
-        , endpoint:"users"
-        , body:{'username':'aaaaaa', 'password':'abcd1234'}
-        } ,done);
-    })
-  });
-  describe('cURL POST Method', function(){
-    it('should create a valid cURL calll for the POST without error', function(){
-      var options = {
-        method:"POST"
-        , uri:"https://api.usergrid.com/1hotrod/sandbox/users"
-        , body:{'username':'aaaaaa', 'password':'abcd1234'}
-      }
-      var curl = myclient.buildCurlCall(options);
-      curl.should.equal("curl -X POST https://api.usergrid.com/1hotrod/sandbox/users -d '{\"username\":\"aaaaaa\",\"password\":\"abcd1234\"}'");
-    });
-  });
-
-
-  describe('PUT Method', function(){
-    it('should PUT without error', function(done){
-      myclient.request(
-        { method:"PUT"
-        , endpoint:"users/aaaaaa"
-        , body:{'fred':'value'}
-        } ,done);
-    });
-  });
-  describe('cURL PUT Method', function(){
-    it('should create a valid cURL calll for the PUT without error', function(){
-      var options = {
-        method:"PUT"
-        , uri:"https://api.usergrid.com/1hotrod/sandbox/users"
-        , body:{'fred':'value'}
-      }
-      var curl = myclient.buildCurlCall(options);
-      curl.should.equal("curl -X PUT https://api.usergrid.com/1hotrod/sandbox/users -d '{\"fred\":\"value\"}'");
-    });
-  });
-
-
-  describe('GET Method', function(){
-    it('should GET without error', function(done){
-      myclient.request(
-        { method:"GET"
-        , endpoint:"users/aaaaaa"
-        } ,done);
-    });
-  });
-  describe('cURL GET Method', function(){
-    it('should create a valid cURL calll for the GET without error', function(){
-      var options = {
-        method:"GET"
-        , uri:"https://api.usergrid.com/1hotrod/sandbox/users/aaaaaa"
-      }
-      var curl = myclient.buildCurlCall(options);
-      curl.should.equal('curl -X GET https://api.usergrid.com/1hotrod/sandbox/users/aaaaaa');
-    });
-  });
-
-  describe('Login Method', function(){
-    it('should Login without error and get token', function(done){
-      myclient.login('aaaaaa', 'abcd1234', function(err){
-        if (err) throw err;
-
-        //test the token first
-        var token = myclient.token;
-        myclient.should.have.property('token');
-
-        //make sure we get a user back
-        var user = myclient.user;
-        var data = user.get();
-        data.should.have.property('username');
-
-        //test for logged in user
-        if (!myclient.isLoggedIn()) throw err;
-
-        //make a query with the app users token
-        myclient.authType = usergrid.APP_USER;
-
-        //do a get on /users
-        describe('GET Method', function(){
-          it('should GET without error', function(done){
-            myclient.request(
-              { method:"GET"
-              , endpoint:"users"
-              } ,done);
-          });
-        });
-
-        //go back to the
-        myclient.authType = usergrid.AUTH_CLIENT_ID;
-
-        //erase the token
-        myclient.token = null;
-        if (myclient.isLoggedIn()) throw err;
-
-        //reset the token
-        myclient.token = token;
-        if (!myclient.isLoggedIn()) throw err;
-
-        //clear the logged in user
-        myclient.user = null;
-        if (myclient.isLoggedIn()) throw err;
-
-        //replace the logged in user
-        myclient.user = user;
-        if (!myclient.isLoggedIn()) throw err;
-
-        //log the user out
-        myclient.logout();
-        if (myclient.isLoggedIn()) throw err;
-
-        //tests finished
-        done();
-      });
-    });
-  })
-
-});
-
diff --git a/test/collection.js b/test/collection.js
deleted file mode 100755
index 1a8eadb..0000000
--- a/test/collection.js
+++ /dev/null
@@ -1,259 +0,0 @@
-//
-// Licensed to the Apache Software Foundation (ASF) under one or more
-// contributor license agreements.  See the NOTICE file distributed with
-// this work for additional information regarding copyright ownership.
-// The ASF licenses this file to You under the Apache License, Version 2.0
-// (the "License"); you may not use this file except in compliance with
-// the License.  You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-//
-
-/**
-* Test suite for Collection object
-*
-* TODO: need to add coverage for the following methods:
-*
-* getFirstEntity
-* getLastEntity
-* hasPrevEntity
-* getPrevEntity
-* resetEntityPointer
-* resetPaging
-*
-* Need to add sample data for paging, check actual results
-*
-* @author rod simpson (rod@apigee.com)
-*/
-require("assert");
-require('should');
-var usergrid = require('../lib/usergrid.js');
-
-//first set up the client
-var myclient = new usergrid.client({
-  orgName:'1hotrod',
-  appName:'sandbox',
-  authType:'CLIENT_ID',
-  clientId:'b3U6y6hRJufDEeGW9hIxOwbREg',
-  clientSecret:'b3U6X__fN2l9vd1HVi1kM9nJvgc-h5k',
-  logging: true
-});
-
-describe('Collection methods - dogs', function(){
-  var doggies = {};
-
-  describe('make new collection', function(){
-    it('should make a new collection without error', function(done){
-      var options = {
-        client:myclient,
-        path:"dogs"
-      }
-      doggies = new usergrid.collection(options, done);
-    });
-  });
-
-  describe('check collection', function(){
-    it('should loop through all collection entities', function(){
-      while(doggies.hasNextEntity()) {
-        //get a reference to the dog
-        var dog = doggies.getNextEntity();
-        var data = dog.get();
-        data.should.have.property('name');
-      }
-    });
-  });
-});
-
-describe('Collection methods - users', function(){
-  var users = {};
-
-  describe('make new collection', function(){
-    it('should make a new collection without error', function(done){
-      var options = {
-        client:myclient,
-        path:'users'
-      }
-      users = new usergrid.collection(options, done);
-    });
-  });
-
-  describe('check collection', function(){
-    it('should loop through all collection entities', function(){
-      while(users.hasNextEntity()) {
-        //get a reference to the dog
-        var user = users.getNextEntity();
-        var data = user.get();
-        data.should.have.property('username');
-      }
-    });
-  });
-});
-
-describe('Collection methods - 1 user - barney', function(){
-  var users = {};
-  var uuid = '';
-  var user_barney = {};
-
-  describe('make new collection', function(){
-    it('should make a new collection without error', function(done){
-      var options = {
-        client:myclient,
-        path:'users',
-        qs:{"ql":"select * where username ='barney'"}
-      }
-      users = new usergrid.collection(options, done);
-    });
-  });
-
-  describe('check collection', function(){
-    it('should loop through all collection entities', function(){
-      while(users.hasNextEntity()) {
-        //get a reference to the dog
-        var user = users.getNextEntity();
-        var data = user.get();
-        data.should.have.property('username', 'barney');
-      }
-    });
-  });
-
-  describe('Add 1 user to collection', function(){
-    it('should make a new user and add it to collection without error', function(done){
-      //first delete the user if he exists (no assertion as the data may or may not be there)
-      myclient.request({
-        method:'DELETE',
-        endpoint:'users/fredflintster'
-        }, function(err) {
-          /// new entity creation
-          var data = {
-          	type:'users',
-            username: 'fredflintster',
-            password: 'barney',
-            email: 'email@myemail.com'
-          };
-          var options = {
-            client:myclient,
-            data:data
-          };
-          user_barney = new Entity(options);
-          users.addEntity(user_barney, done);
-        });
-    });
-  });
-
-  describe('Get 1 user from collection', function(){
-    it('should return user without error', function(done){
-      //make sure we get the uuid from barney
-      var data = user_barney.get();
-      data.should.have.property('uuid');
-
-      var uuid =  user_barney.get('uuid');
-      users.getEntityByUUID(uuid, function(err, data, user) {
-        user_barney = user;
-        var data = user_barney.get();
-        data.should.have.property('uuid');
-        uuid = user_barney.get('uuid');
-        done();
-      });
-    });
-  });
-
-  describe('remove entity from collection', function(){
-    it('should remove entity from collection without error', function(done){
-      users.destroyEntity(user_barney, done);
-    });
-  });
-
-});
-
-
-
-
-
-var messageeClient = new usergrid.client({
-  orgName:'apigee',
-  appName:'messageeapp',
-  authType:'CLIENT_ID',
-  clientId:'YXA6URHEY2pCEeG23RIxOAoChA',
-  clientSecret:'YXA6ukLeZvwB0JOdmAprY1azi9DtCPY',
-  logging: true
-});
-
-describe('Collection methods - users paging', function(){
-  var users = {};
-
-  describe('make new collection', function(){
-    it('should make a new collection without error', function(done){
-      var options = {
-        path:'users',
-        client:messageeClient
-      }
-      users = new usergrid.collection(options, done);
-    });
-  });
-
-  describe('check collection', function(){
-    it('should loop through all collection entities', function(){
-      while(users.hasNextEntity()) {
-        //get a reference to the dog
-        var user = users.getNextEntity();
-        var data = user.get();
-        data.should.have.property('username');
-        console.log(data.username);
-      }
-    });
-  });
-
-  describe('get next page', function(){
-    it('should get next page of users', function(done){
-      console.log('starting next page test');
-      if (users.hasNextPage()) {
-        console.log('next page - yes');
-        users.getNextPage(done);
-      } else {
-        done();
-      }
-    });
-  });
-
-  describe('check collection', function(){
-    it('should loop through all collection entities', function(){
-      while(users.hasNextEntity()) {
-        //get a reference to the dog
-        var user = users.getNextEntity();
-        var data = user.get();
-        data.should.have.property('username');
-        console.log(data.username);
-      }
-    });
-  });
-
-  describe('get previous page', function(){
-    it('should get previous page of users', function(done){
-      if (users.hasPreviousPage()) {
-        users.getPreviousPage(done);
-      } else {
-        done();
-      }
-    });
-  });
-
-  describe('check collection', function(){
-    it('should loop through all collection entities', function(){
-      while(users.hasNextEntity()) {
-        //get a reference to the dog
-        var user = users.getNextEntity();
-        var data = user.get();
-        data.should.have.property('username');
-        console.log(data.username);
-      }
-    });
-  });
-
-});
-
diff --git a/test/entity.js b/test/entity.js
deleted file mode 100755
index 3cd3b2e..0000000
--- a/test/entity.js
+++ /dev/null
@@ -1,59 +0,0 @@
-//
-// Licensed to the Apache Software Foundation (ASF) under one or more
-// contributor license agreements.  See the NOTICE file distributed with
-// this work for additional information regarding copyright ownership.
-// The ASF licenses this file to You under the Apache License, Version 2.0
-// (the "License"); you may not use this file except in compliance with
-// the License.  You may obtain a copy of the License at
-//
-//     http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-//
-
-/**
-* Test suite for Entity object
-*
-* Run with mocha v. 1.7.x
-* http://visionmedia.github.com/mocha/
-*
-* @author rod simpson (rod@apigee.com)
-*/
-require("assert");
-var usergrid = require('../lib/usergrid.js');
-
-//first set up the client
-var client = new usergrid.client({
-  orgName:'1hotrod',
-  appName:'sandbox',
-  authType:'CLIENT_ID',
-  clientId:'b3U6y6hRJufDEeGW9hIxOwbREg',
-  clientSecret:'b3U6X__fN2l9vd1HVi1kM9nJvgc-h5k'
-});
-
-describe('Entity methods', function(){
-  var dog = new usergrid.entity({
-    client:client,
-    data:{type:"dogs"}
-  });
-  describe('save method', function(){
-    it('should save without error', function(done){
-      dog.set('name','dougy');
-      dog.save(done);
-    });
-  });
-  describe('fetch method', function(){
-    it('should fetch without error', function(done){
-      dog.fetch(done);
-    });
-  });
-  describe('destroy method', function(){
-    it('should destroy without error', function(done){
-      dog.destroy(done);
-    });
-  });
-});
\ No newline at end of file
diff --git a/tests/config.test.json b/tests/config.test.json
new file mode 100644
index 0000000..654298e
--- /dev/null
+++ b/tests/config.test.json
@@ -0,0 +1,28 @@
+{
+    "1.0": {
+        "orgId": "rwalsh",
+        "appId": "nodejs",
+        "baseUrl": "https://api.usergrid.com",
+        "clientId": "YXA68wzo4KbAEea4p6tiytxmag",
+        "clientSecret": "YXA671McJDKY_C3oU1HpdbJBqGMf_Y0",
+        "test": {
+            "collection": "nodejs",
+            "email": "authtest@test.com",
+            "password": "P@ssw0rd",
+            "username": "authtest"
+        }
+    },
+    "2.1": {
+        "appId": "sdksandbox",
+        "baseUrl": "https://api-connectors-prod.apigee.net/appservices",
+        "clientId": "YXA6WMhAuFJTEeWoggrRE9kXrQ",
+        "clientSecret": "YXA6zZbat7PKgOlN73rpByc36LWaUhw",
+        "orgId": "api-connectors",
+        "test": {
+            "collection": "nodejs",
+            "email": "authtest@test.com",
+            "password": "P@ssw0rd",
+            "username": "authtest"
+        }
+    }
+}
\ No newline at end of file
diff --git a/tests/lib/asset.test.js b/tests/lib/asset.test.js
new file mode 100644
index 0000000..389a616
--- /dev/null
+++ b/tests/lib/asset.test.js
@@ -0,0 +1,118 @@
+'use strict'
+
+var config = require('../../helpers').config,
+    UsergridEntity = require('../../lib/entity'),
+    UsergridAsset = require('../../lib/asset'),
+    UsergridClient = require('../../lib/client'),
+    util = require('util'),
+    fs = require('fs')
+
+var _slow = 6000,
+    _timeout = 12000,
+    filename = 'old_man',
+    file = __dirname + '/image.jpg',
+    testFile = __dirname + '/image_test.jpg',
+    expectedContentLength = 109055
+
+describe('init from fs.readFile()', function() {
+    var asset = new UsergridAsset(filename, file)
+
+    before(function(done) {
+        fs.readFile(file, function(err, data) {
+            asset.data = data
+            done()
+        })
+    })
+
+    it('asset.data should be a binary Buffer', function() {
+        asset.data.should.be.a.buffer()
+    })
+
+    it('asset.contentType should be inferred from Buffer', function() {
+        asset.contentType.should.equal('image/jpeg')
+    })
+
+    it(util.format('asset.contentLength should be %s bytes', expectedContentLength), function() {
+        asset.contentLength.should.equal(expectedContentLength)
+    })
+})
+
+describe('init from piped writable stream', function() {
+    var asset = new UsergridAsset(filename, file)
+    var writeTestAsset = new UsergridAsset('image_test', testFile)
+    before(function(done) {
+        var stream = fs.createReadStream(file).pipe(asset),
+            writeTest
+        stream.on('finish', function() {
+            fs.writeFile(testFile, asset.data)
+            writeTest = fs.createReadStream(file).pipe(writeTestAsset)
+            writeTest.on('finish', function() {
+                done()
+            })
+        })
+    })
+
+    it('asset.data should be a binary Buffer', function() {
+        asset.data.should.be.a.buffer()
+    })
+
+    it('asset.contentType should be inferred from Buffer', function() {
+        asset.contentType.should.equal('image/jpeg')
+    })
+
+    it(util.format('asset.contentLength should be %s bytes', expectedContentLength), function() {
+        asset.contentLength.should.equal(expectedContentLength)
+    })
+
+    it('should write an identical asset to the filesystem', function() {
+        writeTestAsset.contentType.should.equal('image/jpeg')
+        writeTestAsset.contentLength.should.equal(expectedContentLength)
+    })
+})
+
+describe('upload via client.POST to a specific entity', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var client = new UsergridClient()
+    it('should upload a binary asset and create a new entity', function(done) {
+        var asset = new UsergridAsset(filename, file)
+        fs.createReadStream(file).pipe(asset).on('finish', function() {
+            client.POST(config.test.collection, asset, function(err, assetResponse, entityWithAsset) {
+                assetResponse.statusCode.should.equal(200)
+                entityWithAsset.should.have.property('file-metadata')
+                entityWithAsset['file-metadata'].should.have.property('content-type').equal('image/jpeg')
+                entityWithAsset['file-metadata'].should.have.property('content-length').equal(expectedContentLength)
+                entityWithAsset.remove(client)
+                done()
+            })
+        })
+    })
+})
+
+describe('upload via client.PUT to a specific entity', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var client = new UsergridClient()
+    it('should upload a binary asset to an existing entity', function(done) {
+        var entity = new UsergridEntity({
+            type: config.test.collection,
+            name: "AssetTestPUT"
+        })
+        var asset = new UsergridAsset(filename, file)
+        client.PUT(entity, function(err, entityResponse, createdEntity) {
+            fs.createReadStream(file).pipe(asset).on('finish', function() {
+                client.PUT(createdEntity, asset, function(err, assetResponse, entityWithAsset) {
+                    assetResponse.statusCode.should.equal(200)
+                    entityWithAsset.should.have.property('file-metadata')
+                    entityWithAsset['file-metadata'].should.have.property('content-type').equal('image/jpeg')
+                    entityWithAsset['file-metadata'].should.have.property('content-length').equal(expectedContentLength)
+                    done()
+                })
+            })
+        })
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/client.auth.test.js b/tests/lib/client.auth.test.js
new file mode 100644
index 0000000..67567de
--- /dev/null
+++ b/tests/lib/client.auth.test.js
@@ -0,0 +1,350 @@
+'use strict'
+
+var should = require('should'),
+    chance = new require('chance').Chance(),
+    util = require('util'),
+    config = require('../../helpers').config,
+    UsergridClient = require('../../lib/client'),
+    UsergridAuth = require('../../lib/auth'),
+    UsergridAppAuth = require('../../lib/appAuth'),
+    UsergridUserAuth = require('../../lib/userAuth'),
+    UsergridUser = require('../../lib/user')
+
+var _slow = 500,
+    _timeout = 4000
+
+describe('authMode', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var token, client = new UsergridClient()
+    before(function(done) {
+        // authenticate app and remove sandbox permissions
+        client.setAppAuth(config.clientId, config.clientSecret)
+        client.authenticateApp(function(e, r, t) {
+            token = t
+            client.usingAuth(client.appAuth).DELETE('roles/guest/permissions', {
+                permission: "get,post,put,delete:/**"
+            }, function() {
+                done()
+            })
+        })
+    })
+
+    it('should fall back to using no authentication when currentUser is not authenticated and authMode is set to NONE', function(done) {
+        client.authMode = UsergridAuth.AUTH_MODE_NONE
+        client.GET('users', function(error, usergridResponse) {
+            should(client.currentUser).be.undefined()
+            usergridResponse.request.headers.should.not.have.property('authorization')
+            error.name.should.equal('unauthorized')
+            usergridResponse.ok.should.be.false()
+            done()
+        })
+    })
+
+    it('should fall back to using the app token when currentUser is not authenticated and authMode is set to APP', function(done) {
+        client.authMode = UsergridAuth.AUTH_MODE_APP
+        client.GET('users', function(error, usergridResponse, user) {
+            should(client.currentUser).be.undefined()
+            usergridResponse.request.headers.should.have.property('authorization').equal(util.format('Bearer %s', token))
+            usergridResponse.ok.should.be.true()
+            user.should.be.an.instanceof(UsergridUser)
+            done()
+        })
+    })
+
+    after(function(done) {
+        // re-add sandbox permissions
+        client.authMode = UsergridAuth.AUTH_MODE_NONE
+        client.usingAuth(client.appAuth).POST('roles/guest/permissions', {
+            permission: "get,post,put,delete:/**"
+        }, function() {
+            done()
+        })
+    })
+})
+
+describe('authenticateApp()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var response, token, client = new UsergridClient()
+    before(function(done) {
+        client.setAppAuth(config.clientId, config.clientSecret)
+        client.authenticateApp(function(err, r, t) {
+            response = r
+            token = t
+            done()
+        })
+    })
+
+    it('response.ok should be true', function() {
+        response.ok.should.be.true()
+    })
+
+    it('should have a valid token', function() {
+        token.should.be.a.String()
+        token.length.should.be.greaterThan(10)
+    })
+
+    it('client.appAuth.token should be set to the token returned from Usergrid', function() {
+        client.appAuth.should.have.property('token').equal(token)
+    })
+
+    it('client.appAuth.isValid should be true', function() {
+        client.appAuth.should.have.property('isValid').which.is.true()
+    })
+
+    it('client.appAuth.expiry should be set to a future date', function() {
+        client.appAuth.should.have.property('expiry').greaterThan(Date.now())
+    })
+
+    it('should fail when called without a clientId and clientSecret', function() {
+        should(function() {
+            var client = new UsergridClient()
+            client.setAppAuth(undefined, undefined, 0)
+            client.authenticateApp()
+        }).throw()
+    })
+
+    it('should authenticate by passing clientId and clientSecret in an object', function(done) {
+        var isolatedClient = new UsergridClient()
+        isolatedClient.authenticateApp(config, function(err, reponse, token) {
+            isolatedClient.appAuth.should.have.property('token').equal(token)
+            done()
+        })
+    })
+
+    it('should authenticate by passing a UsergridAppAuth instance with a custom ttl', function(done) {
+        var isolatedClient = new UsergridClient()
+        var ttlInMilliseconds = 500000
+        var appAuth = new UsergridAppAuth(config.clientId, config.clientSecret, ttlInMilliseconds)
+        isolatedClient.authenticateApp(appAuth, function(err, response, token) {
+            isolatedClient.appAuth.should.have.property('token').equal(token)
+            response.body.expires_in.should.equal(ttlInMilliseconds / 1000)
+            done()
+        })
+    })
+
+    it('should not set client.appAuth when authenticating with a bad clientId and clientSecret in an object', function(done) {
+        var failClient = new UsergridClient()
+        failClient.appAuth = undefined
+        failClient.authenticateApp(new UsergridAppAuth('BADCLIENTID', 'BADCLIENTSECRET'), function(e, r, token) {
+            e.should.containDeep({
+                name: 'invalid_grant',
+                description: 'invalid username or password'
+            })
+            should(token).be.undefined()
+            should(failClient.appAuth).be.undefined()
+            done()
+        })
+    })
+
+    it('should not set client.appAuth when authenticating with a bad UsergridAppAuth instance (using an object)', function(done) {
+        var failClient = new UsergridClient()
+        failClient.appAuth = undefined
+        failClient.authenticateApp(new UsergridAppAuth('BADCLIENTID', 'BADCLIENTSECRET'), function(e, r, token) {
+            e.should.containDeep({
+                name: 'invalid_grant',
+                description: 'invalid username or password'
+            })
+            should(token).be.undefined()
+            should(failClient.appAuth).be.undefined()
+            done()
+        })
+    })
+
+
+    it('should not set client.appAuth when authenticating with a bad UsergridAppAuth instance (using arguments)', function(done) {
+        var failClient = new UsergridClient()
+        failClient.appAuth = undefined
+        failClient.authenticateApp(new UsergridAppAuth('BADCLIENTID', 'BADCLIENTSECRET'), function(e, r, token) {
+            e.should.containDeep({
+                name: 'invalid_grant',
+                description: 'invalid username or password'
+            })
+            should(token).be.undefined()
+            should(failClient.appAuth).be.undefined()
+            done()
+        })
+    })
+})
+
+describe('authenticateUser()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var response, token, email = util.format("%s@%s.com", chance.word(), chance.word()),
+        client = new UsergridClient()
+    before(function(done) {
+        client.authenticateUser({
+            username: config.test.username,
+            password: config.test.password,
+            email: email
+        }, function(err, r, t) {
+            response = r
+            token = t
+            done()
+        })
+    })
+
+    it('should fail when called without a email (or username) and password', function() {
+        should(function() {
+            var badClient = new UsergridClient()
+            badClient.authenticateUser({})
+        }).throw()
+    })
+
+    it('response.ok should be true', function() {
+        response.ok.should.be.true()
+    })
+
+    it('should have a valid token', function() {
+        token.should.be.a.String()
+        token.length.should.be.greaterThan(10)
+    })
+
+    it('client.currentUser.auth.token should be set to the token returned from Usergrid', function() {
+        client.currentUser.auth.should.have.property('token').equal(token)
+    })
+
+    it('client.currentUser.auth.isValid should be true', function() {
+        client.currentUser.auth.should.have.property('isValid').which.is.true()
+    })
+
+    it('client.currentUser.auth.expiry should be set to a future date', function() {
+        client.currentUser.auth.should.have.property('expiry').greaterThan(Date.now())
+    })
+
+    it('client.currentUser should have a username and email', function() {
+        client.currentUser.should.have.property('username')
+        client.currentUser.should.have.property('email').equal(email)
+    })
+
+    it('client.currentUser and client.currentUser.auth should not store password', function() {
+        client.currentUser.should.not.have.property('password')
+        client.currentUser.auth.should.not.have.property('password')
+    })
+
+    it('should support an optional bool to not set as current user', function(done) {
+        var noCurrentUserClient = new UsergridClient()
+        noCurrentUserClient.authenticateUser({
+            username: config.test.username,
+            password: config.test.password,
+            email: email
+        }, false, function() {
+            should(noCurrentUserClient.currentUser).be.undefined()
+            done()
+        })
+    })
+
+    it('should support passing a UsergridUserAuth instance with a custom ttl', function(done) {
+        var newClient = new UsergridClient()
+        var ttlInMilliseconds = 500000
+        var userAuth = new UsergridUserAuth(config.test.username, config.test.password, ttlInMilliseconds)
+        newClient.authenticateUser(userAuth, function(err, usergridResponse, token) {
+            usergridResponse.ok.should.be.true()
+            newClient.currentUser.auth.token.should.equal(token)
+            usergridResponse.body.expires_in.should.equal(ttlInMilliseconds / 1000)
+            done()
+        })
+    })
+})
+
+describe('appAuth, setAppAuth()', function() {
+    it('should initialize by passing a list of arguments', function() {
+        var client = new UsergridClient()
+        client.setAppAuth(config.clientId, config.clientSecret, config.tokenTtl)
+        client.appAuth.should.be.instanceof(UsergridAppAuth)
+    })
+
+    it('should be a subclass of UsergridAuth', function() {
+        var client = new UsergridClient()
+        client.setAppAuth(config.clientId, config.clientSecret, config.tokenTtl)
+        client.appAuth.should.be.instanceof(UsergridAuth)
+    })
+
+    it('should initialize by passing an object', function() {
+        var client = new UsergridClient()
+        client.setAppAuth({
+            clientId: config.clientId,
+            clientSecret: config.clientSecret,
+            tokenTtl: config.tokenTtl
+        })
+        client.appAuth.should.be.instanceof(UsergridAppAuth)
+    })
+
+    it('should initialize by passing an instance of UsergridAppAuth', function() {
+        var client = new UsergridClient()
+        client.setAppAuth(new UsergridAppAuth(config.clientId, config.clientSecret, config.tokenTtl))
+        client.appAuth.should.be.instanceof(UsergridAppAuth)
+    })
+
+    it('should initialize by setting to an instance of UsergridAppAuth', function() {
+        var client = new UsergridClient()
+        client.appAuth = new UsergridAppAuth(config.clientId, config.clientSecret, config.tokenTtl)
+        client.appAuth.should.be.instanceof(UsergridAppAuth)
+    })
+})
+
+describe('usingAuth()', function() {
+
+    this.slow(_slow + 500)
+    this.timeout(_timeout)
+
+    var client = new UsergridClient(),
+        authFromToken
+
+    before(function(done) {
+        client.authenticateUser({
+            username: config.test.username,
+            password: config.test.password
+        }, function(error, response, token) {
+            authFromToken = new UsergridAuth(token)
+            done()
+        })
+    })
+
+    it('should authenticate using an ad-hoc token', function(done) {
+        authFromToken.isValid.should.be.true()
+        authFromToken.should.have.property('token')
+        client.usingAuth(authFromToken).GET({
+            path: '/users/me'
+        }, function(error, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            usergridResponse.should.have.property('user').which.is.an.instanceof(UsergridUser)
+            usergridResponse.user.should.have.property('uuid').which.is.a.uuid()
+            done()
+        })
+    })
+
+    it('client.tempAuth should be destroyed after making a request with ad-hoc authentication', function(done) {
+        should(client.tempAuth).be.undefined()
+        done()
+    })
+
+    it('should send an unauthenticated request when UsergridAuth.NO_AUTH is passed to .usingAuth()', function(done) {
+        client.usingAuth(UsergridAuth.NO_AUTH).GET({
+            path: '/users/me'
+        }, function(error, usergridResponse) {
+            usergridResponse.ok.should.be.false()
+            usergridResponse.request.headers.should.not.have.property('authentication')
+            usergridResponse.should.not.have.property('user')
+            done()
+        })
+    })
+
+    it('should send an unauthenticated request when no arguments are passed to .usingAuth()', function(done) {
+        client.usingAuth().GET({
+            path: '/users/me'
+        }, function(error, usergridResponse) {
+            usergridResponse.ok.should.be.false()
+            usergridResponse.request.headers.should.not.have.property('authentication')
+            usergridResponse.should.not.have.property('user')
+            done()
+        })
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/client.connections.test.js b/tests/lib/client.connections.test.js
new file mode 100644
index 0000000..22ed45f
--- /dev/null
+++ b/tests/lib/client.connections.test.js
@@ -0,0 +1,294 @@
+'use strict'
+
+var should = require('should'),
+    urljoin = require('url-join'),
+    config = require('../../helpers').config,
+    UsergridClient = require('../../lib/client'),
+    UsergridQuery = require('../../lib/query')
+
+var _slow = 500,
+    _timeout = 4000
+
+describe('connect()', function() {
+
+    this.slow(_slow + 1000)
+    this.timeout(_timeout + 4000)
+
+    var response,
+        entity1,
+        entity2,
+        client = new UsergridClient(),
+        query = new UsergridQuery(config.test.collection).eq('name', 'testClientConnectOne').or.eq('name', 'testClientConnectTwo').asc('name')
+
+    before(function(done) {
+        // Create the entities we're going to use for connections
+        client.POST(config.test.collection, [{
+            "name": "testClientConnectOne"
+        }, {
+            "name": "testClientConnectTwo"
+        }], function() {
+            client.GET(query, function(err, usergridResponse) {
+                response = usergridResponse
+                entity1 = response.first
+                entity2 = response.last
+                done()
+            })
+        })
+    })
+
+    it('should connect entities by passing UsergridEntity objects as parameters', function(done) {
+        var relationship = "foos"
+
+        client.connect(entity1, relationship, entity2, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                    "",
+                    config.test.collection,
+                    entity1.uuid,
+                    relationship,
+                    entity2.uuid,
+                    "connecting",
+                    relationship
+                ))
+                done()
+            })
+        })
+    })
+
+    it('should connect entities by passing a source UsergridEntity object and a target uuid', function(done) {
+        var relationship = "bars"
+
+        client.connect(entity1, relationship, entity2.uuid, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                    "",
+                    config.test.collection,
+                    entity1.uuid,
+                    relationship,
+                    entity2.uuid,
+                    "connecting",
+                    relationship
+                ))
+                done()
+            })
+        })
+    })
+
+    it('should connect entities by passing source type, source uuid, and target uuid as parameters', function(done) {
+        var relationship = "bazzes"
+
+        client.connect(entity1.type, entity1.uuid, relationship, entity2.uuid, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                    "",
+                    config.test.collection,
+                    entity1.uuid,
+                    relationship,
+                    entity2.uuid,
+                    "connecting",
+                    relationship
+                ))
+                done()
+            })
+        })
+    })
+
+    it('should connect entities by passing source type, source name, target type, and target name as parameters', function(done) {
+        var relationship = "quxes"
+
+        client.connect(entity1.type, entity1.name, relationship, entity2.type, entity2.name, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                    "",
+                    config.test.collection,
+                    entity1.uuid,
+                    relationship,
+                    entity2.uuid,
+                    "connecting",
+                    relationship
+                ))
+                done()
+            })
+        })
+    })
+
+    it('should connect entities by passing a preconfigured options object', function(done) {
+        var options = {
+            entity: entity1,
+            relationship: "quuxes",
+            to: entity2
+        }
+
+        client.connect(options, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, options.relationship, function(err, usergridResponse) {
+                usergridResponse.first.metadata.connecting[options.relationship].should.equal(urljoin(
+                    "",
+                    config.test.collection,
+                    entity1.uuid,
+                    options.relationship,
+                    entity2.uuid,
+                    "connecting",
+                    options.relationship
+                ))
+                done()
+            })
+        })
+    })
+
+    it('should fail to connect entities when specifying target name without type', function() {
+        should(function() {
+            client.connect(entity1.type, entity1.name, "fails", 'badName', function() {})
+        }).throw()
+    })
+})
+
+describe('getConnections()', function() {
+
+    this.slow(_slow + 1000)
+    this.timeout(_timeout + 4000)
+
+    var response,
+        client = new UsergridClient(),
+        query = new UsergridQuery(config.test.collection).eq('name', 'testClientConnectOne').or.eq('name', 'testClientConnectTwo').asc('name')
+
+    before(function(done) {
+        client.GET(query, function(err, usergridResponse) {
+            response = usergridResponse
+            done()
+        })
+    })
+
+    it('should get an entity\'s outbound connections', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "foos"
+
+        client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+            usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                "",
+                config.test.collection,
+                entity1.uuid,
+                relationship,
+                entity2.uuid,
+                "connecting",
+                relationship
+            ))
+            done()
+        })
+    })
+
+    it('should get an entity\'s inbound connections', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "foos"
+
+        client.getConnections(UsergridClient.Connections.DIRECTION_IN, entity2, relationship, function(err, usergridResponse) {
+            usergridResponse.first.metadata.connections[relationship].should.equal(urljoin(
+                "",
+                config.test.collection,
+                entity2.uuid,
+                "connecting",
+                entity1.uuid,
+                relationship
+            ))
+            done()
+        })
+    })
+})
+
+describe('disconnect()', function() {
+
+    this.slow(_slow + 1000)
+    this.timeout(_timeout + 4000)
+
+    var response,
+        client = new UsergridClient(),
+        query = new UsergridQuery(config.test.collection).eq('name', 'testClientConnectOne').or.eq('name', 'testClientConnectTwo').asc('name')
+
+    before(function(done) {
+        client.GET(query, function(err, usergridResponse) {
+            response = usergridResponse
+            done()
+        })
+    })
+
+    it('should disconnect entities by passing UsergridEntity objects as parameters', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "foos"
+
+        client.disconnect(entity1, relationship, entity2, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.entities.should.be.an.Array().with.lengthOf(0)
+                done()
+            })
+        })
+    })
+
+    it('should disconnect entities by passing source type, source uuid, and target uuid as parameters', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "bars"
+
+        client.disconnect(entity1.type, entity1.uuid, relationship, entity2.uuid, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.entities.should.be.an.Array().with.lengthOf(0)
+                done()
+            })
+        })
+    })
+
+    it('should disconnect entities by passing source type, source name, target type, and target name as parameters', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "bazzes"
+
+        client.disconnect(entity1.type, entity1.name, relationship, entity2.type, entity2.name, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.entities.should.be.an.Array().with.lengthOf(0)
+                done()
+            })
+        })
+    })
+
+    it('should disconnect entities by passing a preconfigured options object', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var options = {
+            entity: entity1,
+            relationship: "quxes",
+            to: entity2
+        }
+
+        client.disconnect(options, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, options.relationship, function(err, usergridResponse) {
+                usergridResponse.entities.should.be.an.Array().with.lengthOf(0)
+                done()
+            })
+        })
+    })
+
+    it('should fail to disconnect entities when specifying target name without type', function() {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        should(function() {
+            client.disconnect(entity1.type, entity1.name, "fails", entity2.name, function() {})
+        }).throw()
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/client.init.test.js b/tests/lib/client.init.test.js
new file mode 100644
index 0000000..01702bd
--- /dev/null
+++ b/tests/lib/client.init.test.js
@@ -0,0 +1,37 @@
+'use strict'
+
+var should = require('should'),
+    config = require('../../helpers').config,
+    UsergridClient = require('../../lib/client')
+
+describe('initialization', function() {
+    it('should fail to initialize without an orgId and appId', function() {
+        should(function() {
+            var client = new UsergridClient(null, null)
+            client.GET()
+        }).throw()
+    })
+
+    it('should initialize using properties defined in config.json', function() {
+        var client = new UsergridClient()
+        client.should.be.an.instanceof(UsergridClient).with.property('orgId').equal(config.orgId)
+        client.should.have.property('appId').equal(config.appId)
+    })
+
+    it('should initialize when passing orgId and appId as arguments, taking precedence over config', function() {
+        var client = new UsergridClient('foo', 'bar')
+        client.should.be.an.instanceof(UsergridClient).with.property('orgId').equal('foo')
+        client.should.have.property('appId').equal('bar')
+    })
+
+    it('should initialize when passing an object containing orgId and appId, taking precedence over config', function() {
+        var client = new UsergridClient({
+            orgId: 'foo',
+            appId: 'bar',
+            baseUrl: 'https://sdk-example-test.apigee.net/appservices'
+        })
+        client.should.be.an.instanceof(UsergridClient).with.property('orgId').equal('foo')
+        client.should.have.property('appId').equal('bar')
+        client.should.have.property('baseUrl').equal('https://sdk-example-test.apigee.net/appservices')
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/client.rest.test.js b/tests/lib/client.rest.test.js
new file mode 100644
index 0000000..017073e
--- /dev/null
+++ b/tests/lib/client.rest.test.js
@@ -0,0 +1,481 @@
+'use strict'
+
+var config = require('../../helpers').config,
+    chance = new require('chance').Chance(),
+    UsergridClient = require('../../lib/client'),
+    UsergridEntity = require('../../lib/entity'),
+    UsergridQuery = require('../../lib/query'),
+    _ = require('lodash')
+
+var _uuid,
+    _slow = 500,
+    _timeout = 4000
+
+describe('GET()', function() {
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var response, client
+    before(function(done) {
+        client = new UsergridClient(config)
+        client.GET(config.test.collection, function(err, usergridResponse) {
+            response = usergridResponse
+            done()
+        })
+    })
+
+    it('should not fail when a callback function is not passed', function() {
+        // note: this test will NOT fail gracefully inside the Mocha event chain
+        client.GET(config.test.collection)
+    })
+
+    it('response.ok should be true', function() {
+        response.ok.should.be.true()
+    })
+
+    it('response.entities should be an array', function() {
+        response.entities.should.be.an.Array()
+    })
+
+    it('response.first should exist and have a valid uuid', function() {
+        response.first.should.be.an.instanceof(UsergridEntity).with.property('uuid').which.is.a.uuid()
+    })
+
+    it('response.entity should exist and have a valid uuid', function() {
+        response.entity.should.be.an.instanceof(UsergridEntity).with.property('uuid').which.is.a.uuid()
+    })
+
+    it('response.last should exist and have a valid uuid', function() {
+        response.last.should.be.an.instanceof(UsergridEntity).with.property('uuid').which.is.a.uuid()
+    })
+
+    it('each entity should match the search criteria when passing a UsergridQuery object', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var query = new UsergridQuery(config.test.collection).eq('color', 'black')
+
+        client.GET(query, function(err, usergridResponse) {
+            usergridResponse.entities.forEach(function(entity) {
+                entity.should.be.an.Object().with.property('color').equal('black')
+            })
+            done()
+        })
+    })
+
+    it('a single entity should be retrieved when specifying a uuid', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        client.GET(config.test.collection, response.entity.uuid, function(err, usergridResponse) {
+            usergridResponse.should.have.property('entity').which.is.an.instanceof(UsergridEntity)
+            usergridResponse.body.entities.should.be.an.Array().with.a.lengthOf(1)
+            done()
+        })
+    })
+})
+
+describe('POST()', function() {
+
+    this.slow(_slow)
+    this.timeout(3000)
+
+    var response, client
+    before(function(done) {
+        client = new UsergridClient()
+        client.POST(config.test.collection, {
+            author: 'Sir Arthur Conan Doyle'
+        }, function(err, usergridResponse) {
+            response = usergridResponse
+            _uuid = usergridResponse.entity.uuid
+            done()
+        })
+    })
+
+    it('should not fail when a callback function is not passed', function() {
+        // note: this test will NOT fail gracefully inside the Mocha event chain
+        client.POST(config.test.collection, {})
+    })
+
+    it('response.ok should be true', function() {
+        response.ok.should.be.true()
+    })
+
+    it('response.entities should be an array', function() {
+        response.entities.should.be.an.Array().with.a.lengthOf(1)
+    })
+
+    it('response.entity should exist and have a valid uuid', function() {
+        response.entity.should.be.an.instanceof(UsergridEntity).with.property('uuid').which.is.a.uuid()
+    })
+
+    it('response.entity.author should equal "Sir Arthur Conan Doyle"', function() {
+        response.entity.should.have.property('author').equal('Sir Arthur Conan Doyle')
+    })
+
+    it('should support creating an entity by passing a UsergridEntity object', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var entity = new UsergridEntity({
+            type: config.test.collection,
+            restaurant: "Dino's Deep Dish",
+            cuisine: "pizza"
+        })
+
+        client.POST(entity, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('restaurant').equal(entity.restaurant)
+            done()
+        })
+    })
+
+    it('should support creating an entity by passing a UsergridEntity object with a unique name', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var entity = new UsergridEntity({
+            type: config.test.collection,
+            name: chance.word()
+        })
+        client.POST(entity, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('name').equal(entity.name)
+            usergridResponse.entity.remove(client)
+            done()
+        })
+    })
+
+    it('should support creating an entity by passing type and a body object', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        client.POST(config.test.collection, {
+            restaurant: "Dino's Deep Dish",
+            cuisine: "pizza"
+        }, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('restaurant').equal("Dino's Deep Dish")
+            done()
+        })
+    })
+
+    it('should support creating an entity by passing a body object that includes type', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        client.POST({
+            type: config.test.collection,
+            restaurant: "Dino's Deep Dish",
+            cuisine: "pizza"
+        }, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('restaurant').equal("Dino's Deep Dish")
+            done()
+        })
+    })
+
+    it('should support creating an entity by passing an array of UsergridEntity objects', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var entities = [
+            new UsergridEntity({
+                type: config.test.collection,
+                restaurant: "Dino's Deep Dish",
+                cuisine: "pizza"
+            }), new UsergridEntity({
+                type: config.test.collection,
+                restaurant: "Chipotle",
+                cuisine: "mexican"
+            })
+        ]
+
+        client.POST(entities, function(err, usergridResponse) {
+            usergridResponse.entities.forEach(function(entity) {
+                entity.should.be.an.Object().with.property('restaurant').equal(entity.restaurant)
+            })
+            done()
+        })
+    })
+
+    it('should support creating an entity by passing a preformatted POST builder object', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var options = {
+            type: config.test.collection,
+            body: {
+                restaurant: "Chipotle",
+                cuisine: "mexican"
+            }
+        }
+
+        client.POST(options, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('restaurant').equal(usergridResponse.entity.restaurant)
+            done()
+        })
+    })
+})
+
+describe('PUT()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var response, client
+    before(function(done) {
+        client = new UsergridClient()
+        client.PUT(config.test.collection, _uuid, {
+            narrator: 'Peter Doyle'
+        }, function(err, usergridResponse) {
+            response = usergridResponse
+            done()
+        })
+    })
+
+    it('should not fail when a callback function is not passed', function() {
+        // note: this test will NOT fail gracefully inside the Mocha event chain
+        client.PUT(config.test.collection, _uuid, {})
+    })
+
+    it('response.ok should be true', function() {
+        response.ok.should.be.true()
+    })
+
+    it('response.entities should be an array with a single entity', function() {
+        response.entities.should.be.an.Array().with.a.lengthOf(1)
+    })
+
+    it('response.entity should exist and its uuid should the uuid from the previous POST request', function() {
+        response.entity.should.be.an.Object().with.property('uuid').equal(_uuid)
+    })
+
+    it('response.entity.narrator should be updated to "Peter Doyle"', function() {
+        response.entity.should.have.property('narrator').equal('Peter Doyle')
+    })
+
+    it('should create a new entity when no uuid or name is passed', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var newEntity = new UsergridEntity({
+            type: config.test.collection,
+            author: 'Frank Mills'
+        })
+
+        client.PUT(newEntity, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object()
+            usergridResponse.entity.should.be.an.instanceof(UsergridEntity).with.property('uuid').which.is.a.uuid()
+            usergridResponse.entity.should.have.property('author').equal('Frank Mills')
+            usergridResponse.entity.created.should.equal(usergridResponse.entity.modified)
+            done()
+        })
+    })
+
+    it('should support updating the entity by passing a UsergridEntity object', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var updateEntity = _.assign(response.entity, {
+            publisher: {
+                name: "George Newns",
+                date: "14 October 1892",
+                country: "United Kingdom"
+            }
+        })
+
+        client.PUT(updateEntity, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('publisher').deepEqual(updateEntity.publisher)
+            done()
+        })
+    })
+
+    it('should support updating an entity by passing type and a body object', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+        client.PUT(config.test.collection, {
+            uuid: response.entity.uuid,
+            updateByPassingTypeAndBody: true
+        }, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('updateByPassingTypeAndBody').equal(true)
+            done()
+        })
+    })
+
+    it('should support updating an entity by passing a body object that includes type', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        client.PUT(config.test.collection, {
+            type: config.test.collection,
+            uuid: response.entity.uuid,
+            updateByPassingBodyIncludingType: true
+        }, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('updateByPassingBodyIncludingType').equal(true)
+            done()
+        })
+    })
+
+    it('should support updating a set of entities by passing an UsergridQuery object', function(done) {
+
+        this.slow(_slow + 1000)
+        this.timeout(_timeout + 10000)
+
+        var query = new UsergridQuery(config.test.collection).eq('cuisine', 'pizza').limit(2)
+        var body = {
+            testUuid: _.uuid()
+        }
+
+        client.PUT(query, body, function(err, usergridResponse) {
+            usergridResponse.entities.forEach(function(entity) {
+                entity.should.be.an.Object().with.property('testUuid').equal(body.testUuid)
+            })
+            done()
+        })
+    })
+
+    it('should support updating an entity by passing a preformatted PUT builder object', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var options = {
+            uuidOrName: response.entity.uuid,
+            type: config.test.collection,
+            body: {
+                relatedUuid: _.uuid()
+            }
+        }
+
+        client.PUT(options, function(err, usergridResponse) {
+            usergridResponse.entity.should.be.an.Object().with.property('relatedUuid').equal(options.body.relatedUuid)
+            done()
+        })
+    })
+})
+
+describe('DELETE()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var response, client
+    before(function(done) {
+        client = new UsergridClient()
+        client.DELETE(config.test.collection, _uuid, function() {
+            client.GET(config.test.collection, _uuid, function(err, usergridResponse) {
+                response = usergridResponse
+                done()
+            })
+        })
+    })
+
+    it('should not fail when a callback function is not passed', function() {
+        // note: this test will NOT fail gracefully inside the Mocha event chain
+        client.DELETE(config.test.collection, _uuid)
+    })
+
+    it('should return a 404 not found', function() {
+        response.statusCode.should.equal(404)
+    })
+
+    it('response.error.name should equal "entity_not_found"', function() {
+        response.error.name.should.equal((config.target === '1.0') ? 'service_resource_not_found' : 'entity_not_found')
+    })
+
+    it('should support deleting an entity by passing a UsergridEntity object', function(done) {
+
+        this.slow(_slow + 1000)
+        this.timeout(_timeout + 1000)
+
+        var entity = new UsergridEntity({
+            type: config.test.collection,
+            command: "CTRL+ALT+DEL"
+        })
+
+        client.POST(entity, function(err, usergridResponse) {
+            client.DELETE(usergridResponse.entity, function() {
+                client.GET(config.test.collection, usergridResponse.entity.uuid, function(err, delResponse) {
+                    delResponse.ok.should.be.false()
+                    delResponse.error.name.should.equal((config.target === '1.0') ? 'service_resource_not_found' : 'entity_not_found')
+                    done()
+                })
+            })
+        })
+    })
+
+    it('should support deleting an entity by passing type and uuid', function(done) {
+
+        this.slow(_slow + 1000)
+        this.timeout(_timeout + 1000)
+
+        var body = {
+            command: "CTRL+ALT+DEL"
+        }
+
+        client.POST(config.test.collection, body, function(err, usergridResponse) {
+            client.DELETE(config.test.collection, usergridResponse.entity.uuid, function() {
+                client.GET(config.test.collection, usergridResponse.entity.uuid, function(err, delResponse) {
+                    delResponse.error.name.should.equal((config.target === '1.0') ? 'service_resource_not_found' : 'entity_not_found')
+                    done()
+                })
+            })
+        })
+    })
+
+    it('should support deleting multiple entities by passing a UsergridQuery object', function(done) {
+
+        this.slow(_slow + 1000)
+        this.timeout(_timeout + 6000)
+
+        var entity = new UsergridEntity({
+            type: config.test.collection,
+            command: "CMD+TAB"
+        })
+
+        var query = new UsergridQuery(config.test.collection).eq('command', 'CMD+TAB')
+
+        client.POST([entity, entity, entity, entity], function() {
+            client.DELETE(query, function() {
+                client.GET(query, function(err, usergridResponse) {
+                    usergridResponse.entities.should.be.an.Array().with.lengthOf(0)
+                    done()
+                })
+            })
+        })
+    })
+
+    it('should support deleting an entity by passing a preformatted DELETE builder object', function(done) {
+
+        this.slow(_slow + 1000)
+        this.timeout(_timeout + 1000)
+
+        var options = {
+            type: config.test.collection,
+            body: {
+                restaurant: "IHOP",
+                cuisine: "breakfast"
+            }
+        }
+
+        client.POST(options, function(err, usergridResponse) {
+            client.DELETE(_.assign(options, {
+                uuid: usergridResponse.entity.uuid
+            }), function() {
+                client.GET(config.test.collection, usergridResponse.entity.uuid, function(err, delResponse) {
+                    delResponse.error.name.should.equal((config.target === '1.0') ? 'service_resource_not_found' : 'entity_not_found')
+                    done()
+                })
+            })
+        })
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/entity.test.js b/tests/lib/entity.test.js
new file mode 100644
index 0000000..8152f23
--- /dev/null
+++ b/tests/lib/entity.test.js
@@ -0,0 +1,696 @@
+'use strict'
+
+var should = require('should'),
+    urljoin = require('url-join'),
+    config = require('../../helpers').config,
+    UsergridClient = require('../../lib/client'),
+    UsergridEntity = require('../../lib/entity'),
+    UsergridQuery = require('../../lib/query'),
+    UsergridAuth = require('../../lib/auth'),
+    UsergridAsset = require('../../lib/asset'),
+    fs = require('fs')
+
+var _slow = 1500,
+    _timeout = 4000,
+    filename = 'old_man',
+    file = __dirname + '/image.jpg',
+    expectedContentLength = 109055,
+    assetEntity = new UsergridEntity({
+        type: config.test.collection,
+        info: "assetTestEntity"
+    })
+
+describe('putProperty()', function() {
+    it('should set the value for a given key if the key does not exist', function() {
+        var entity = new UsergridEntity('cat', 'Cosmo')
+        entity.putProperty('foo', ['bar'])
+        entity.should.have.property('foo').deepEqual(['bar'])
+    })
+
+    it('should overwrite the value for a given key if the key exists', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'baz'
+        })
+        entity.putProperty('foo', 'bar')
+        entity.should.have.property('foo').deepEqual('bar')
+    })
+
+    it('should not be able to set the name key (name is immutable)', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'baz'
+        })
+        should(function() {
+            entity.putProperty('name', 'Bazinga')
+        }).throw()
+    })
+})
+
+describe('putProperties()', function() {
+    it('should set properties for a given object, overwriting properties that exist and creating those that don\'t', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'bar'
+        })
+        entity.putProperties({
+            foo: 'baz',
+            qux: 'quux',
+            barray: [1, 2, 3, 4]
+        })
+        entity.should.containEql({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'baz',
+            qux: 'quux',
+            barray: [1, 2, 3, 4]
+        })
+    })
+
+    it('should not be able to set properties for immutable keys', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'baz'
+        })
+        entity.putProperties({
+            name: 'Bazinga',
+            uuid: 'BadUuid',
+            bar: 'qux'
+        })
+        entity.should.containEql({
+            type: 'cat',
+            name: 'Cosmo',
+            bar: 'qux',
+            foo: 'baz'
+        })
+    })
+})
+
+describe('removeProperty()', function() {
+    it('should remove a given property if it exists', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'baz'
+        })
+        entity.removeProperty('foo')
+        entity.should.not.have.property('foo')
+    })
+
+    it('should fail gracefully when removing an undefined property', function() {
+        var entity = new UsergridEntity('cat', 'Cosmo')
+        entity.removeProperty('foo')
+        entity.should.not.have.property('foo')
+    })
+})
+
+describe('removeProperties()', function() {
+    it('should remove an array of properties for a given object, failing gracefully for undefined properties', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'bar',
+            baz: 'qux'
+        })
+        entity.removeProperties(['foo', 'baz'])
+        entity.should.containEql({
+            type: 'cat',
+            name: 'Cosmo'
+        })
+    })
+})
+
+describe('insert()', function() {
+    it('should insert a single value into an existing array at the specified index', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: [1, 2, 3, 5, 6]
+        })
+        entity.insert('foo', 4, 3)
+        entity.should.have.property('foo').deepEqual([1, 2, 3, 4, 5, 6])
+    })
+
+    it('should merge an array of values into an existing array at the specified index', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: [1, 2, 3, 7, 8]
+        })
+        entity.insert('foo', [4, 5, 6], 3)
+        entity.should.have.property('foo').deepEqual([1, 2, 3, 4, 5, 6, 7, 8])
+    })
+
+    it('should convert an existing value into an array when inserting a second value', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'bar'
+        })
+        entity.insert('foo', 'baz', 1)
+        entity.should.have.property('foo').deepEqual(['bar', 'baz'])
+    })
+
+    it('should create a new array when a property does not exist', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo'
+        })
+        entity.insert('foo', 'bar', 1000)
+        entity.should.have.property('foo').deepEqual(['bar'])
+    })
+
+    it('should gracefully handle indexes out of range', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: ['bar']
+        })
+        entity.insert('foo', 'baz', 1000)
+        entity.should.have.property('foo').deepEqual(['bar', 'baz'])
+        entity.insert('foo', 'qux', -1000)
+        entity.should.have.property('foo').deepEqual(['qux', 'bar', 'baz'])
+    })
+})
+
+describe('append()', function() {
+    it('should append a value to the end of an existing array', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: [1, 2, 3]
+        })
+        entity.append('foo', 4)
+        entity.should.have.property('foo').deepEqual([1, 2, 3, 4])
+    })
+
+    it('should create a new array if a property does not exist', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo'
+        })
+        entity.append('foo', 'bar')
+        entity.should.have.property('foo').deepEqual(['bar'])
+    })
+})
+
+describe('prepend()', function() {
+    it('should prepend a value to the beginning of an existing array', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: [1, 2, 3]
+        })
+        entity.prepend('foo', 0)
+        entity.should.have.property('foo').deepEqual([0, 1, 2, 3])
+    })
+
+    it('should create a new array if a property does not exist', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo'
+        })
+        entity.prepend('foo', 'bar')
+        entity.should.have.property('foo').deepEqual(['bar'])
+    })
+})
+
+describe('pop()', function() {
+    it('should remove the last value of an existing array', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: [1, 2, 3]
+        })
+        entity.pop('foo')
+        entity.should.have.property('foo').deepEqual([1, 2])
+    })
+
+    it('value should remain unchanged if it is not an array', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'bar'
+        })
+        entity.pop('foo')
+        entity.should.have.property('foo').deepEqual('bar')
+    })
+
+    it('should gracefully handle empty arrays', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: []
+        })
+        entity.pop('foo')
+        entity.should.have.property('foo').deepEqual([])
+    })
+})
+
+describe('shift()', function() {
+    it('should remove the first value of an existing array', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: [1, 2, 3]
+        })
+        entity.shift('foo')
+        entity.should.have.property('foo').deepEqual([2, 3])
+    })
+
+    it('value should remain unchanged if it is not an array', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: 'bar'
+        })
+        entity.shift('foo')
+        entity.should.have.property('foo').deepEqual('bar')
+    })
+
+    it('should gracefully handle empty arrays', function() {
+        var entity = new UsergridEntity({
+            type: 'cat',
+            name: 'Cosmo',
+            foo: []
+        })
+        entity.shift('foo')
+        entity.should.have.property('foo').deepEqual([])
+    })
+})
+
+describe('reload()', function() {
+
+    this.slow(_slow + 1000)
+    this.timeout(_timeout + 4000)
+
+    it('should refresh an entity with the latest server copy of itself', function(done) {
+        var client = new UsergridClient(config),
+            now = Date.now()
+        client.GET(config.test.collection, function(err, getResponse) {
+            var entity = new UsergridEntity(getResponse.first)
+            var modified = entity.modified
+            getResponse.first.putProperty('reloadTest', now)
+            client.PUT(getResponse.first, function() {
+                entity.reload(client, function() {
+                    client.isSharedInstance.should.be.false()
+                    entity.reloadTest.should.equal(now)
+                    entity.modified.should.not.equal(modified)
+                    done()
+                })
+            })
+        })
+    })
+})
+
+describe('save()', function() {
+
+    this.slow(_slow + 1000)
+    this.timeout(_timeout + 4000)
+
+    it('should save an updated entity to the server', function(done) {
+        var client = new UsergridClient(config),
+            now = Date.now()
+        client.GET(config.test.collection, function(err, getResponse) {
+            var entity = new UsergridEntity(getResponse.first)
+            entity.putProperty('saveTest', now)
+            entity.save(client, function() {
+                client.isSharedInstance.should.be.false()
+                entity.saveTest.should.equal(now)
+                done()
+            })
+        })
+    })
+})
+
+describe('remove()', function() {
+
+    this.slow(_slow + 1000)
+    this.timeout(_timeout + 4000)
+
+    it('should remove an entity from the server', function(done) {
+        var client = new UsergridClient(config)
+        client.POST(config.test.collection, {
+            removeTest: 'test'
+        }, function(err, postResponse) {
+            var entity = new UsergridEntity(postResponse.first)
+            entity.remove(client, function(err, deleteResponse) {
+                client.isSharedInstance.should.be.false()
+                deleteResponse.ok.should.be.true()
+                    // best practice is to desroy the 'entity' instance here, because it no longer exists on the server
+                entity = null
+                done()
+            })
+        })
+    })
+})
+
+describe('attachAsset()', function() {
+
+    var asset = new UsergridAsset(filename, file),
+        entity = new UsergridEntity({
+            type: config.test.collection,
+            info: "attachAssetTest"
+        })
+    before(function(done) {
+        fs.readFile(file, function(err, data) {
+            asset.data = data
+            done()
+        })
+    })
+
+    it('should attach a UsergridAsset to the entity', function(done) {
+        entity.attachAsset(asset)
+        entity.should.have.property('asset').equal(asset)
+        done()
+    })
+})
+
+describe('uploadAsset()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var asset = new UsergridAsset(filename, file)
+    before(function(done) {
+        fs.readFile(file, function(err, data) {
+            asset.data = data
+            done()
+        })
+    })
+
+    it('should upload an image asset to the remote entity', function(done) {
+        var client = new UsergridClient(config)
+        assetEntity.attachAsset(asset)
+        assetEntity.uploadAsset(client, function(err, usergridResponse, entity) {
+            assetEntity = entity
+            entity.should.have.property('file-metadata')
+            entity['file-metadata'].should.have.property('content-length').equal(expectedContentLength)
+            entity['file-metadata'].should.have.property('content-type').equal('image/jpeg')
+            done()
+        })
+    })
+})
+
+describe('downloadAsset()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    it('should download a an image from the remote entity', function(done) {
+        var client = new UsergridClient(config)
+        assetEntity.downloadAsset(client, 'image/jpeg', function(err, usergridResponse, entityWithAsset) {
+            entityWithAsset.should.have.property('asset').which.is.an.instanceof(UsergridAsset)
+            entityWithAsset.asset.should.have.property('contentType').equal(assetEntity['file-metadata']['content-type'])
+            entityWithAsset.asset.should.have.property('contentLength').equal(assetEntity['file-metadata']['content-length'])
+            // clean up the now un-needed asset entity
+            entityWithAsset.remove(client)
+            done()
+        })
+    })
+})
+
+describe('connect()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout + 4000)
+
+    var response,
+        entity1,
+        entity2,
+        client = new UsergridClient(),
+        query = new UsergridQuery(config.test.collection).eq('name', 'testEntityConnectOne').or.eq('name', 'testEntityConnectTwo').asc('name')
+
+    before(function(done) {
+        // Create the entities we're going to use for connections
+        client.POST(config.test.collection, [{
+            "name": "testEntityConnectOne"
+        }, {
+            "name": "testEntityConnectTwo"
+        }], function() {
+            client.GET(query, function(err, usergridResponse) {
+                response = usergridResponse
+                entity1 = response.first
+                entity2 = response.last
+                done()
+            })
+        })
+    })
+
+    it('should connect entities by passing a target UsergridEntity object as a parameter', function(done) {
+        var relationship = "foos"
+
+        entity1.connect(client, relationship, entity2, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                    "",
+                    config.test.collection,
+                    entity1.uuid,
+                    relationship,
+                    entity2.uuid,
+                    "connecting",
+                    relationship
+                ))
+                done()
+            })
+        })
+    })
+
+    it('should connect entities by passing target uuid as a parameter', function(done) {
+        var relationship = "bars"
+
+        entity1.connect(client, relationship, entity2.uuid, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                    "",
+                    config.test.collection,
+                    entity1.uuid,
+                    relationship,
+                    entity2.uuid,
+                    "connecting",
+                    relationship
+                ))
+                done()
+            })
+        })
+    })
+
+    it('should connect entities by passing target type and name as parameters', function(done) {
+        var relationship = "bazzes"
+
+        entity1.connect(client, relationship, entity2.type, entity2.name, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                    "",
+                    config.test.collection,
+                    entity1.uuid,
+                    relationship,
+                    entity2.uuid,
+                    "connecting",
+                    relationship
+                ))
+                done()
+            })
+        })
+    })
+
+    it('should fail to connect entities when specifying target name without type', function() {
+        should(function() {
+            entity1.connect("fails", 'badName', function() {})
+        }).throw()
+    })
+})
+
+describe('getConnections()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout + 4000)
+
+    var response,
+        client = new UsergridClient(),
+        query = new UsergridQuery(config.test.collection).eq('name', 'testEntityConnectOne').or.eq('name', 'testEntityConnectTwo').asc('name')
+
+    before(function(done) {
+        client.GET(query, function(err, usergridResponse) {
+            response = usergridResponse
+            done()
+        })
+    })
+
+    it('should get an entity\'s outbound connections', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "foos"
+
+        entity1.getConnections(client, UsergridClient.Connections.DIRECTION_OUT, relationship, function(err, usergridResponse) {
+            usergridResponse.first.metadata.connecting[relationship].should.equal(urljoin(
+                "",
+                config.test.collection,
+                entity1.uuid,
+                relationship,
+                entity2.uuid,
+                "connecting",
+                relationship
+            ))
+            done()
+        })
+    })
+
+    it('should get an entity\'s inbound connections', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "foos"
+
+        entity2.getConnections(client, UsergridClient.Connections.DIRECTION_IN, relationship, function(err, usergridResponse) {
+            usergridResponse.first.metadata.connections[relationship].should.equal(urljoin(
+                "",
+                config.test.collection,
+                entity2.uuid,
+                "connecting",
+                entity1.uuid,
+                relationship
+            ))
+            done()
+        })
+    })
+})
+
+describe('disconnect()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout + 4000)
+
+    var response,
+        client = new UsergridClient(),
+        query = new UsergridQuery(config.test.collection).eq('name', 'testEntityConnectOne').or.eq('name', 'testEntityConnectTwo').asc('name')
+
+    before(function(done) {
+        client.GET(query, function(err, usergridResponse) {
+            response = usergridResponse
+            done()
+        })
+    })
+
+    it('should disconnect entities by passing a target UsergridEntity object as a parameter', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "foos"
+
+        entity1.disconnect(client, relationship, entity2, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.entities.should.be.an.Array().with.lengthOf(0)
+                done()
+            })
+        })
+    })
+
+    it('should disconnect entities by passing target uuid as a parameter', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "bars"
+
+        entity1.disconnect(client, relationship, entity2.uuid, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.entities.should.be.an.Array().with.lengthOf(0)
+                done()
+            })
+        })
+    })
+
+    it('should disconnect entities by passing target type and name as parameters', function(done) {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        var relationship = "bazzes"
+
+        entity1.disconnect(client, relationship, entity2.type, entity2.name, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            client.getConnections(UsergridClient.Connections.DIRECTION_OUT, entity1, relationship, function(err, usergridResponse) {
+                usergridResponse.entities.should.be.an.Array().with.lengthOf(0)
+                done()
+            })
+        })
+    })
+
+    it('should fail to disconnect entities when specifying target name without type', function() {
+        var entity1 = response.first
+        var entity2 = response.last
+
+        should(function() {
+            entity1.disconnect("fails", entity2.name, function() {})
+        }).throw()
+    })
+})
+
+describe('usingAuth()', function() {
+
+    this.slow(_slow + 500)
+    this.timeout(_timeout)
+
+    var client = new UsergridClient(),
+        authFromToken = new UsergridAuth('BADTOKEN'),
+        _entity
+
+    it('should fail to reload an entity when using a bad ad-hoc token', function(done) {
+        client.GET(config.test.collection, function(err, getResponse) {
+            _entity = new UsergridEntity(getResponse.first)
+            _entity.usingAuth(authFromToken).reload(client, function(error, usergridResponse) {
+                usergridResponse.request.headers.should.not.have.property('authentication')
+                usergridResponse.ok.should.be.false()
+                error.name.should.equal('auth_bad_access_token')
+                done()
+            })
+        })
+    })
+
+    it('client.tempAuth should be destroyed after making a request with ad-hoc authentication', function(done) {
+        should(client.tempAuth).be.undefined()
+        done()
+    })
+
+    it('entity.tempAuth should be destroyed after making a request with ad-hoc authentication', function(done) {
+        should(_entity.tempAuth).be.undefined()
+        done()
+    })
+
+    it('should send an unauthenticated request when UsergridAuth.NO_AUTH is passed to .usingAuth()', function(done) {
+        // hack this using 'me' in case test apps have sandbox permissions
+        var entity = new UsergridEntity({
+            uuid: 'me',
+            type: 'users'
+        })
+        entity.usingAuth(UsergridAuth.NO_AUTH).reload(client, function(error, usergridResponse) {
+            usergridResponse.request.headers.should.not.have.property('authentication')
+            usergridResponse.ok.should.be.false()
+            error.name.should.equal('service_resource_not_found')
+            done()
+        })
+    })
+
+    it('should send an unauthenticated request when no arguments are passed to .usingAuth()', function(done) {
+        // hack this using 'me' in case test apps have sandbox permissions
+        var entity = new UsergridEntity({
+            uuid: 'me',
+            type: 'users'
+        })
+        entity.usingAuth().reload(client, function(error, usergridResponse) {
+            usergridResponse.request.headers.should.not.have.property('authentication')
+            usergridResponse.ok.should.be.false()
+            error.name.should.equal('service_resource_not_found')
+            done()
+        })
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/image.jpg b/tests/lib/image.jpg
new file mode 100644
index 0000000..32f4fa3
--- /dev/null
+++ b/tests/lib/image.jpg
Binary files differ
diff --git a/tests/lib/image_test.jpg b/tests/lib/image_test.jpg
new file mode 100644
index 0000000..32f4fa3
--- /dev/null
+++ b/tests/lib/image_test.jpg
Binary files differ
diff --git a/tests/lib/query.test.js b/tests/lib/query.test.js
new file mode 100644
index 0000000..e92c34d
--- /dev/null
+++ b/tests/lib/query.test.js
@@ -0,0 +1,106 @@
+'use strict'
+
+var UsergridQuery = require('../../lib/query')
+
+describe('_type', function() {
+    it('_type should equal "cats" when passing "type" as a parameter to UsergridQuery', function() {
+        var query = new UsergridQuery('cats')
+        query.should.have.property('_type').equal('cats')
+    })
+
+    it('_type should equal "cats" when calling .type() builder method', function() {
+        var query = new UsergridQuery().type('cats')
+        query.should.have.property('_type').equal('cats')
+    })
+
+    it('_type should equal "cats" when calling .collection() builder method', function() {
+        var query = new UsergridQuery().collection('cats')
+        query.should.have.property('_type').equal('cats')
+    })
+})
+
+describe('_limit', function() {
+    it('_limit should equal 2 when setting .limit(2)', function() {
+        var query = new UsergridQuery('cats').limit(2)
+        query.should.have.property('_limit').equal(2)
+    })
+
+    it('_limit should equal 10 when setting .limit(10)', function() {
+        var query = new UsergridQuery('cats').limit(10)
+        query.should.have.property('_limit').equal(10)
+    })
+})
+
+describe('_ql', function() {
+    it('should equal \'select *\' if query or sort are empty or underfined', function() {
+        var query = new UsergridQuery('cats')
+        query.should.have.property('_ql').equal('select *')
+    })
+
+    it('should support complex builder pattern syntax (chained constructor methods)', function() {
+        var query = new UsergridQuery('cats')
+            .gt('weight', 2.4)
+            .contains('color', 'bl*')
+            .not
+            .eq('color', 'blue')
+            .or
+            .eq('color', 'orange')
+        query.should.have.property('_ql').equal("select * where weight > 2.4 and color contains 'bl*' and not color = 'blue' or color = 'orange'")
+    })
+
+    it('and operator should be implied when joining multiple conditions', function() {
+        var query1 = new UsergridQuery('cats')
+            .gt('weight', 2.4)
+            .contains('color', 'bl*')
+        query1.should.have.property('_ql').equal("select * where weight > 2.4 and color contains 'bl*'")
+        var query2 = new UsergridQuery('cats')
+            .gt('weight', 2.4)
+            .and
+            .contains('color', 'bl*')
+        query2.should.have.property('_ql').equal("select * where weight > 2.4 and color contains 'bl*'")
+    })
+
+    it('not operator should precede conditional statement', function() {
+        var query = new UsergridQuery('cats')
+            .not
+            .eq('color', 'white')
+        query.should.have.property('_ql').equal("select * where not color = 'white'")
+    })
+
+    it('fromString should set _ql directly, bypassing builder pattern methods', function() {
+        var q = "where color = 'black' or color = 'orange'"
+        var query = new UsergridQuery('cats')
+            .fromString(q)
+        query.should.have.property('_ql').equal(q)
+    })
+
+    it('string values should be contained in single quotes', function() {
+        var query = new UsergridQuery('cats')
+            .eq('color', 'black')
+        query.should.have.property('_ql').equal("select * where color = 'black'")
+    })
+
+    it('boolean values should not be contained in single quotes', function() {
+        var query = new UsergridQuery('cats')
+            .eq('longHair', true)
+        query.should.have.property('_ql').equal("select * where longHair = true")
+    })
+
+    it('float values should not be contained in single quotes', function() {
+        var query = new UsergridQuery('cats')
+            .lt('weight', 18)
+        query.should.have.property('_ql').equal("select * where weight < 18")
+    })
+
+    it('integer values should not be contained in single quotes', function() {
+        var query = new UsergridQuery('cats')
+            .gte('weight', 2)
+        query.should.have.property('_ql').equal("select * where weight >= 2")
+    })
+
+    it('uuid values should not be contained in single quotes', function() {
+        var query = new UsergridQuery('cats')
+            .eq('uuid', 'a61e29ba-944f-11e5-8690-fbb14f62c803')
+        query.should.have.property('_ql').equal("select * where uuid = a61e29ba-944f-11e5-8690-fbb14f62c803")
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/response.test.js b/tests/lib/response.test.js
new file mode 100644
index 0000000..685d132
--- /dev/null
+++ b/tests/lib/response.test.js
@@ -0,0 +1,188 @@
+'use strict'
+
+var should = require('should'),
+    config = require('../../helpers').config,
+    UsergridClient = require('../../lib/client'),
+    UsergridEntity = require('../../lib/entity'),
+    UsergridUser = require('../../lib/user'),
+    UsergridQuery = require('../../lib/query'),
+    UsergridResponseError = require('../../lib/responseError'),
+    _ = require('lodash')
+
+var client = new UsergridClient()
+
+var _response,
+    _slow = 500,
+    _timeout = 4000
+
+before(function(done) {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    client.GET(config.test.collection, function(err, usergridResponse) {
+        _response = usergridResponse
+        done()
+    })
+})
+
+describe('headers', function() {
+    it('should be an object', function() {
+        _response.headers.should.be.an.Object().with.property('content-type')
+    })
+})
+
+describe('statusCode', function() {
+    it('should be a number', function() {
+        _response.statusCode.should.be.a.Number()
+    })
+})
+
+describe('ok', function() {
+    it('should be a bool', function() {
+        _response.ok.should.be.a.Boolean()
+    })
+})
+
+describe('metadata', function() {
+    it('should be a read-only object', function() {
+        _response.metadata.should.be.an.Object().with.any.properties(['action', 'application', 'path', 'uri', 'timestamp', 'duration'])
+        Object.isFrozen(_response.metadata).should.be.true()
+        should(function() {
+            _response.metadata.uri = 'TEST'
+        }).throw()
+    })
+})
+
+describe('error', function() {
+    it('should be a UsergridResponseError object', function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        client.GET(config.test.collection, 'BADNAMEORUUID', function(err, usergridResponse) {
+            usergridResponse.error.should.be.an.instanceof(UsergridResponseError)
+            done()
+        })
+    })
+})
+
+describe('users', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    it('response.users should be an array of UsergridUser objects', function(done) {
+        client.setAppAuth(config.clientId, config.clientSecret, config.tokenTtl)
+        client.authenticateApp(function(err) {
+            should(err).be.undefined()
+            client.GET('users', function(err, usergridResponse) {
+                usergridResponse.ok.should.be.true()
+                usergridResponse.users.should.be.an.Array()
+                usergridResponse.users.forEach(function(user) {
+                    user.should.be.an.instanceof(UsergridUser)
+                })
+                done()
+            })
+        })
+    })
+})
+
+describe('user', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var user
+
+    it('response.user should be a UsergridUser object and have a valid uuid matching the first object in response.users', function(done) {
+        client.setAppAuth(config.clientId, config.clientSecret, config.tokenTtl)
+        client.authenticateApp(function(err) {
+            should(err).be.undefined()
+            client.GET('users', function(err, usergridResponse) {
+                user = usergridResponse.user
+                user.should.be.an.instanceof(UsergridUser).with.property('uuid').equal(_.first(usergridResponse.entities).uuid)
+                done()
+            })
+        })
+    })
+
+    it('response.user should be a subclass of UsergridEntity', function(done) {
+        user.isUser.should.be.true()
+        user.should.be.an.instanceof(UsergridEntity)
+        done()
+    })
+})
+
+describe('entities', function() {
+    it('should be an array of UsergridEntity objects', function() {
+        _response.entities.should.be.an.Array()
+        _response.entities.forEach(function(entity) {
+            entity.should.be.an.instanceof(UsergridEntity)
+        })
+    })
+})
+
+describe('first, entity', function() {
+    it('response.first should be a UsergridEntity object and have a valid uuid matching the first object in response.entities', function() {
+        _response.first.should.be.an.instanceof(UsergridEntity).with.property('uuid').equal(_.first(_response.entities).uuid)
+    })
+
+    it('response.entity should be a reference to response.first', function() {
+        _response.should.have.property('entity').deepEqual(_response.first)
+    })
+})
+
+describe('last', function() {
+    it('last should be a UsergridEntity object and have a valid uuid matching the last object in response.entities', function() {
+        _response.last.should.be.an.instanceof(UsergridEntity).with.property('uuid').equal(_.last(_response.entities).uuid)
+    })
+})
+
+describe('hasNextPage', function() {
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    it('should be true when more entities exist', function(done) {
+        client.GET(config.test.collection, function(err, usergridResponse) {
+            usergridResponse.hasNextPage.should.be.true()
+            done()
+        })
+    })
+
+    it('should be false when no more entities exist', function(done) {
+        client.GET('users', function(err, usergridResponse) {
+            usergridResponse.metadata.count.should.be.lessThan(10)
+            usergridResponse.hasNextPage.should.not.be.true()
+            done()
+        })
+    })
+})
+
+describe('loadNextPage()', function() {
+    this.slow(_slow + 800)
+    this.timeout(_timeout + 2000)
+
+    var firstResponse
+
+    before(function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        var query = new UsergridQuery(config.test.collection).limit(10)
+
+        client.GET(query, function(err, usergridResponse) {
+            firstResponse = usergridResponse
+            done()
+        })
+    })
+
+    it('should load a new page of entities by passing an instance of UsergridClient', function(done) {
+        firstResponse.loadNextPage(client, function(err, usergridResponse) {
+            usergridResponse.first.uuid.should.not.equal(firstResponse.first.uuid)
+            usergridResponse.entities.length.should.equal(10)
+            done()
+        })
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/responseError.test.js b/tests/lib/responseError.test.js
new file mode 100644
index 0000000..f746279
--- /dev/null
+++ b/tests/lib/responseError.test.js
@@ -0,0 +1,47 @@
+'use strict'
+
+var should = require('should'),
+    config = require('../../helpers').config,
+    UsergridClient = require('../../lib/client'),
+    UsergridResponseError = require('../../lib/responseError')
+
+var client = new UsergridClient()
+
+var _response,
+    _slow = 500,
+    _timeout = 4000
+
+describe('name, description, exception', function() {
+
+    before(function(done) {
+
+        this.slow(_slow)
+        this.timeout(_timeout)
+
+        client.GET(config.test.collection, 'BADNAMEORUUID', function(err, usergridResponse) {
+            _response = usergridResponse
+            done()
+        })
+    })
+
+    it('response.statusCode should be greater than or equal to 400', function() {
+        _response.ok.should.be.false()
+    })
+
+    it('response.error should be a UsergridResponseError object with name, description, and exception keys', function() {
+        _response.ok.should.be.false()
+        _response.error.should.be.an.instanceof(UsergridResponseError).with.properties(['name', 'description', 'exception'])
+    })
+})
+
+describe('undefined check', function() {
+    it('response.error should be undefined on a successful response', function(done) {
+        this.slow(_slow)
+        this.timeout(_timeout)
+        client.GET(config.test.collection, function(err, usergridResponse) {
+            usergridResponse.ok.should.be.true()
+            should(usergridResponse.error).be.undefined()
+            done()
+        })
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/user.test.js b/tests/lib/user.test.js
new file mode 100644
index 0000000..ef89a20
--- /dev/null
+++ b/tests/lib/user.test.js
@@ -0,0 +1,273 @@
+'use strict'
+
+var should = require('should'),
+    util = require('util'),
+    chance = new require('chance').Chance(),
+    config = require('../../helpers').config,
+    UsergridClient = require('../../lib/client'),
+    UsergridUser = require('../../lib/user'),
+    UsergridQuery = require('../../lib/query')
+
+var _slow = 1500,
+    _timeout = 4000,
+    _username1 = chance.word(),
+    _user1 = new UsergridUser({
+        username: _username1,
+        password: config.test.password
+    }),
+    client = new UsergridClient(config)
+
+before(function(done) {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var query = new UsergridQuery('users').not.eq('username', config.test.username).limit(20)
+    // clean up old user entities as the UsergridResponse tests rely on this collection containing less than 10 entities
+    client.DELETE(query, function() {
+        _user1.create(client, function() {
+            done()
+        })
+    })
+})
+
+describe('create()', function() {
+
+    it(util.format("should create a new user with the username '%s'", _username1), function() {
+        _user1.username.should.equal(_username1)
+    })
+
+    it('should have a valid uuid', function() {
+        _user1.should.have.property('uuid').which.is.a.uuid()
+    })
+
+    it('should have a created date', function() {
+        _user1.should.have.property('created')
+    })
+
+    it('should be activated (i.e. has a valid password)', function() {
+        _user1.should.have.property('activated').true()
+    })
+
+    it('should not have a password property', function() {
+        _user1.should.not.have.property('password')
+    })
+
+    it('should fail gracefully when a username already exists', function(done) {
+        var user = new UsergridUser({
+            username: _username1,
+            password: config.test.password
+        })
+        user.create(client, function(err, usergridResponse) {
+            err.should.not.be.null()
+            err.should.containDeep({
+                name: 'duplicate_unique_property_exists'
+            })
+            usergridResponse.ok.should.be.false()
+            done()
+        })
+    })
+
+    it('should create a new user on the server', function(done) {
+        var username = chance.word()
+        var user = new UsergridUser({
+            username: username,
+            password: config.test.password
+        })
+        user.create(client, function(err, usergridResponse, user) {
+            client.isSharedInstance.should.be.false()
+            user.username.should.equal(username)
+            user.should.have.property('uuid').which.is.a.uuid()
+            user.should.have.property('created')
+            user.should.have.property('activated').true()
+            user.should.not.have.property('password')
+                // cleanup
+            user.remove(client, function() {
+                done()
+            })
+        })
+    })
+})
+
+describe('login()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    it(util.format("it should log in the user '%s' and receive a token", _username1), function(done) {
+        _user1.password = config.test.password
+        _user1.login(client, function(err, response, token) {
+            _user1.auth.should.have.property('token').equal(token)
+            _user1.should.not.have.property('password')
+            _user1.auth.should.not.have.property('password')
+            done()
+        })
+    })
+})
+
+describe('logout()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    it(util.format("it should log out '%s' and destroy the saved UsergridUserAuth instance", _username1), function(done) {
+        _user1.logout(client, function(err, response) {
+            response.ok.should.be.true()
+            response.body.action.should.equal("revoked user token")
+            _user1.auth.isValid.should.be.false()
+            done()
+        })
+    })
+
+    it("it should return an error when attempting to log out a user that does not have a valid token", function(done) {
+        _user1.logout(client, function(err) {
+            err.should.containDeep({
+                name: 'no_valid_token'
+            })
+            done()
+        })
+    })
+})
+
+describe('logoutAllSessions()', function() {
+    it(util.format("it should log out all tokens for the user '%s' destroy the saved UsergridUserAuth instance", _username1), function(done) {
+        _user1.password = config.test.password
+        _user1.login(client, function() {
+            _user1.logoutAllSessions(client, function(err, response) {
+                response.ok.should.be.true()
+                response.body.action.should.equal("revoked user tokens")
+                _user1.auth.isValid.should.be.false()
+                done()
+            })
+        })
+    })
+})
+
+describe('resetPassword()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    it(util.format("it should reset the password for '%s' by passing parameters", _username1), function(done) {
+        _user1.resetPassword(client, config.test.password, '2cool4u', function(err, response) {
+            response.ok.should.be.true()
+            response.body.action.should.equal("set user password")
+            done()
+        })
+    })
+
+    it(util.format("it should reset the password for '%s' by passing an object", _username1), function(done) {
+        _user1.resetPassword(client, {
+            oldPassword: '2cool4u',
+            newPassword: config.test.password
+        }, function(err, response) {
+            response.ok.should.be.true()
+            response.body.action.should.equal("set user password")
+            done()
+        })
+    })
+
+    it(util.format("it should not reset the password for '%s' when passing a bad old password", _username1), function(done) {
+        _user1.resetPassword(client, {
+            oldPassword: 'BADOLDPASSWORD',
+            newPassword: config.test.password
+        }, function(err, response) {
+            response.ok.should.be.false()
+            err.name.should.equal('auth_invalid_username_or_password')
+            _user1.remove(client, function() {
+                done()
+            })
+        })
+    })
+
+    it("it should return an error when attempting to reset a password with missing arguments", function() {
+        should(function() {
+            _user1.resetPassword(client, 'NEWPASSWORD', function() {})
+        }).throw()
+    })
+})
+
+describe('CheckAvailable()', function() {
+
+    this.slow(_slow)
+    this.timeout(_timeout)
+
+    var nonExistentEmail = util.format('%s@%s.com', chance.word(), chance.word())
+    var nonExistentUsername = chance.word()
+
+    it(util.format("it should return true for username '%s'", config.test.username), function(done) {
+        UsergridUser.CheckAvailable(client, {
+            username: config.test.username
+        }, function(err, response, exists) {
+            exists.should.be.true()
+            done()
+        })
+    })
+
+    it(util.format("it should return true for email '%s'", config.test.email), function(done) {
+        UsergridUser.CheckAvailable(client, {
+            email: config.test.email
+        }, function(err, response, exists) {
+            exists.should.be.true()
+            done()
+        })
+    })
+
+    it(util.format("it should return true for email '%s' and non-existent username '%s'", config.test.email, nonExistentUsername), function(done) {
+        UsergridUser.CheckAvailable(client, {
+            email: config.test.email,
+            username: nonExistentUsername
+        }, function(err, response, exists) {
+            exists.should.be.true()
+            done()
+        })
+    })
+
+    it(util.format("it should return true for non-existent email '%s' and username '%s'", nonExistentEmail, config.test.username), function(done) {
+        UsergridUser.CheckAvailable(client, {
+            email: nonExistentEmail,
+            username: config.test.username
+        }, function(err, response, exists) {
+            exists.should.be.true()
+            done()
+        })
+    })
+
+    it(util.format("it should return true for email '%s' and username '%s'", config.test.email, config.test.username), function(done) {
+        UsergridUser.CheckAvailable(client, {
+            email: config.test.email,
+            username: config.test.useranme
+        }, function(err, response, exists) {
+            exists.should.be.true()
+            done()
+        })
+    })
+
+    it(util.format("it should return false for non-existent email '%s'", nonExistentEmail), function(done) {
+        UsergridUser.CheckAvailable(client, {
+            email: nonExistentEmail
+        }, function(err, response, exists) {
+            exists.should.be.false()
+            done()
+        })
+    })
+
+    it(util.format("it should return false for non-existent username '%s'", nonExistentUsername), function(done) {
+        UsergridUser.CheckAvailable(client, {
+            username: nonExistentUsername
+        }, function(err, response, exists) {
+            exists.should.be.false()
+            done()
+        })
+    })
+
+    it(util.format("it should return false for non-existent email '%s' and non-existent username '%s'", nonExistentEmail, nonExistentUsername), function(done) {
+        UsergridUser.CheckAvailable(client, {
+            email: nonExistentEmail,
+            username: nonExistentUsername
+        }, function(err, response, exists) {
+            exists.should.be.false()
+            done()
+        })
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/usergrid.init.test.js b/tests/lib/usergrid.init.test.js
new file mode 100644
index 0000000..b8a9fd9
--- /dev/null
+++ b/tests/lib/usergrid.init.test.js
@@ -0,0 +1,21 @@
+'use strict'
+
+var config = require('../../helpers').config,
+    Usergrid = require('../../usergrid'),
+    UsergridClient = require('../../lib/client'),
+    util = require('util'),
+    _ = require('lodash') 
+
+describe('init() / initSharedInstance()', function() {
+    it('should be an instance of UsergridClient', function(done) {
+        Usergrid.init()
+        Usergrid.initSharedInstance()
+        Usergrid.should.be.an.instanceof(UsergridClient)
+        done()
+    })
+    
+    it(util.format('should be testing against a Usergrid v%s instance', config.target), function(done) {
+        util.format('%s', config.target).should.equal((_.last(process.argv)).startsWith('--target=') ? _.last(process.argv).replace(/--target=/, '') : '2.1')
+        done()
+    })
+})
\ No newline at end of file
diff --git a/tests/lib/usergrid.singleton.test.js b/tests/lib/usergrid.singleton.test.js
new file mode 100644
index 0000000..9f73bab
--- /dev/null
+++ b/tests/lib/usergrid.singleton.test.js
@@ -0,0 +1,9 @@
+'use strict'
+
+var Usergrid = require('../../usergrid')
+
+it('should be initialized when defined in another module', function(done) {
+    Usergrid.should.have.property('isInitialized').which.is.true()
+    Usergrid.should.have.property('isSharedInstance').which.is.true()
+    done()
+})
\ No newline at end of file
diff --git a/tests/lib/usergrid.teardown.test.js b/tests/lib/usergrid.teardown.test.js
new file mode 100644
index 0000000..d50ecd4
--- /dev/null
+++ b/tests/lib/usergrid.teardown.test.js
@@ -0,0 +1,14 @@
+'use strict'
+
+var Usergrid = require('../../usergrid'),
+    UsergridClient = require('../../lib/client')
+
+it('should be destroyed', function(done) {
+    // destroy shared instance to prevent other tests from defaulting to use the shared instance
+    var UsergridRef = require.resolve('../../usergrid')
+    delete require.cache[UsergridRef]
+    Usergrid = require('../../usergrid')
+    Usergrid.should.have.property('isInitialized').which.is.false()
+    Usergrid.should.not.be.an.instanceof(UsergridClient)
+    done()
+})
\ No newline at end of file
diff --git a/tests/main.test.js b/tests/main.test.js
new file mode 100644
index 0000000..22bbedd
--- /dev/null
+++ b/tests/main.test.js
@@ -0,0 +1,75 @@
+'use strict'
+
+// module config
+var should = require('should'),
+    _ = require('lodash')
+
+_.mixin(require('lodash-uuid'))
+
+should.Assertion.add('uuid', function() {
+    this.params = {
+        operator: 'to be a valid uuid'
+    }
+    this.assert(_.isUuid(this.obj))
+})
+
+should.Assertion.add('buffer', function() {
+    this.params = {
+        operator: 'to be buffer data'
+    }
+    this.assert(Buffer.isBuffer(this.obj))
+})
+
+// end module config
+
+describe('Usergrid initialization', function() {
+    return require('./lib/usergrid.init.test')
+})
+
+describe('Usergrid singleton', function() {
+    return require('./lib/usergrid.singleton.test')
+})
+
+describe('Usergrid teardown', function() {
+    return require('./lib/usergrid.teardown.test')
+})
+
+describe('UsergridClient initialization', function() {
+    return require('./lib/client.init.test')
+})
+
+describe('UsergridClient REST operations', function() {
+    return require('./lib/client.rest.test')
+})
+
+describe('UsergridClient connections', function() {
+    return require('./lib/client.connections.test')
+})
+
+describe('UsergridClient authentication', function() {
+    return require('./lib/client.auth.test')
+})
+
+describe('UsergridQuery', function() {
+    return require('./lib/query.test')
+})
+
+describe('UsergridResponse', function() {
+    return require('./lib/response.test')
+})
+
+describe('UsergridResponseError', function() {
+    return require('./lib/responseError.test')
+})
+
+describe('UsergridEntity', function() {
+    return require('./lib/entity.test')
+})
+
+describe('UsergridUser', function() {
+    return require('./lib/user.test')
+})
+
+describe('UsergridAsset', function() {
+    return require('./lib/asset.test')
+})
\ No newline at end of file
diff --git a/usergrid.js b/usergrid.js
new file mode 100644
index 0000000..cc6ba27
--- /dev/null
+++ b/usergrid.js
@@ -0,0 +1,37 @@
+/*
+Licensed under the Apache License, Version 2.0 (the "License");
+you may not use this file except in compliance with the License.
+You may obtain a copy of the License at
+
+    http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing, software
+distributed under the License is distributed on an "AS IS" BASIS,
+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+See the License for the specific language governing permissions and
+limitations under the License.
+*/
+
+'use strict'
+
+var _ = require('lodash')
+
+var Usergrid = {
+    isInitialized: false,
+    isSharedInstance: true,
+    initSharedInstance: function(options) {
+        var self = this
+        if (self.isInitialized) {
+            console.log('Usergrid shared instance is already initialized')
+            return self
+        }
+        var UsergridClient = require('./lib/client')
+        Object.setPrototypeOf(self, new UsergridClient(options))
+        _.assign(self, new UsergridClient(options))
+        self.isInitialized = true
+        self.isSharedInstance = true
+    }
+}
+
+Usergrid.init = Usergrid.initSharedInstance
+module.exports = Usergrid
\ No newline at end of file
