From 02d26985e19c4b51de143f93bf793fce0d34172a Mon Sep 17 00:00:00 2001 From: Youmi Koh Date: Wed, 2 Nov 2022 19:21:37 -0400 Subject: [PATCH 1/2] Add example OAuth workflow --- README.md | 2 ++ docs/oauth-workflow-example.md | 58 ++++++++++++++++++++++++++++++++++ 2 files changed, 60 insertions(+) create mode 100644 docs/oauth-workflow-example.md diff --git a/README.md b/README.md index d473a015..49d82ec1 100644 --- a/README.md +++ b/README.md @@ -70,6 +70,8 @@ pip install --upgrade ShopifyAPI # you should save the access token now for future use. ``` + > See an [example OAuth workflow here](docs/oauth-workflow-example.md) + 1. Now you're ready to make authorized API requests to your shop!: ```python diff --git a/docs/oauth-workflow-example.md b/docs/oauth-workflow-example.md new file mode 100644 index 00000000..fb81b1a9 --- /dev/null +++ b/docs/oauth-workflow-example.md @@ -0,0 +1,58 @@ +# Example OAuth workflow + +The Shopify Python API [validates HMAC and timing attacks](https://shopify.dev/apps/auth/oauth/getting-started#step-2-verify-the-installation-request) with the `request_token` function. Below is a basic example OAuth workflow for a FastAPI app. + + +## Setup + +1. Create a new application in the Partners Dashboard, and retrieve your API key and API secret. + +2. Configure your app URL and Admin API version. Initialize your `shopify.Session` class with your API key and API secret for authentication. + +```python +import shopify + +VERSION = "2022-07" +HOST = "https://app-url" + +API_KEY = "api-key" +API_SECRET = "api-secret" + +shopify.Session.setup(api_key=API_KEY, secret=API_SECRET) +``` + +3. Request permissions from the merchant with the `auth_url` from the `create_permission_url` function. Once the merchant acccepts, a temporary token `code` is sent to the specified `redirect_uri` of your app. + +```python +from fastapi import FastAPI, Request +from fastapi.responses import RedirectResponse + +@app.get("/", response_class=RedirectResponse) +async def install(shop_name: str): + shop_url = f"{shop_name}.myshopify.com" + state = binascii.b2a_hex(os.urandom(15)).decode("utf-8") + redirect_uri = f"{HOST}/auth/shopify/callback" + scopes = ['read_products'] + + new_session = shopify.Session(shop_url, VERSION) + auth_url = new_session.create_permission_url(scopes, redirect_uri, state) + return RedirectResponse( + url=auth_url, + status_code=303 + ) +``` + +4. To capture the `code`, set up a callback handler in your app. To exchange the temporary token for a permanent access token, supply the parameters from this request to the `request_token` function. + +```python +@app.get("/auth/shopify/callback") +async def auth_callback(request: Request): + request_params = dict(request.query_params) + shop_url = request_params.get("shop") + + session = shopify.Session(shop_url, VERSION) + access_token = session.request_token(request_params) + # store access_token +``` + + From c145d1f5310622a33b78422b6a27e928ac14dc71 Mon Sep 17 00:00:00 2001 From: Youmi Koh Date: Wed, 2 Nov 2022 19:32:35 -0400 Subject: [PATCH 2/2] Add example query string from dev docs --- docs/oauth-workflow-example.md | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/docs/oauth-workflow-example.md b/docs/oauth-workflow-example.md index fb81b1a9..e3790550 100644 --- a/docs/oauth-workflow-example.md +++ b/docs/oauth-workflow-example.md @@ -1,6 +1,6 @@ # Example OAuth workflow -The Shopify Python API [validates HMAC and timing attacks](https://shopify.dev/apps/auth/oauth/getting-started#step-2-verify-the-installation-request) with the `request_token` function. Below is a basic example OAuth workflow for a FastAPI app. +The Shopify Python API [validates HMAC and timing attacks](https://shopify.dev/apps/auth/oauth/getting-started#step-2-verify-the-installation-request) with the `request_token` function. Below is a basic example OAuth workflow for a FastAPI app. ## Setup @@ -19,7 +19,7 @@ API_KEY = "api-key" API_SECRET = "api-secret" shopify.Session.setup(api_key=API_KEY, secret=API_SECRET) -``` +``` 3. Request permissions from the merchant with the `auth_url` from the `create_permission_url` function. Once the merchant acccepts, a temporary token `code` is sent to the specified `redirect_uri` of your app. @@ -37,22 +37,20 @@ async def install(shop_name: str): new_session = shopify.Session(shop_url, VERSION) auth_url = new_session.create_permission_url(scopes, redirect_uri, state) return RedirectResponse( - url=auth_url, + url=auth_url, status_code=303 ) ``` -4. To capture the `code`, set up a callback handler in your app. To exchange the temporary token for a permanent access token, supply the parameters from this request to the `request_token` function. +4. To capture the `code`, set up a callback handler in your app. To exchange the temporary token for a permanent access token, supply the parameters from this request to the `request_token` function. See an [example query string here](https://shopify.dev/apps/auth/oauth/getting-started#step-2-verify-the-installation-request) to be passed as the `request_params`. ```python @app.get("/auth/shopify/callback") async def auth_callback(request: Request): request_params = dict(request.query_params) shop_url = request_params.get("shop") - + session = shopify.Session(shop_url, VERSION) access_token = session.request_token(request_params) # store access_token ``` - -