# Interacting with Shopify Admin Once you [set up your backend](/docs/api/shopify-app-remix#shopify-app), you can use the [`authenticate.admin` function](/docs/api/shopify-app-remix/authenticate/admin) to integrate your app with Shopify Admin. This function works for both embedded and non-embedded apps, and ensures the app is installed on the current store. It returns a context with functions to enable loaders and actions to respond to any requests made by or in Shopify Admin. This page goes over the basics of authenticating those requests, and some of the things you can do with it, like querying the Admin API. ## Authenticating requests To authenticate admin requests you can call `authenticate.admin(request)` in a loader or an action. If there's a session for this user, then this loader will return null. If there's no session for the user, then the loader will throw the appropriate redirect Response. > Tip: If you are authenticating more than one route, then we recommend using [Remix layout routes](https://remix.run/docs/en/1.18.1/file-conventions/routes-files#layout-routes) to automatically authenticate them. ### Authenticating requests ```tsx import {LoaderFunction, ActionFunction} from '@remix-run/node'; import {authenticate} from '~/shopify.server'; export const loader: LoaderFunction = async ({request}) => { await authenticate.admin(request); // App logic return null; }; export const action: ActionFunction = async ({request}) => { await authenticate.admin(request); // App logic return null; }; ``` ## Headers The OAuth process can't happen inside the admin iframe, and this package is capable of detecting that scenario and properly redirecting using the [Remix `ErrorBoundary`](https://remix.run/docs/en/main/guides/errors) export to set the correct headers for App Bridge. Use the abstractions provided by this package in your authenticated routes, to automatically set up the error and headers boundaries to redirect outside the iframe when needed. > Tip: You can also add this to a [Remix layout](https://remix.run/docs/en/main/file-conventions/route-files-v2) if you want to authenticate more than one route, but make sure to call the Shopify boundary methods whenever you need to add your own exports. ### Configure header boundaries ```tsx import {useRouteError} from '@remix-run/react'; import {boundary} from '@shopify/shopify-app-remix'; export function ErrorBoundary() { return boundary.error(useRouteError()); } export const headers = (headersArgs) => { return boundary.headers(headersArgs); }; ``` ## Authenticating cross-origin admin requests If your Remix server is authenticating an admin extension, then a request from the extension to Remix will be cross-origin. Here `authenticate.admin` provides a `cors` function to add the required cross-origin headers. ### Add cross-origin headers ```tsx import {json, LoaderFunction} from '@remix-run/node'; import {authenticate} from '~/shopify.server'; export const loader: LoaderFunction = async ({request}) => { const {cors} = await authenticate.admin(request); // App logic return cors(json({my: 'data'})); }; ``` ## Using the GraphQL API Once a request is authenticated, `authenticate.admin` will return an `admin` object that contains a GraphQL client that can interact with the [GraphQL Admin API](/docs/api/admin-graphql). ### Make GraphQL requests ```tsx import {ActionFunction, json} from '@remix-run/node'; import {authenticate} from '../shopify.server'; export const action: ActionFunction = async ({request}) => { const {admin} = await authenticate.admin(request); const response = await admin.graphql( `#graphql mutation populateProduct($input: ProductInput!) { productCreate(input: $input) { product { id } } }`, { variables: { input: { title: 'New product', variants: [{price: 100}], }, }, }, ); const parsedResponse = await response.json(); return json({data: parsedResponse.data}); }; ``` - [](/docs/api/shopify-app-remix/guide-graphql-types): Typing GraphQL operations ## Using the REST API (Deprecated) **Shopify is [all-in on graphql](https://www.shopify.com/ca/partners/blog/all-in-on-graphql). In the next major release, the REST API will be removed from the `@shopify/shopify-app-remix` package.If the `removeRest` [future flag](/docs/api/shopify-app-remix/v3/guide-future-flags) is true, then the REST API will not be available.** Once a request is authenticated, `authenticate.admin` will return an `admin` object that contains a REST client that can interact with the [REST Admin API](/docs/api/admin-rest). You can also import a set of resource classes from the `@shopify/shopify-api` package, which is included in `@shopify/shopify-app-remix`. These classes map to the individual REST endpoints, and will be returned under `admin.rest.resources`. ### Interacting with the REST API ```tsx import {shopifyApp} from '@shopify/shopify-app-remix/server'; import {restResources} from '@shopify/shopify-api/rest/admin/2023-07'; const shopify = shopifyApp({ restResources, // ...etc }); export const authenticate = shopify.authenticate; ``` ```tsx import {LoaderFunction, json} from '@remix-run/node'; import {useRouteError} from '@remix-run/react'; import {authenticate} from '~/shopify.server'; export const loader: LoaderFunction = async ({request}) => { const {admin, session} = await authenticate.admin(request); // Use REST resources const data = await admin.rest.resources.Product.count({session}); // Or use the REST client const response = await admin.rest.get({path: 'products/count'}); const data = response.body; return json({productCount: data.count}); }; ``` ## Resources ## References - [AppProvider](https://shopify.dev/docs/api/shopify-app-remix/v1/entrypoints/appprovider.txt): Sets up the Polaris `AppProvider` and injects the App Bridge script. This component extends the [`AppProvider`](https://polaris.shopify.com/components/utilities/app-provider) component from Polaris, and accepts all of its props except for `linkComponent`, which is overridden to use the Remix `Link` component. - [Admin](https://shopify.dev/docs/api/shopify-app-remix/v1/authenticate/admin.txt): Contains functions for authenticating and interacting with the Admin API. This function can handle requests for apps embedded in the Admin, Admin extensions, or non-embedded apps. - [Billing](https://shopify.dev/docs/api/shopify-app-remix/v1/apis/billing.txt): Contains function used to bill merchants for your app. This object is returned on authenticated Admin requests. - [App proxy](https://shopify.dev/docs/api/shopify-app-remix/v1/authenticate/public/app-proxy.txt): The `authenticate.public.appProxy` function validates app proxy requests made by Shopify, and returns a context to enable querying Shopify APIs. - [Checkout](https://shopify.dev/docs/api/shopify-app-remix/v1/authenticate/public/checkout.txt): The `authenticate.public.checkout` function ensures that checkout extension requests are coming from Shopify, and returns helpers to respond with the correct headers. - [Webhook](https://shopify.dev/docs/api/shopify-app-remix/v1/authenticate/webhook.txt): Contains functions for verifying Shopify webhooks. - [Admin API](https://shopify.dev/docs/api/shopify-app-remix/v1/apis/admin-api.txt): Contains objects used to interact with the Admin API. This object is returned as part of different contexts, such as [`admin`](/docs/api/shopify-app-remix/authenticate/admin), [`unauthenticated.admin`](/docs/api/shopify-app-remix/unauthenticated/unauthenticated-admin), and [`webhook`](/docs/api/shopify-app-remix/authenticate/webhook). - [Storefront API](https://shopify.dev/docs/api/shopify-app-remix/v1/apis/storefront-api.txt): Contains objects used to interact with the Storefront API. This object is returned as part of different contexts, such as [`appProxy`](/docs/api/shopify-app-remix/authenticate/public/app-proxy), and [`unauthenticated.storefront`](/docs/api/shopify-app-remix/unauthenticated/unauthenticated-storefront). - [shopifyApp](https://shopify.dev/docs/api/shopify-app-remix/v1/entrypoints/shopifyapp.txt): Returns a set of functions that can be used by the app's backend to be able to respond to all Shopify requests. The shape of the returned object changes depending on the value of `distribution`. If it is `AppDistribution.ShopifyAdmin`, then only `ShopifyAppBase` objects are returned, otherwise `ShopifyAppLogin` objects are included. - [Unauthenticated admin](https://shopify.dev/docs/api/shopify-app-remix/v1/unauthenticated/unauthenticated-admin.txt): Allows interacting with the Admin API on requests that didn't come from Shopify. > Caution: This should only be used for Requests that do not originate from Shopify. > You must do your own authentication before using this method. >This function doesn't perform **any** validation and shouldn't rely on unvalidated user input. - [Unauthenticated storefront](https://shopify.dev/docs/api/shopify-app-remix/v1/unauthenticated/unauthenticated-storefront.txt): Allows interacting with the Storefront API on requests that didn't come from Shopify. > Caution: This should only be used for Requests that do not originate from Shopify. > You must do your own authentication before using this method. >This function doesn't perform **any** validation and shouldn't rely on unvalidated user input. - [AppProvider](https://shopify.dev/docs/api/shopify-app-remix/v2/entrypoints/appprovider.txt): Sets up the Polaris `AppProvider` and injects the App Bridge script. This component extends the [`AppProvider`](https://polaris.shopify.com/components/utilities/app-provider) component from Polaris, and accepts all of its props except for `linkComponent`, which is overridden to use the Remix `Link` component. - [AppProxyForm](https://shopify.dev/docs/api/shopify-app-remix/v2/app-proxy-components/appproxyform.txt): Sets up a Remix `