我是 Shopify 新手,我正在尝试帮助朋友处理他们的网站。我目前收到以下错误。
- 应用程序必须设置安全标头以防止点击劫持。
单击“添加应用程序”后,您的应用程序不会立即请求在商店中安装。应用程序首次安装到商店时以及删除后重新安装时必须向商店请求访问权限。在安装或重新安装期间,我们预计 OAuth 将在 https://cambridgetestshop.myshopify.com/admin/oauth/request_grant 启动,但被重定向到 https://app-staging.hashgifted.com/。在我们的开发者文档中了解有关身份验证的更多信息- 应用程序必须验证 Shopify 请求的真实性。
单击“添加应用程序”后,您的应用程序不会立即请求在商店中安装。应用程序首次安装到商店时以及删除后重新安装时必须向商店请求访问权限。在安装或重新安装期间,我们预计 OAuth 将在 https://cambridgetestshop.myshopify.com/admin/oauth/request_grant 启动,但被重定向到 https://app-staging.hashgifted.com/。在我们的开发者文档中了解有关身份验证的更多信息
我们正在使用 Yarn 中内置的 React。
您似乎没有遵循有关身份验证和应用程序安装过程的文档。
当您使用节点时,我建议您看一下这个项目https://github.com/Shopify/shopify-app-node
特别是对于身份验证中间件,这是一部分
import { Shopify } from "@shopify/shopify-api";
import topLevelAuthRedirect from "../helpers/top-level-auth-redirect.js";
export default function applyAuthMiddleware(app) {
app.get("/auth", async (req, res) => {
if (!req.signedCookies[app.get("top-level-oauth-cookie")]) {
return res.redirect(
`/auth/toplevel?${new URLSearchParams(req.query).toString()}`
);
}
const redirectUrl = await Shopify.Auth.beginAuth(
req,
res,
req.query.shop,
"/auth/callback",
app.get("use-online-tokens")
);
res.redirect(redirectUrl);
});
app.get("/auth/toplevel", (req, res) => {
res.cookie(app.get("top-level-oauth-cookie"), "1", {
signed: true,
httpOnly: true,
sameSite: "strict",
});
res.set("Content-Type", "text/html");
res.send(
topLevelAuthRedirect({
apiKey: Shopify.Context.API_KEY,
hostName: Shopify.Context.HOST_NAME,
host: req.query.host,
query: req.query,
})
);
});
app.get("/auth/callback", async (req, res) => {
try {
const session = await Shopify.Auth.validateAuthCallback(
req,
res,
req.query
);
const host = req.query.host;
app.set(
"active-shopify-shops",
Object.assign(app.get("active-shopify-shops"), {
[session.shop]: session.scope,
})
);
const response = await Shopify.Webhooks.Registry.register({
shop: session.shop,
accessToken: session.accessToken,
topic: "APP_UNINSTALLED",
path: "/webhooks",
});
if (!response["APP_UNINSTALLED"].success) {
console.log(
`Failed to register APP_UNINSTALLED webhook: ${response.result}`
);
}
// Redirect to app with shop parameter upon auth
res.redirect(`/?shop=${session.shop}&host=${host}`);
} catch (e) {
switch (true) {
case e instanceof Shopify.Errors.InvalidOAuthError:
res.status(400);
res.send(e.message);
break;
case e instanceof Shopify.Errors.CookieNotFound:
case e instanceof Shopify.Errors.SessionNotFound:
// This is likely because the OAuth session cookie expired before the merchant approved the request
res.redirect(`/auth?shop=${req.query.shop}`);
break;
default:
res.status(500);
res.send(e.message);
break;
}
}
});
}