-
Notifications
You must be signed in to change notification settings - Fork 3.8k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
PhoneGap wrapper around Shopify4J to make authenticated API calls
to the Shopify API from Javascript
- Loading branch information
Showing
3 changed files
with
279 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,100 @@ | ||
# ShopGap plugin for Android/Phonegap | ||
|
||
Chris Saunders // @csaunders | ||
|
||
## About | ||
|
||
ShopGap is a wrapper around [Shopify4J](http://github.com/shopify/Shopify4J) to allow you to make Authenticated API calls to the Shopify API. | ||
|
||
## Dependencies | ||
|
||
You will need to include Shopify4J and all of it's dependencies in your project in order for this tool to work. This should be as simple as adding Shopify4J as a Library in your Android configuration. | ||
|
||
## Using the plugin | ||
|
||
**This has been developed against PhoneGap 1.1.0** | ||
|
||
* Add java code to your projects source | ||
|
||
* Register the plugin in the plugins.xml file | ||
|
||
```xml | ||
<plugin name="ShopGapPlugin" value="ca.christophersaunders.shopgap.ShopGapPlugin" /> | ||
``` | ||
|
||
* Setup your authenticated session with the Shopify API | ||
|
||
```javascript | ||
window.plugins.shopGap.setup( | ||
'YOUR_API_KEY', | ||
'GENERATED_API_PASSWORD', | ||
'SHOP_NAME', | ||
successFunctionOrNull, | ||
failureFunctionOrNull | ||
); | ||
``` | ||
|
||
* Make calls to the Shopify API | ||
|
||
```javascript | ||
var success = function(resultJson){ | ||
console.log(JSON.stringify(resultJson)); | ||
} | ||
|
||
window.plugins.shopGap.read( | ||
'products', // endpoint | ||
null, // query -- not supported yet | ||
null, // data -- not needed for GET requests | ||
function(r){success(r);}, // success callback | ||
function(e){console.log}); // failure callback | ||
``` | ||
|
||
### Endpoints | ||
|
||
The plugin takes care of most of the work for the endpoints, all you need to | ||
do is fill in a few missing pieces. | ||
|
||
```javascript | ||
// get all products, | ||
window.plugins.shopGap.read('products', null, null, s, f); | ||
|
||
// get product 1 | ||
window.plugins.shopGap.read('products/1', null, null, s, f); | ||
|
||
// create product | ||
window.plugins.shopGap.create('products', null, JSON.stringify(newProduct), s, f); | ||
|
||
// update product 1 | ||
window.plugins.shopGap.update('products/1', null, JSON.stringify(updateProduct), s, f); | ||
|
||
// delete product 1 | ||
window.plugins.shopGap.destry('products/1', null, null, s, f); | ||
``` | ||
|
||
## Release Notes | ||
|
||
0.1.0 Initial Release | ||
|
||
## License | ||
|
||
The MIT License | ||
|
||
Copyright (c) 2011 Chris Saunders | ||
|
||
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. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,138 @@ | ||
package ca.christophersaunders.shopgap; | ||
|
||
import java.io.BufferedInputStream; | ||
import java.io.ByteArrayOutputStream; | ||
import java.io.IOException; | ||
import java.io.InputStream; | ||
import java.io.StringReader; | ||
|
||
import org.json.JSONArray; | ||
import org.json.JSONException; | ||
import org.json.JSONObject; | ||
|
||
import com.phonegap.api.Plugin; | ||
import com.phonegap.api.PluginResult; | ||
import com.phonegap.api.PluginResult.Status; | ||
import com.shopify.api.client.ShopifyClient; | ||
import com.shopify.api.credentials.Credential; | ||
import com.shopify.api.endpoints.JsonPipeService; | ||
|
||
public class ShopGapPlugin extends Plugin { | ||
private static final String API_KEY = "apikey"; | ||
private static final String PASSWORD = "password"; | ||
private static final String SHOPNAME = "shopname"; | ||
private static final String CALL = "call"; | ||
private static final String ENDPOINT = "endpoint"; | ||
private static final String QUERY = "query"; | ||
private static final String DATA = "data"; | ||
|
||
private ShopifyClient client; | ||
private JsonPipeService service; | ||
|
||
enum Methods { CALL_API, SETUP }; | ||
enum Call { READ, CREATE, UPDATE, DESTROY }; | ||
|
||
@Override | ||
public PluginResult execute(String func, JSONArray arguments, String callbackId) { | ||
try { | ||
JSONObject argsMap = arguments.getJSONObject(0); | ||
switch(determineMethod(func)) { | ||
case CALL_API: | ||
JSONObject results = callAPI(determineCall(argsMap.getString(CALL)), argsMap); | ||
return new PluginResult(Status.OK, results); | ||
case SETUP: | ||
if(setupClient(argsMap)) { | ||
return new PluginResult(Status.OK); | ||
} | ||
break; | ||
default: | ||
return new PluginResult(PluginResult.Status.INVALID_ACTION); | ||
} | ||
} catch (JSONException e) { | ||
// Trololololololo | ||
return new PluginResult(PluginResult.Status.JSON_EXCEPTION); | ||
} | ||
return null; | ||
} | ||
|
||
private Methods determineMethod(String name){ | ||
if(name.equals("callapi")) | ||
return Methods.CALL_API; | ||
if(name.equals("setup")) | ||
return Methods.SETUP; | ||
return null; | ||
} | ||
|
||
private Call determineCall(String callname) { | ||
if(callname.equals("read")) | ||
return Call.READ; | ||
if (callname.equals("update")) | ||
return Call.UPDATE; | ||
if (callname.equals("create")) | ||
return Call.CREATE; | ||
if (callname.equals("destroy")) | ||
return Call.DESTROY; | ||
return null; | ||
} | ||
|
||
private boolean setupClient(JSONObject args) throws JSONException { | ||
if (args.has(API_KEY) && args.has(PASSWORD) && args.has(SHOPNAME)) { | ||
String apiKey = args.getString(API_KEY); | ||
String passwd = args.getString(PASSWORD); | ||
String shop = args.getString(SHOPNAME); | ||
|
||
Credential cred = new Credential(apiKey, "", shop, passwd); | ||
client = new ShopifyClient(cred); | ||
service = client.constructService(JsonPipeService.class); | ||
return true; | ||
} | ||
return false; | ||
} | ||
|
||
private JSONObject callAPI(Call call, JSONObject args) { | ||
try { | ||
String endpoint = null, data = null, query = null; | ||
if(args.has(ENDPOINT)) | ||
endpoint = args.getString(ENDPOINT); | ||
if(args.has(QUERY)) | ||
query = args.getString(QUERY); | ||
if(args.has(DATA)) | ||
data = args.getString(DATA); | ||
|
||
InputStream result = null; | ||
|
||
switch(call) { | ||
case CREATE: | ||
result = service.create(endpoint, data); | ||
break; | ||
case READ: | ||
result = service.read(endpoint); | ||
break; | ||
case UPDATE: | ||
result = service.update(endpoint, data); | ||
break; | ||
case DESTROY: | ||
result = service.destroy(endpoint); | ||
break; | ||
} | ||
|
||
if( result != null) { | ||
ByteArrayOutputStream baos = new ByteArrayOutputStream(); | ||
BufferedInputStream bis = new BufferedInputStream(result); | ||
byte[] resultData = new byte[0x4000]; | ||
int dataRead = 0; | ||
while((dataRead = bis.read(resultData)) > 0) { | ||
baos.write(resultData, 0, dataRead); | ||
} | ||
return new JSONObject(new String(baos.toByteArray())); | ||
} | ||
|
||
} catch (JSONException e) { | ||
e.printStackTrace(); | ||
} catch (IOException e) { | ||
e.printStackTrace(); | ||
} | ||
return new JSONObject(); | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,41 @@ | ||
var ShopGap = function(){}; | ||
|
||
ShopGap.prototype.setup = function(apiKey, password, shopname, onSuccessFn, onFailureFn){ | ||
var args = {'apikey': apiKey, 'password': password, 'shopname': shopname}; | ||
return PhoneGap.exec(onSuccessFn, onFailureFn, 'ShopGapPlugin', 'setup', [args]); | ||
}; | ||
|
||
ShopGap.prototype.consArgs = function(call, endpoint, query, data){ | ||
return {call: call, endpoint: endpoint, query: query, data: data}; | ||
}; | ||
|
||
ShopGap.prototype.read = function(endpoint, query, data, success, failure){ | ||
return this.callapi(this.consArgs('read', endpoint, query, data), success, failure); | ||
}; | ||
|
||
ShopGap.prototype.update = function(endpoint, query, data, success, failure){ | ||
return this.callapi(this.consArgs('update', endpoint, query, data), success, failure); | ||
}; | ||
|
||
ShopGap.prototype.create = function(endpoint, query, data, success, failure){ | ||
return this.callapi(this.consArgs('create', endpoint, query, data), success, failure); | ||
}; | ||
|
||
ShopGap.prototype.destroy = function(endpoint, query, data, success, failure){ | ||
return this.callapi(this.consArgs('destroy', endpoint, query, data), success, failure); | ||
}; | ||
|
||
ShopGap.prototype.callapi = function(args, onSuccessFn, onFailureFn){ | ||
return PhoneGap.exec(onSuccessFn, onFailureFn, 'ShopGapPlugin', 'callapi', [args]); | ||
}; | ||
|
||
/* | ||
ShopGap.prototype.callapi = function(call, endpoint, query, data, onSuccessFn, onFailureFn){ | ||
var args = {'endpoint': endpoint, 'data': data, 'query': query}; | ||
return PhoneGap.exec(onSuccessFn, onFailureFn, 'ShopGapPlugin', 'callapi', [args]); | ||
}; | ||
*/ | ||
|
||
PhoneGap.addConstructor(function(){ | ||
PhoneGap.addPlugin('shopGap', new ShopGap()); | ||
}); |