401 (Unauthorized) trying to insert script_tag using Python API

Solved
Highlighted
Tourist
6 1 1

My public app is developed with Python API and uses Flask.

 

It successfully installs and I get and keep an offline access_token in my database with the scope ["write_products", "read_products", "read_script_tags", "write_script_tags"].

 

Now I want to use my new-found authenticated session to actually do something useful! The first order of business is inserting a script_tag on the customer's shop.

 

So I do the following:

 

    def upsert_script_tag(self, src):
        script_reference={"event": "onload", "src": f"{src}"}
        print(f"UPSERTING SCRIPT TAG WITH '{script_reference}'")
        st=shopify.ScriptTag(script_reference)
        ret = st.save()
        if st.errors:
            print(f"ERROR: {st.errors.full_messages()}")
        print(f" + Return was :{ret}")

At which point I get the following in my log when it gets called:

 

 UPSERTING SCRIPT TAG WITH '{'event': 'onload', 'src': 'https://bsp.this-some-whaky-site.com/shopify/script_tag'}'
shopify_app     | Traceback (most recent call last):
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/pyactiveresource/connection.py", line 286, in _open
shopify_app     |     http_response = self._handle_error(self._urlopen(request))
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/pyactiveresource/connection.py", line 316, in _urlopen
shopify_app     |     return urllib.request.urlopen(request, timeout=self.timeout)
shopify_app     |   File "/usr/local/lib/python3.7/urllib/request.py", line 222, in urlopen
shopify_app     |     return opener.open(url, data, timeout)
shopify_app     |   File "/usr/local/lib/python3.7/urllib/request.py", line 531, in open
shopify_app     |     response = meth(req, response)
shopify_app     |   File "/usr/local/lib/python3.7/urllib/request.py", line 641, in http_response
shopify_app     |     'http', request, response, code, msg, hdrs)
shopify_app     |   File "/usr/local/lib/python3.7/urllib/request.py", line 569, in error
shopify_app     |     return self._call_chain(*args)
shopify_app     |   File "/usr/local/lib/python3.7/urllib/request.py", line 503, in _call_chain
shopify_app     |     result = func(*args)
shopify_app     |   File "/usr/local/lib/python3.7/urllib/request.py", line 649, in http_error_default
shopify_app     |     raise HTTPError(req.full_url, code, msg, hdrs, fp)
shopify_app     | urllib.error.HTTPError: HTTP Error 401: Unauthorized
shopify_app     | 
shopify_app     | During handling of the above exception, another exception occurred:
shopify_app     | 
shopify_app     | Traceback (most recent call last):
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/app.py", line 2463, in __call__
shopify_app     |     return self.wsgi_app(environ, start_response)
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/app.py", line 2449, in wsgi_app
shopify_app     |     response = self.handle_exception(e)
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/app.py", line 1866, in handle_exception
shopify_app     |     reraise(exc_type, exc_value, tb)
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/_compat.py", line 39, in reraise
shopify_app     |     raise value
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/app.py", line 2446, in wsgi_app
shopify_app     |     response = self.full_dispatch_request()
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/app.py", line 1951, in full_dispatch_request
shopify_app     |     rv = self.handle_user_exception(e)
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/app.py", line 1820, in handle_user_exception
shopify_app     |     reraise(exc_type, exc_value, tb)
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/_compat.py", line 39, in reraise
shopify_app     |     raise value
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/app.py", line 1949, in full_dispatch_request
shopify_app     |     rv = self.dispatch_request()
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/flask/app.py", line 1935, in dispatch_request
shopify_app     |     return self.view_functions[rule.endpoint](**req.view_args)
shopify_app     |   File "./shopify_app/shopify_bp/decorators.py", line 51, in decorated_function
shopify_app     |     return f(*args, **kwargs)
shopify_app     |   File "./shopify_app/shopify_bp/views.py", line 196, in settings_post
shopify_app     |     sm.upsert_script_tag(script_tag_url)
shopify_app     |   File "./fk/api/shopify/Shopify.py", line 159, in upsert_script_tag
shopify_app     |     script = st.save()
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/pyactiveresource/activeresource.py", line 824, in save
shopify_app     |     data=self.encode())
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/pyactiveresource/connection.py", line 364, in post
shopify_app     |     return self._open('POST', path, headers=headers, data=data)
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/shopify/base.py", line 23, in _open
shopify_app     |     self.response = super(ShopifyConnection, self)._open(*args, **kwargs)
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/pyactiveresource/connection.py", line 288, in _open
shopify_app     |     http_response = self._handle_error(err)
shopify_app     |   File "/usr/local/lib/python3.7/site-packages/pyactiveresource/connection.py", line 404, in _handle_error
shopify_app     |     raise UnauthorizedAccess(err)
shopify_app     | pyactiveresource.connection.UnauthorizedAccess: Response(code=401, body="b'{"errors":"[API] Invalid API key or access token (unrecognized login or wrong password)"}'", headers={'Date': 'Sun, 15 Sep 2019 22:17:42 GMT', 'Content-Type': 'application/json; charset=utf-8', 'Transfer-Encoding': 'chunked', 'Connection': 'close', 'Set-Cookie': '__cfduid=da23de8c***************0e609367701568585861; expires=Mon, 14-Sep-20 22:17:41 GMT; path=/; domain=.myshopify.com; HttpOnly', 'X-Sorting-Hat-PodId': '34', 'X-Sorting-Hat-ShopId': '5263130659', 'Referrer-Policy': 'origin-when-cross-origin', 'X-Frame-Options': 'DENY', 'X-ShopId': '5263130659', 'X-ShardId': '34', 'WWW-Authenticate': 'Basic Realm="Shopify API Authentication"', 'Strict-Transport-Security': 'max-age=7889238', 'X-Request-Id': 'cfb8e7c***************c-740f4136eced', 'X-Shopify-Stage': 'production', 'Content-Security-Policy': "default-src 'self' data: blob: 'unsafe-inline' 'unsafe-eval' https://* shopify-pos://*; block-all-mixed-content; child-src 'self' https://* shopify-pos://*; connect-src 'self' wss://* https://*; frame-ancestors 'none'; img-src 'self' data: blob: https:; script-src https://cdn.shopify.com https://cdn.shopify.cn https://checkout.shopifycs.com https://js-agent.newrelic.com https://bam.nr-data.net https://dme0ih8comzn4.cloudfront.net https://api.stripe.com https://mpsnare.iesnare.com https://appcenter.intuit.com https://www.paypal.com https://js.braintreegateway.com https://c.paypal.com https://maps.googleapis.com https://www.google-analytics.com https://v.shopify.com https://widget.intercom.io https://js.intercomcdn.com 'self' 'unsafe-inline' 'unsafe-eval'; upgrade-insecure-requests; report-uri /csp-report?source%5Baction%5D=create&source%5Bapp%5D=Shopify&source%5Bcontroller%5D=admin%2Fscript_tags&source%5Bsection%5D=admin_api&source%5Buuid%5D=cfb8e7c6-0c90-4507-a9bc-740f4136eced", 'X-Content-Type-Options': 'nosniff', 'X-Download-Options': 'noopen', 'X-Permitted-Cross-Domain-Policies': 'none', 'X-XSS-Protection': '1; mode=block; report=/xss-report?source%5Baction%5D=create&source%5Bapp%5D=Shopify&source%5Bcontroller%5D=admin%2Fscript_tags&source%5Bsection%5D=admin_api&source%5Buuid%5D=cfb8e7c***************c-740f4136eced', 'X-Dc': 'gcp-us-central1,gcp-us-central1', 'set-cookie': '__cfduid=da23de8c***************0e609367701568585861; expires=Mon, 14-Sep-20 22:17:41 GMT; path=/; domain=.myshopify.com; HttpOnly', 'Expect-CT': 'max-age=604800, report-uri="https://report-uri.cloudflare.com/cdn-cgi/beacon/expect-ct"', 'Server': 'cloudflare', 'CF-RAY': '51**********dfdf-FRA'}, msg="Unauthorized")

 

So how can I debug this? Is there some way I can get more information about why it was unauthorized?

0 Likes
Trailblazer
274 60 55
Hi, Devdude,
 
This is Evita from On The Map. 
 
401 error is showing up because you have provided the wrong API key or access token. For this case, it's more likely that the access token is wrong.
 
Make sure you have token saved in the session.
 
Best, 
Evita
 
On The Map Marketing | Developing custom Shopify Sites & Apps is our thing

- Install our latest app Accessibly - Makes your store accessible for everyone, helps to avoid fines
- Inc 5000 | Shopify Parners | 20+ stores launched | 300+ active clients
- Need help with your Shopify store? Reach out to us!
1 Like

Success.

Tourist
6 1 1

I discovered this later. I was incorrectly using the return code instead of actually requesting the permanent offline access token. For anyone struggling with this, the function you want to get that token given request that contains "code" is like this:

 

 

    def request_access_token(self, request):
        print(f"Requesting session token for: {self.request.args}")
        token=None
        try:
            # Here self.session is a shopify session made earlier
            token = self.session.request_token(request.args)
        except Exception as e:
            print(f" + Failed with {e}")
        return token

And the code to insert a new script tag once you have token looks like this:

 

    def upsert_script_tag(self, src):
        script_reference={"event": "onload", "src": f"{src}"}
        print(f"UPSERTING SCRIPT TAG WITH '{script_reference}'")
        st=shopify.ScriptTag(script_reference)
        ret = st.save()
        if st.errors:
            print(f"ERROR: {st.errors.full_messages()}")
        print(f" + Return was :{ret}")

This works!

 

Thanks for your help.

 

1 Like