Development discussions around Shopify APIs
To continue receiving payouts, you need to secure your account by turning on two-step authentication. If two-step authentication is not turned on your payouts will be paused. Learn more
With the strong focus on privacy, browsers have recently started phasing out support for the 3rd party cookie. This has caused issues for embedded apps which until now have required the use of 3rd party cookies.
Our new App Bridge auth beta introduces “session tokens” to empower developers to create faster, more flexible, and more compatible apps. Session token based auth does not depend on cookies and instead relies on a Shopify-generated token that your app needs to send with every request.
In order to get started with App Bridge auth, or migrate your current app from traditional, cookie-based authentication, you can follow the guide in our developer documentation.
Questions about App Bridge auth or session tokens? Post them in this board or reach out to support through your partner dashboard.
Liam | Developer Advocate @ Shopify
- Was my reply helpful? Click Like to let me know!
- Was your question answered? Mark it as an Accepted Solution
- To learn more visit Shopify.dev or the Shopify Web Design and Development Blog
You are not loading an authenticated session inside the iframe. Shopify is hoisting you into an iframe but it cannot hoist your session in there, without using cookies. Anyway, if you are happy and your App works, why worry. If you are actually leaking and not secure, someone will hack you and or inform you and you'll fix things up later. I am sure you are fine though. It is tough to screw up and get away with it.
I agree with HunkyBill here. It may also be worth hearing about how you've accomplished this.. worst case we can poke some security holes in your setup, best case we can learn something new.
Absolutely. If I have any concern it is that I am doing something insecure. But I think I have thought it all out pretty well. Feel free to pick it apart. I actually wanted to work in PHP for multiple reasons (main one being I tried getting started with the tutorials out there for Ruby with Shopify's gem and I ended up with a 96MB app that just authenticated (and barely did that even) before I even started coding out the actual functionality of the app). The only PHP app I found was outdated and did not work with Shopify's current Oauth and API, so I wrote my own bare-bones PHP app and put it on GitHub. It includes all steps to get it up and running easily as well as the added security measures I spoke about in my first comment on here. Check it out here and let me know what you think or if there are any flaws you find in it: https://github.com/XenithTech/php-shopify-app-skeleton
Also, I have not gone through and commented anything yet so feel free to ask me either on here or GitHub about what any of it is doing. But it should be mostly straightforward.
I agress on the bloat. I used Sinatra for years to avoid it. But you have to also remember this. That bloat buys you code battle-tested and proven, code you eventually need, and code you cannot hope to replicate yourself. Rare is the person that writes an App these days without some kind of framework. So while it is true you get little out of the box for your initial foray into Rails, for just a few extra minutes of work, you could put into play a useful API call pattern, that is battle-tested for the same 96MB. Good luck rolling your own there. Also PHP? Hardcore hanging on to yesteryear! It is still a thing for sure, but you won't stumble across anything nice for Shopify. Stick with Ruby, or Python (or even gasp, Node) for the most current community efforts. And don't discount the fact that Shopify's gems for App and API are always going to expose cutting edge before anything else by default. PHP will almost always be your long distant cousin on a dial-up modem with electricity only 4 hours a day, from a bicycle feeding a battery when the sun does not shine.
I definitely get what you are saying about having the pre built out API but the Admin API for Shopify is very well documented and very straightforward as far as the calls being made. The wrapper API doesn't seem to give me much advantage overall. As I go and need to make calls I am going to be building on this PDP bare-bones app to have a similar built in API structure of reusable functions but I also gain a lot out of doing this by hand in way of learning. Now the choice of PHP is for a whole different discussion. I would argue (as an active professional web developer) though that PHP is actually by no means a dying language. The new versions of PHP have fixed a lot of old performance concerns and between just WordPress and Magento alone, there are thousands upon thousands of sites written in PHP that will likely never be rewritten to another language. That being said, I am familiar with Node and may give that a shot at some point.
What is this wrapper API you speak of? I am not familiar with referring to anything as a wrapper API
Hi @rezaansyed - where are the docs for `userAuthenticatedFetch` ? I only see `authenticatedFetch` mentioned. Just plugging it in the same way throws errors.. is this tested at all??
@releod sorry I had meant to say `authenticatedFetch`. This is the link showing the example for `authenticatedFetch`: https://shopify.dev/tools/app-bridge/authentication#frontend-changes
@HunkyBill Wrapper API refers to an API that wraps around another one. In other words, a class/object that contains functions taking in arguments to make calls to the REST API and returns an object native to that language. Something like `$products = $Store->getProduct('29249471');`.
Thanks @Martin_Caum I get it!
Kind of a precocious thing to say though, as almost everyone in conversation just makes API calls. Hence why it can be a head-scratcher for a second. You did what?
If you used PHP, sure it looks different than Ruby or Javascript code would, because they are different languages with unique syntaxes. I guess the years have dulled my ability to just let it go. Of course ActiveResource is the common Ruby wrapper around making Rest API calls. I would never refer to it as such, as a Wrapper API, but that is succinct in case it were up for debate with someone, sure!
Hi!
We're running into an issue where app.getState() and getSessionToken(app) do not resolve to anything - no results or errors are return. authenticatedFetch has the same issue but that is because it is uses getSessionToken(app). We can can confirm that the app bridge is loaded and app exists.
Here is the code:
import React, { useContext } from 'react';
import ReactDOM from 'react-dom';
import { createBrowserHistory } from 'history';
import { Router, Route, Switch } from 'react-router-dom';
import { Context, Provider } from '@shopify/app-bridge-react';
import { authenticatedFetch, getSessionToken } from '@shopify/app-bridge-utils';
import COMPONENT from 'app/component.jsx';
let component = COMPONENT;
let apiKey = 'XXXXXXXXXXXX';
let shop = 'YYYYYYYYYYY';
const MyApp = () => {
const app = useContext(Context);
if (app) {
console.log(app)
app.getState()
.then((state) => console.log('state'))
.catch((err) => console.log(err));
getSessionToken(app)
.then((result) => console.log(result))
.catch((err) => console.log(err));
authenticatedFetch(app)('https://www.espn.com/').then(response => console.log(response)).catch((err) => console.log(err))
}
return (
<Router history={createBrowserHistory()}>
<Switch>
<Route path='/' component={component} />
</Switch>
</Router>
);
};
ReactDOM.render(
<Provider config={{ apiKey: apiKey, shopOrigin: shop }}>
<MyApp />
</Provider>
, document.getElementById('root'));
The app variable looks like this:
What are we doing wrong? We just want to grab the session token to replace the cookies for authenticated AJAX calls.
I think this thread needs to be closed and have more specific new threads dedicated to specific problems. Just my 0.02.
HunkyBill Agreed, I just moved the question to this new thread. Please let me know if you have any ideas there.
@Liam @rezaansyed @Michael_Ragalie We have an issue where app.getState() and getSessionToken(app) do not resolve - no results or errors are returned. Do you have any idea why that may be? We created a thread here
For those trying to figure out how to implement this having built your app using the Node + Koa + Next + Apollo tutorial featured on Shopify:
For the server-side. You will need to remove the Koa Auth package and write your own oauth method. You can simply take the koa auth package and strip out the parts that do a bunch of cookie things before it's oauth process begins.
You'll want to perform the JWT verification on your /graphql endpoint for your graphql proxy. You will also need to store the store's access token you get during the oauth callback in a database and retrieve that access token to make the call to graphQL.
The basic flow:
Some other things to be aware of: You may want to perform a "check if this is a known shop" anytime a shop accesses your app. You perform a query to see if they have any valid access tokens in your database. If they're not a known shop, pass them to the oauth start process.
Regarding "How do I get the shop parameter into my frontend?" You don't have to pass it via a cookie. Anytime a merchant accesses your app, a shop query parameter is passed with it. If you are creating links within your frontend, make sure you are also appending the shop query parameter to the end of your links using that query parameter.
Hey Michael! I have created a complete app using NodeJs, React, and MongoDB. You can check that out on:
https://github.com/MathewsJoseph25/create-shopify-app
I was playing around with the JWT tokens issued by Shopify. This seems like a great solution to get around the recent 3rd party cookies issues. However, I do have a few questions.
Can you please provide some clarification on this?
@dsingh JWT is separate from the access token. You generate the access token, online or offline, during your oauth callback and handle storing it in your db depending on if it's online or offline. You always should be storing the myshopify domain imo. If you are doing offline tokens, match it up with the access token via the domain name and make your shop domain column in your db a unique constraint. Basically just ignore the sub field from jwt if offline. The sub is always the user id of user who that jwt token is for.
@KisukaKiza My concern is security related here. i.e. Are the shopify domains recycled? or changed? If answer to either of those questions is yes then it'll break the authentication process if we're matching based on shopify domain.
User | RANK |
---|---|
5 | |
5 | |
5 | |
5 | |
4 |
Learn these 5 things I had to learn the hard way with starting and running my own business
By Kitana Jan 27, 2023Would you love to unleash the unbridled power of the Google Shopping Channel into your sho...
By Gabe Jan 6, 2023How can you turn a hobby into a career? That’s what Emmanuel did while working as a wa...
By Skye Dec 30, 2022