docs: improvements to API reference intro sections (#9397)
- Improve intro sections of API reference to utilize divided columns - Improve the content of the intro sections - Add a new Workflows section to explain the workflows badge and how to use it - Fixes to headings and add anchor for copying the link to a section - Fixes responsiveness of intro sections on mobile devices - Other: fix loading not showing when a sidebar category is opened. Closes DOCS-932, DOCS-934, DOCS-937 Preview: https://api-reference-v2-git-docs-api-ref-intro-fixes-medusajs.vercel.app/v2/api/store
This commit is contained in:
@@ -1,9 +1,23 @@
|
|||||||
import { Feedback, CodeTabs, CodeTab } from "docs-ui"
|
import { Feedback, CodeTabs, CodeTab } from "docs-ui"
|
||||||
import SectionContainer from "@/components/Section/Container"
|
import SectionContainer from "@/components/Section/Container"
|
||||||
|
import DividedMarkdownLayout from "@/layouts/DividedMarkdown"
|
||||||
|
import {
|
||||||
|
DividedMarkdownContent,
|
||||||
|
DividedMarkdownCode
|
||||||
|
} from "@/layouts/DividedMarkdown/Sections"
|
||||||
|
import Section from "@/components/Section"
|
||||||
import formatReportLink from "@/utils/format-report-link"
|
import formatReportLink from "@/utils/format-report-link"
|
||||||
|
|
||||||
|
import ClientLibraries from "./client-libraries.mdx"
|
||||||
|
|
||||||
|
<Section checkActiveOnScroll>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
<Note type="warning" title="Production Warning">
|
<Note type="warning" title="Production Warning">
|
||||||
|
|
||||||
Medusa v2.0 is in development and not suitable for production
|
Medusa v2.0 is in development and not suitable for production
|
||||||
@@ -12,7 +26,7 @@ change, so please use it with caution.
|
|||||||
|
|
||||||
</Note>
|
</Note>
|
||||||
|
|
||||||
This API reference includes Medusa's Admin APIs, which are REST APIs exposed by the Medusa application. They are used to perform admin functionalities or create an admin dashboard to access and manipulate your commerce store's data.
|
This API reference includes Medusa v2's Admin APIs, which are REST APIs exposed by the Medusa application. They are used to perform admin functionalities or create an admin dashboard to access and manipulate your commerce store's data.
|
||||||
|
|
||||||
All API Routes are prefixed with `/admin`. So, during development, the API Routes will be available under the path `http://localhost:9000/admin`. For production, replace `http://localhost:9000` with your Medusa application URL.
|
All API Routes are prefixed with `/admin`. So, during development, the API Routes will be available under the path `http://localhost:9000/admin`. For production, replace `http://localhost:9000` with your Medusa application URL.
|
||||||
|
|
||||||
@@ -28,25 +42,49 @@ All API Routes are prefixed with `/admin`. So, during development, the API Route
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
<ClientLibraries />
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Authentication
|
## Authentication
|
||||||
|
|
||||||
There are three ways to send authenticated requests to the Medusa server: Using a JWT token in a bearer authorization header, using an admin user's API token, or using a cookie session ID.
|
There are three ways to send authenticated requests to the Medusa server: Using a JWT token in a bearer authorization header, using an admin user's API token, or using a cookie session ID.
|
||||||
|
|
||||||
### Bearer Authorization with JWT Tokens
|
### 1. Bearer Authorization with JWT Tokens
|
||||||
|
|
||||||
Use a JWT token in a request's bearer authorization header to send authenticated requests. Authentication state is managed by the client, which is ideal for Jamstack applications and mobile applications.
|
Use a JWT token in a request's bearer authorization header to send authenticated requests. Authentication state is managed by the client, which is ideal for Jamstack applications and mobile applications.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### How to Obtain the JWT Token
|
#### How to Obtain the JWT Token
|
||||||
|
|
||||||
JWT tokens are obtained by sending a request to the authentication route passing it the user's email and password in the request body.
|
To obtain a JWT token, send a request to the [authentication route](#auth_postactor_typeauth_provider) passing it the user's email and password in the request body.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Obtain JWT token"
|
||||||
curl -X POST '{backend_url}/auth/user/emailpass' \
|
curl -X POST '{backend_url}/auth/user/emailpass' \
|
||||||
-H 'Content-Type: application/json' \
|
-H 'Content-Type: application/json' \
|
||||||
--data-raw '{
|
--data-raw '{
|
||||||
@@ -55,61 +93,122 @@ curl -X POST '{backend_url}/auth/user/emailpass' \
|
|||||||
}'
|
}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
If authenticated successfully, an object is returned in the response with the property `token` being the JWT token.
|
If authenticated successfully, an object is returned in the response with the property `token` being the JWT token.
|
||||||
|
|
||||||
Learn more about the authentication route [here](#auth_postactor_typeauth_provider)
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```json title="Example response"
|
||||||
|
{
|
||||||
|
"token": "123..."
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### How to Use the JWT Token
|
#### How to Use the JWT Token
|
||||||
|
|
||||||
Pass the JWT token in the authorization bearer header:
|
To use the JWT token, pass it in the authorization bearer header.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Use JWT token"
|
||||||
Authorization: Bearer {jwt_token}
|
Authorization: Bearer {jwt_token}
|
||||||
```
|
```
|
||||||
|
|
||||||
---
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
### API Token
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
|
### 2. API Token
|
||||||
|
|
||||||
Use a user's API Token to send authenticated requests.
|
Use a user's API Token to send authenticated requests.
|
||||||
|
|
||||||
<Note>
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
This authentication method relies on using another authentication method first, as you must be an authenticated user to create an API token.
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</Note>
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### How to Create an API Token for a User
|
#### How to Create an API Token for a User
|
||||||
|
|
||||||
Use the [Create API Key API Route](#api-keys_postapikeys) to create an API token:
|
Use the [Create API Key API Route](#api-keys_postapikeys) to create an API token.
|
||||||
|
|
||||||
```bash
|
<Note>
|
||||||
curl --location 'localhost:9000/admin/api-keys' \
|
|
||||||
--header 'Content-Type: application/json' \
|
You must be an authenticated user to create an API token.
|
||||||
--header 'Authorization: Bearer {jwt_token}' \
|
|
||||||
|
</Note>
|
||||||
|
|
||||||
|
An `api_key` object is returned in the response. You need its `token` property.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Create API token"
|
||||||
|
curl -X POST 'localhost:9000/admin/api-keys' \
|
||||||
|
-H 'Content-Type: application/json' \
|
||||||
|
-H 'Authorization: Bearer {jwt_token}' \
|
||||||
--data '{
|
--data '{
|
||||||
"title": "my token",
|
"title": "my token",
|
||||||
"type": "secret"
|
"type": "secret"
|
||||||
}'
|
}'
|
||||||
```
|
```
|
||||||
|
|
||||||
{/* TODO add a link to the API key object */}
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
An `api_key` object is returned in the response. You need its `token` property.
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### How to Use the API Token
|
#### How to Use the API Token
|
||||||
|
|
||||||
|
|
||||||
The API token can be used by providing it in a basic authorization header:
|
Use the API token by passing it in a basic authorization header.
|
||||||
|
|
||||||
```bash
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Use API token"
|
||||||
Authorization: Basic {api_key_token}
|
Authorization: Basic {api_key_token}
|
||||||
```
|
```
|
||||||
|
|
||||||
---
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
### Cookie Session ID
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
|
### 3. Cookie Session ID
|
||||||
|
|
||||||
When you authenticate a user and create a cookie session ID for them, the cookie session ID is passed automatically when sending the request from the browser, or with tools like Postman.
|
When you authenticate a user and create a cookie session ID for them, the cookie session ID is passed automatically when sending the request from the browser, or with tools like Postman.
|
||||||
|
|
||||||
@@ -117,49 +216,97 @@ When you authenticate a user and create a cookie session ID for them, the cookie
|
|||||||
|
|
||||||
To obtain a cookie session ID, you must have a [JWT token for bearer authentication](#bearer-authorization-with-jwt-tokens).
|
To obtain a cookie session ID, you must have a [JWT token for bearer authentication](#bearer-authorization-with-jwt-tokens).
|
||||||
|
|
||||||
{/* TODO add a link to the session authentication route. */}
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
Then, send a request to the session authentication API route. To view the cookie session ID, pass the `-v` option to the `curl` command:
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
|
Then, send a request to the session authentication API route.
|
||||||
|
|
||||||
|
To view the cookie session ID, pass the `-v` option to the `curl` command.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Obtain cookie session"
|
||||||
curl -v -X POST '{backend_url}/auth/session' \
|
curl -v -X POST '{backend_url}/auth/session' \
|
||||||
--header 'Authorization: Bearer {jwt_token}'
|
--header 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
The headers will be logged in the terminal as well as the response. You
|
The headers will be logged in the terminal as well as the response. You
|
||||||
should find in the headers a Cookie header similar to this:
|
should find in the headers a Cookie header.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
Set-Cookie: connect.sid=s%3A2Bu8BkaP9JUfHu9rG59G16Ma0QZf6Gj1.WT549XqX37PN8n0OecqnMCq798eLjZC5IT7yiDCBHPM;
|
|
||||||
|
```bash title="Logged cookie session"
|
||||||
|
Set-Cookie: connect.sid=s%3A2Bu8B...;
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### How to Use the Cookie Session ID in cURL
|
#### How to Use the Cookie Session ID in cURL
|
||||||
|
|
||||||
Copy the value after `connect.sid` (without the `;` at the end) and pass
|
Copy the value after `connect.sid` (without the `;` at the end) and pass
|
||||||
it as a cookie in subsequent requests as the following:
|
it as a cookie in subsequent requests.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Use cookie session"
|
||||||
curl '{backend_url}/admin/products' \
|
curl '{backend_url}/admin/products' \
|
||||||
-H 'Cookie: connect.sid={sid}'
|
-H 'Cookie: connect.sid={sid}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
Where `{sid}` is the value of `connect.sid` that you copied.
|
Where `{sid}` is the value of `connect.sid` that you copied.
|
||||||
|
|
||||||
#### Including Credentials in the Fetch API
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
If you're sending requests using JavaScript's Fetch API, you must pass the `credentials` option
|
If you're sending requests using JavaScript's Fetch API, you must pass the `credentials` option
|
||||||
with the value `include` to all the requests you're sending. For example:
|
with the value `include` to all the requests you're sending.
|
||||||
|
|
||||||
```js
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```js title="Include credentials in fetch"
|
||||||
fetch(`<BACKEND_URL>/admin/products`, {
|
fetch(`<BACKEND_URL>/admin/products`, {
|
||||||
credentials: "include",
|
credentials: "include",
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -172,20 +319,44 @@ fetch(`<BACKEND_URL>/admin/products`, {
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## HTTP Compression
|
## HTTP Compression
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
If you've enabled HTTP Compression in your Medusa configurations, and you
|
If you've enabled HTTP Compression in your Medusa configurations, and you
|
||||||
want to disable it for some requests, you can pass the `x-no-compression`
|
want to disable it for some requests, you can pass the `x-no-compression`
|
||||||
header in your requests:
|
header in your requests.
|
||||||
|
|
||||||
```bash
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Enable HTTP compression"
|
||||||
x-no-compression: true
|
x-no-compression: true
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -198,24 +369,48 @@ x-no-compression: true
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Select Fields and Relations
|
## Select Fields and Relations
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
Many API Routes accept a `fields` query that allows you to select which fields and relations should be returned in a record.
|
Many API Routes accept a `fields` query that allows you to select which fields and relations should be returned in a record.
|
||||||
Fields and relations are separated by a comma `,`.
|
Fields and relations are separated by a comma `,`.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Select fields"
|
||||||
curl 'localhost:9000/admin/products?fields=title,handle' \
|
curl 'localhost:9000/admin/products?fields=title,handle' \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
This returns only the `title` and `handle` fields of a product.
|
This returns only the `title` and `handle` fields of a product.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Fields Operator
|
### Fields Operator
|
||||||
|
|
||||||
By default, only the selected fields and relations are returned in the response.
|
By default, only the selected fields and relations are returned in the response.
|
||||||
@@ -225,106 +420,182 @@ Before every field or relation, you can pass one of the following operators to c
|
|||||||
- `+`: Add the field to the fields returned by default. For example, `+title` returns the `title` field along with the fields returned by default.
|
- `+`: Add the field to the fields returned by default. For example, `+title` returns the `title` field along with the fields returned by default.
|
||||||
- `-`: Remove the field from the fields returned by default. For example, `-title` removes the `title` field from the fields returned by default.
|
- `-`: Remove the field from the fields returned by default. For example, `-title` removes the `title` field from the fields returned by default.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Select Relations
|
### Select Relations
|
||||||
|
|
||||||
To select a relation, pass to `fields` the relation name prefixed by `*`. For example:
|
To select a relation, pass to `fields` the relation name prefixed by `*`.
|
||||||
|
|
||||||
```bash
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Select relations"
|
||||||
curl 'localhost:9000/admin/products?fields=*variants' \
|
curl 'localhost:9000/admin/products?fields=*variants' \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
This returns the variants of each product.
|
This returns the variants of each product.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Select Fields in a Relation
|
### Select Fields in a Relation
|
||||||
|
|
||||||
The `*` prefix selects all fields of the relation's data model.
|
The `*` prefix selects all fields of the relation's data model.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
To select a specific field, pass a `.<field>` suffix instead of the `*` prefix. For example, `variants.title`.
|
To select a specific field, pass a `.<field>` suffix instead of the `*` prefix. For example, `variants.title`.
|
||||||
|
|
||||||
To specify multiple fields, pass each of the fields with the `<relation>.<field>` format, separated by a comma.
|
To specify multiple fields, pass each of the fields with the `<relation>.<field>` format, separated by a comma.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Select relation's fields"
|
||||||
curl 'localhost:9000/admin/products?fields=variants.title,variants.sku' \
|
curl 'localhost:9000/admin/products?fields=variants.title,variants.sku' \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
This returns the variants of each product, but the variants only have their `id`, `title`, and `sku` fields. The `id` is always included.
|
This returns the variants of each product, but the variants only have their `id`, `title`, and `sku` fields. The `id` is always included.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Query Parameter Types
|
## Query Parameter Types
|
||||||
|
|
||||||
|
|
||||||
This section covers how to pass some common data types as query parameters.
|
This section covers how to pass some common data types as query parameters.
|
||||||
|
|
||||||
|
This is useful if you're sending requests to the API Routes using cURL or Postman.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Strings
|
### Strings
|
||||||
|
|
||||||
|
|
||||||
You can pass a string value in the form of `<parameter_name>=<value>`.
|
You can pass a string value in the form of `<parameter_name>=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="String filter"
|
||||||
```bash
|
|
||||||
curl "http://localhost:9000/admin/products?title=Shirt" \
|
curl "http://localhost:9000/admin/products?title=Shirt" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
If the string has any characters other than letters and numbers, you must
|
If the string has any characters other than letters and numbers, you must
|
||||||
encode them.
|
encode them.
|
||||||
|
|
||||||
|
|
||||||
For example, if the string has spaces, you can encode the space with `+` or
|
For example, if the string has spaces, you can encode the space with `+` or
|
||||||
`%20`:
|
`%20`.
|
||||||
|
|
||||||
|
|
||||||
```bash
|
|
||||||
curl "http://localhost:9000/admin/products?title=Blue%20Shirt" \
|
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
|
||||||
```
|
|
||||||
|
|
||||||
|
|
||||||
You can use tools like [this one](https://www.urlencoder.org/) to learn how
|
You can use tools like [this one](https://www.urlencoder.org/) to learn how
|
||||||
a value can be encoded.
|
a value can be encoded.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Encoded string filter"
|
||||||
|
curl "http://localhost:9000/admin/products?title=Blue%20Shirt" \
|
||||||
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Integers
|
### Integers
|
||||||
|
|
||||||
|
|
||||||
You can pass an integer value in the form of `<parameter_name>=<value>`.
|
You can pass an integer value in the form of `<parameter_name>=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Integer filter"
|
||||||
```bash
|
|
||||||
curl "http://localhost:9000/admin/products?offset=1" \
|
curl "http://localhost:9000/admin/products?offset=1" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Boolean
|
### Boolean
|
||||||
|
|
||||||
|
|
||||||
You can pass a boolean value in the form of `<parameter_name>=<value>`.
|
You can pass a boolean value in the form of `<parameter_name>=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Boolean filter"
|
||||||
```bash
|
|
||||||
curl "http://localhost:9000/admin/products?is_giftcard=true" \
|
curl "http://localhost:9000/admin/products?is_giftcard=true" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Date and DateTime
|
### Date and DateTime
|
||||||
|
|
||||||
@@ -332,28 +603,42 @@ curl "http://localhost:9000/admin/products?is_giftcard=true" \
|
|||||||
You can pass a date value in the form `<parameter_name>=<value>`. The date
|
You can pass a date value in the form `<parameter_name>=<value>`. The date
|
||||||
must be in the format `YYYY-MM-DD`.
|
must be in the format `YYYY-MM-DD`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Date filter"
|
||||||
```bash
|
|
||||||
curl -g "http://localhost:9000/admin/products?created_at[$lt]=2023-02-17" \
|
curl -g "http://localhost:9000/admin/products?created_at[$lt]=2023-02-17" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
You can also pass the time using the format `YYYY-MM-DDTHH:MM:SSZ`. Please
|
You can also pass the time using the format `YYYY-MM-DDTHH:MM:SSZ`. Please
|
||||||
note that the `T` and `Z` here are fixed.
|
note that the `T` and `Z` here are fixed.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Date and time filter"
|
||||||
```bash
|
|
||||||
curl -g "http://localhost:9000/admin/products?created_at[$lt]=2023-02-17T07:22:30Z" \
|
curl -g "http://localhost:9000/admin/products?created_at[$lt]=2023-02-17T07:22:30Z" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Array
|
### Array
|
||||||
|
|
||||||
@@ -362,20 +647,26 @@ Each array value must be passed as a separate query parameter in the form
|
|||||||
`<parameter_name>[]=<value>`. You can also specify the index of each
|
`<parameter_name>[]=<value>`. You can also specify the index of each
|
||||||
parameter in the brackets `<parameter_name>[0]=<value>`.
|
parameter in the brackets `<parameter_name>[0]=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Array filter"
|
||||||
```bash
|
|
||||||
curl -g "http://localhost:9000/admin/products?sales_channel_id[]=sc_01GPGVB42PZ7N3YQEP2WDM7PC7&sales_channel_id[]=sc_234PGVB42PZ7N3YQEP2WDM7PC7" \
|
curl -g "http://localhost:9000/admin/products?sales_channel_id[]=sc_01GPGVB42PZ7N3YQEP2WDM7PC7&sales_channel_id[]=sc_234PGVB42PZ7N3YQEP2WDM7PC7" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
Note that the `-g` parameter passed to `curl` disables errors being thrown
|
Note that the `-g` parameter passed to `curl` disables errors being thrown
|
||||||
for using the brackets. Read more
|
for using the brackets. Read more
|
||||||
[here](https://curl.se/docs/manpage.html#-g).
|
[here](https://curl.se/docs/manpage.html#-g).
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Object
|
### Object
|
||||||
|
|
||||||
@@ -383,15 +674,21 @@ for using the brackets. Read more
|
|||||||
Object parameters must be passed as separate query parameters in the form
|
Object parameters must be passed as separate query parameters in the form
|
||||||
`<parameter_name>[<key>]=<value>`.
|
`<parameter_name>[<key>]=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Object filter"
|
||||||
```bash
|
|
||||||
curl -g "http://localhost:9000/admin/products?created_at[$lt]=2023-02-17&created_at[$gt]=2022-09-17" \
|
curl -g "http://localhost:9000/admin/products?created_at[$lt]=2023-02-17&created_at[$gt]=2022-09-17" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -404,10 +701,16 @@ curl -g "http://localhost:9000/admin/products?created_at[$lt]=2023-02-17&created
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Pagination
|
## Pagination
|
||||||
|
|
||||||
### Query Parameters
|
### Query Parameters
|
||||||
@@ -415,20 +718,35 @@ curl -g "http://localhost:9000/admin/products?created_at[$lt]=2023-02-17&created
|
|||||||
|
|
||||||
In listing API Routes, such as list customers or list products, you can control the pagination using the query parameters `limit` and `offset`.
|
In listing API Routes, such as list customers or list products, you can control the pagination using the query parameters `limit` and `offset`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
`limit` is used to specify the maximum number of items to be returned in the response. `offset` is used to specify how many items to skip before returning the resulting records.
|
`limit` is used to specify the maximum number of items to be returned in the response. `offset` is used to specify how many items to skip before returning the resulting records.
|
||||||
|
|
||||||
|
|
||||||
Use the `offset` query parameter to change between pages. For example, if the limit is `50`, at page `1` the offset should be `0`; at page `2` the offset should be `50`, and so on.
|
Use the `offset` query parameter to change between pages. For example, if the limit is `50`, at page `1` the offset should be `0`; at page `2` the offset should be `50`, and so on.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
```bash
|
```bash title="Pagination query parameters"
|
||||||
curl "http://localhost:9000/admin/products?limit=5" \
|
curl "http://localhost:9000/admin/products?limit=5" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Response Fields
|
### Response Fields
|
||||||
|
|
||||||
@@ -445,6 +763,13 @@ there are three pagination-related fields returned:
|
|||||||
For example, if the `count` is `100` and the `limit` is `50`, divide the
|
For example, if the `count` is `100` and the `limit` is `50`, divide the
|
||||||
`count` by the `limit` to get the number of pages: `100/50 = 2 pages`.
|
`count` by the `limit` to get the number of pages: `100/50 = 2 pages`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Sort Order
|
### Sort Order
|
||||||
|
|
||||||
@@ -452,26 +777,45 @@ For example, if the `count` is `100` and the `limit` is `50`, divide the
|
|||||||
The `order` field (available on API Routes that support pagination) allows you to
|
The `order` field (available on API Routes that support pagination) allows you to
|
||||||
sort the retrieved items by a field of that item.
|
sort the retrieved items by a field of that item.
|
||||||
|
|
||||||
For example, pass the query parameter `order=created_at` to sort products by their `created_at` field:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Ascending sort by a field"
|
||||||
curl "http://localhost:9000/admin/products?order=created_at" \
|
curl "http://localhost:9000/admin/products?order=created_at" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
This sorts the products by their `created_at` field in the ascending order.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
By default, the sort direction is ascending. To change it to
|
By default, the sort direction is ascending. To change it to
|
||||||
descending, pass a dash (`-`) before the field name.
|
descending, pass a dash (`-`) before the field name.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Descending sort by a field"
|
||||||
curl "http://localhost:9000/admin/products?order=-created_at" \
|
curl "http://localhost:9000/admin/products?order=-created_at" \
|
||||||
-H 'Authorization: Bearer {jwt_token}'
|
-H 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
This sorts the products by their `created_at` field in the descending order.
|
This sorts the products by their `created_at` field in the descending order.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -484,4 +828,42 @@ This sorts the products by their `created_at` field in the descending order.
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
</SectionContainer>
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
</SectionContainer>
|
||||||
|
|
||||||
|
<SectionContainer noTopPadding>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
|
## Workflows
|
||||||
|
|
||||||
|
While browsing this reference, you'll find some API routes mention what workflow is used in them.
|
||||||
|
|
||||||
|
If you click on the workflow, you'll view a reference of that workflow, including its hooks.
|
||||||
|
|
||||||
|
This is useful if you want to extend an API route and pass additional data or perform custom actions.
|
||||||
|
|
||||||
|
Refer to [this guide](https://docs.medusajs.com/v2/customization/extend-models/extend-create-product) to find an example of extending an API route.
|
||||||
|
|
||||||
|
<Feedback
|
||||||
|
event="survey_api-ref"
|
||||||
|
extraData={{
|
||||||
|
area: "admin",
|
||||||
|
section: "workflows"
|
||||||
|
}}
|
||||||
|
reportLink={formatReportLink("admin", "Workflows")}
|
||||||
|
pathName="/api/admin"
|
||||||
|
question="Was this section helpful?"
|
||||||
|
vertical={true}
|
||||||
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
</SectionContainer>
|
||||||
|
|
||||||
|
</Section>
|
||||||
@@ -1,20 +1,21 @@
|
|||||||
|
import { H3 } from "docs-ui"
|
||||||
import Space from "@/components/Space"
|
import Space from "@/components/Space"
|
||||||
import DownloadFull from "@/components/DownloadFull"
|
import DownloadFull from "@/components/DownloadFull"
|
||||||
|
|
||||||
### Just Getting Started?
|
<H3 className="!mt-0">Just Getting Started?</H3>
|
||||||
|
|
||||||
Check out the [quickstart guide](https://docs.medusajs.com/create-medusa-app).
|
Check out the [Medusa v2 Documentation](https://docs.medusajs.com/v2).
|
||||||
|
|
||||||
<Space bottom={8} />
|
<Space bottom={8} />
|
||||||
|
|
||||||
<Note type="soon">
|
<Note type="soon">
|
||||||
|
|
||||||
Support for v2 API Routes is coming soon in Medusa JS Client and Medusa React.
|
JavaScript client libraries are coming soon for Medusa v2.
|
||||||
|
|
||||||
</Note>
|
</Note>
|
||||||
|
|
||||||
### Download Full Reference
|
### Download Full Reference
|
||||||
|
|
||||||
Download this reference as an OpenApi YAML file. You can import this file to tools like Postman and start sending requests directly to your Medusa backend.
|
Download this reference as an OpenApi YAML file. You can import this file to tools like Postman and start sending requests directly to your Medusa application.
|
||||||
|
|
||||||
<DownloadFull />
|
<DownloadFull />
|
||||||
@@ -1,10 +1,23 @@
|
|||||||
|
|
||||||
import { Feedback, CodeTabs, CodeTab } from "docs-ui"
|
|
||||||
import SectionContainer from "@/components/Section/Container"
|
import SectionContainer from "@/components/Section/Container"
|
||||||
|
import DividedMarkdownLayout from "@/layouts/DividedMarkdown"
|
||||||
|
import {
|
||||||
|
DividedMarkdownContent,
|
||||||
|
DividedMarkdownCode
|
||||||
|
} from "@/layouts/DividedMarkdown/Sections"
|
||||||
|
import Section from "@/components/Section"
|
||||||
|
import { Feedback, CodeTabs, CodeTab } from "docs-ui"
|
||||||
import formatReportLink from "@/utils/format-report-link"
|
import formatReportLink from "@/utils/format-report-link"
|
||||||
|
|
||||||
|
import ClientLibraries from "./client-libraries.mdx"
|
||||||
|
|
||||||
|
<Section checkActiveOnScroll>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
<Note type="warning" title="Production Warning">
|
<Note type="warning" title="Production Warning">
|
||||||
|
|
||||||
Medusa v2.0 is in development and not suitable for production
|
Medusa v2.0 is in development and not suitable for production
|
||||||
@@ -13,7 +26,7 @@ change, so please use it with caution.
|
|||||||
|
|
||||||
</Note>
|
</Note>
|
||||||
|
|
||||||
This API reference includes Medusa's Store APIs, which are REST APIs exposed by the Medusa application. They are used to create a storefront for your commerce store, such as a webshop or a commerce mobile app.
|
This API reference includes Medusa v2's Store APIs, which are REST APIs exposed by the Medusa application. They are used to create a storefront for your commerce store, such as a webshop or a commerce mobile app.
|
||||||
|
|
||||||
All API Routes are prefixed with `/store`. So, during development, the API Routes will be available under the path `http://localhost:9000/store`. For production, replace `http://localhost:9000` with your Medusa application URL.
|
All API Routes are prefixed with `/store`. So, during development, the API Routes will be available under the path `http://localhost:9000/store`. For production, replace `http://localhost:9000` with your Medusa application URL.
|
||||||
|
|
||||||
@@ -29,25 +42,49 @@ All API Routes are prefixed with `/store`. So, during development, the API Route
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
<ClientLibraries />
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Authentication
|
## Authentication
|
||||||
|
|
||||||
There are two ways to send authenticated requests to the Medusa application: Using a JWT token or using a Cookie Session ID.
|
There are two ways to send authenticated requests to the Medusa application: Using a JWT token or using a Cookie Session ID.
|
||||||
|
|
||||||
### Bearer Authorization with JWT Tokens
|
### 1. Bearer Authorization with JWT Tokens
|
||||||
|
|
||||||
Use a JWT token in a request's bearer authorization header to send authenticated requests. Authentication state is managed by the client, which is ideal for Jamstack applications and mobile applications.
|
Use a JWT token in a request's bearer authorization header to send authenticated requests. Authentication state is managed by the client, which is ideal for Jamstack applications and mobile applications.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### How to Obtain the JWT Token
|
#### How to Obtain the JWT Token
|
||||||
|
|
||||||
JWT tokens are obtained by sending a request to the authentication route passing it the customer's email and password in the request body.
|
To obtain a JWT token, send a request to the [authentication route](#auth_postactor_typeauth_provider) passing it the customer's email and password in the request body.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Obtain JWT token"
|
||||||
curl -X POST '{backend_url}/auth/customer/emailpass' \
|
curl -X POST '{backend_url}/auth/customer/emailpass' \
|
||||||
-H 'Content-Type: application/json' \
|
-H 'Content-Type: application/json' \
|
||||||
--data-raw '{
|
--data-raw '{
|
||||||
@@ -56,22 +93,55 @@ curl -X POST '{backend_url}/auth/customer/emailpass' \
|
|||||||
}'
|
}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
If authenticated successfully, an object is returned in the response with the property `token` being the JWT token.
|
If authenticated successfully, an object is returned in the response with the property `token` being the JWT token.
|
||||||
|
|
||||||
Learn more about the authentication route [here](#auth_postactor_typeauth_provider)
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```json title="Example response"
|
||||||
|
{
|
||||||
|
"token": "123..."
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### How to Use the JWT Token
|
#### How to Use the JWT Token
|
||||||
|
|
||||||
Pass the JWT token in the authorization bearer header:
|
To use the JWT token, pass it in the authorization bearer header.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Use JWT token"
|
||||||
Authorization: Bearer {jwt_token}
|
Authorization: Bearer {jwt_token}
|
||||||
```
|
```
|
||||||
|
|
||||||
---
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
### Cookie Session ID
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
|
### 2. Cookie Session ID
|
||||||
|
|
||||||
When you authenticate a customer and create a cookie session ID for them, the cookie session ID is passed automatically when sending the request from the browser, or with tools like Postman.
|
When you authenticate a customer and create a cookie session ID for them, the cookie session ID is passed automatically when sending the request from the browser, or with tools like Postman.
|
||||||
|
|
||||||
@@ -81,47 +151,99 @@ To obtain a cookie session ID, you must have a [JWT token for bearer authenticat
|
|||||||
|
|
||||||
{/* TODO add a link to the session authentication route. */}
|
{/* TODO add a link to the session authentication route. */}
|
||||||
|
|
||||||
Then, send a request to the session authentication API route. To view the cookie session ID, pass the `-v` option to the `curl` command:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
|
Then, send a request to the session authentication API route.
|
||||||
|
|
||||||
|
To view the cookie session ID, pass the `-v` option to the `curl` command.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Obtain cookie session"
|
||||||
curl -v -X POST '{backend_url}/auth/session' \
|
curl -v -X POST '{backend_url}/auth/session' \
|
||||||
--header 'Authorization: Bearer {jwt_token}'
|
--header 'Authorization: Bearer {jwt_token}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
The headers will be logged in the terminal as well as the response. You
|
The headers will be logged in the terminal as well as the response. You
|
||||||
should find in the headers a Cookie header similar to this:
|
should find in the headers a Cookie header.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
Set-Cookie: connect.sid=s%3A2Bu8BkaP9JUfHu9rG59G16Ma0QZf6Gj1.WT549XqX37PN8n0OecqnMCq798eLjZC5IT7yiDCBHPM;
|
|
||||||
|
```bash title="Logged cookie session"
|
||||||
|
Set-Cookie: connect.sid=s%3A2Bu8B...;
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### How to Use the Cookie Session ID in cURL
|
#### How to Use the Cookie Session ID in cURL
|
||||||
|
|
||||||
Copy the value after `connect.sid` (without the `;` at the end) and pass
|
Copy the value after `connect.sid` (without the `;` at the end) and pass
|
||||||
it as a cookie in subsequent requests as the following:
|
it as a cookie in subsequent requests.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Use cookie session"
|
||||||
curl '{backend_url}/store/products' \
|
curl '{backend_url}/store/products' \
|
||||||
-H 'Cookie: connect.sid={sid}'
|
-H 'Cookie: connect.sid={sid}'
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
Where `{sid}` is the value of `connect.sid` that you copied.
|
Where `{sid}` is the value of `connect.sid` that you copied.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
#### Including Credentials in the Fetch API
|
#### Including Credentials in the Fetch API
|
||||||
|
|
||||||
If you're sending requests using JavaScript's Fetch API, you must pass the `credentials` option
|
If you're sending requests using JavaScript's Fetch API, you must pass the `credentials` option
|
||||||
with the value `include` to all the requests you're sending. For example:
|
with the value `include` to all the requests you're sending.
|
||||||
|
|
||||||
```js
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```js title="Include credentials in fetch"
|
||||||
fetch(`<BACKEND_URL>/store/products`, {
|
fetch(`<BACKEND_URL>/store/products`, {
|
||||||
credentials: "include",
|
credentials: "include",
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -134,10 +256,16 @@ fetch(`<BACKEND_URL>/store/products`, {
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Publishable API Key
|
## Publishable API Key
|
||||||
|
|
||||||
You must pass a publishable API key in the header of your requests to the store API routes.
|
You must pass a publishable API key in the header of your requests to the store API routes.
|
||||||
@@ -154,17 +282,33 @@ Create a publishable API key either using the [admin REST APIs](https://docs.med
|
|||||||
|
|
||||||
### How to Use a Publishable API Key
|
### How to Use a Publishable API Key
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
You pass the publishable API key in the header `x-publishable-api-key` in all your requests to the store APIs.
|
You pass the publishable API key in the header `x-publishable-api-key` in all your requests to the store APIs.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Use publishable API key"
|
||||||
curl 'http://localhost:9000/store/products' \
|
curl 'http://localhost:9000/store/products' \
|
||||||
-H 'x-publishable-api-key: {your_publishable_api_key}'
|
-H 'x-publishable-api-key: {your_publishable_api_key}'
|
||||||
```
|
```
|
||||||
|
|
||||||
Where `{your_publishable_api_key}` is the token of the publishable API key.
|
Where `{your_publishable_api_key}` is the token of the publishable API key.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -177,20 +321,44 @@ Where `{your_publishable_api_key}` is the token of the publishable API key.
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## HTTP Compression
|
## HTTP Compression
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
If you've enabled HTTP Compression in your Medusa configurations, and you
|
If you've enabled HTTP Compression in your Medusa configurations, and you
|
||||||
want to disable it for some requests, you can pass the `x-no-compression`
|
want to disable it for some requests, you can pass the `x-no-compression`
|
||||||
header in your requests:
|
header in your requests.
|
||||||
|
|
||||||
```bash
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Enable HTTP compression"
|
||||||
x-no-compression: true
|
x-no-compression: true
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -203,23 +371,47 @@ x-no-compression: true
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Select Fields and Relations
|
## Select Fields and Relations
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
Many API Routes accept a `fields` query that allows you to select which fields and relations should be returned in a record.
|
Many API Routes accept a `fields` query that allows you to select which fields and relations should be returned in a record.
|
||||||
Fields and relations are separated by a comma `,`.
|
Fields and relations are separated by a comma `,`.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Select fields"
|
||||||
curl 'localhost:9000/store/products?fields=title,handle'
|
curl 'localhost:9000/store/products?fields=title,handle'
|
||||||
```
|
```
|
||||||
|
|
||||||
This returns only the `title` and `handle` fields of a product.
|
This returns only the `title` and `handle` fields of a product.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Fields Operator
|
### Fields Operator
|
||||||
|
|
||||||
By default, only the selected fields and relations are returned in the response.
|
By default, only the selected fields and relations are returned in the response.
|
||||||
@@ -229,32 +421,68 @@ Before every field or relation, you can pass one of the following operators to c
|
|||||||
- `+`: Add the field to the fields returned by default. For example, `+title` returns the `title` field along with the fields returned by default.
|
- `+`: Add the field to the fields returned by default. For example, `+title` returns the `title` field along with the fields returned by default.
|
||||||
- `-`: Remove the field from the fields returned by default. For example, `-title` removes the `title` field from the fields returned by default.
|
- `-`: Remove the field from the fields returned by default. For example, `-title` removes the `title` field from the fields returned by default.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Select Relations
|
### Select Relations
|
||||||
|
|
||||||
To select a relation, pass to `fields` the relation name prefixed by `*`. For example:
|
To select a relation, pass to `fields` the relation name prefixed by `*`.
|
||||||
|
|
||||||
```bash
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Select relations"
|
||||||
curl 'localhost:9000/store/products?fields=*variants'
|
curl 'localhost:9000/store/products?fields=*variants'
|
||||||
```
|
```
|
||||||
|
|
||||||
This returns the variants of each product.
|
This returns the variants of each product.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Select Fields in a Relation
|
### Select Fields in a Relation
|
||||||
|
|
||||||
The `*` prefix selects all fields of the relation's data model.
|
The `*` prefix selects all fields of the relation's data model.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
To select a specific field, pass a `.<field>` suffix instead of the `*` prefix. For example, `variants.title`.
|
To select a specific field, pass a `.<field>` suffix instead of the `*` prefix. For example, `variants.title`.
|
||||||
|
|
||||||
To specify multiple fields, pass each of the fields with the `<relation>.<field>` format, separated by a comma.
|
To specify multiple fields, pass each of the fields with the `<relation>.<field>` format, separated by a comma.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Select relation's fields"
|
||||||
curl 'localhost:9000/store/products?fields=variants.title,variants.sku'
|
curl 'localhost:9000/store/products?fields=variants.title,variants.sku'
|
||||||
```
|
```
|
||||||
|
|
||||||
This returns the variants of each product, but the variants only have their `id`, `title`, and `sku` fields. The `id` is always included.
|
This returns the variants of each product, but the variants only have their `id`, `title`, and `sku` fields. The `id` is always included.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -267,74 +495,118 @@ This returns the variants of each product, but the variants only have their `id`
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Query Parameter Types
|
## Query Parameter Types
|
||||||
|
|
||||||
|
|
||||||
This section covers how to pass some common data types as query parameters.
|
This section covers how to pass some common data types as query parameters.
|
||||||
This is useful if you're sending requests to the API Routes and not using
|
|
||||||
our JS Client. For example, when using cURL or Postman.
|
|
||||||
|
|
||||||
|
This is useful if you're sending requests to the API Routes using cURL or Postman.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Strings
|
### Strings
|
||||||
|
|
||||||
|
|
||||||
You can pass a string value in the form of `<parameter_name>=<value>`.
|
You can pass a string value in the form of `<parameter_name>=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="String filter"
|
||||||
```bash
|
|
||||||
curl "http://localhost:9000/store/products?title=Shirt"
|
curl "http://localhost:9000/store/products?title=Shirt"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
If the string has any characters other than letters and numbers, you must
|
If the string has any characters other than letters and numbers, you must
|
||||||
encode them.
|
encode them.
|
||||||
|
|
||||||
|
|
||||||
For example, if the string has spaces, you can encode the space with `+` or
|
For example, if the string has spaces, you can encode the space with `+` or
|
||||||
`%20`:
|
`%20`.
|
||||||
|
|
||||||
|
|
||||||
```bash
|
|
||||||
curl "http://localhost:9000/store/products?title=Blue%20Shirt"
|
|
||||||
```
|
|
||||||
|
|
||||||
|
|
||||||
You can use tools like [this one](https://www.urlencoder.org/) to learn how
|
You can use tools like [this one](https://www.urlencoder.org/) to learn how
|
||||||
a value can be encoded.
|
a value can be encoded.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Encoded string filter"
|
||||||
|
curl "http://localhost:9000/store/products?title=Blue%20Shirt"
|
||||||
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Integers
|
### Integers
|
||||||
|
|
||||||
You can pass an integer value in the form of `<parameter_name>=<value>`.
|
You can pass an integer value in the form of `<parameter_name>=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Integer filter"
|
||||||
```bash
|
|
||||||
curl "http://localhost:9000/store/products?offset=1"
|
curl "http://localhost:9000/store/products?offset=1"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Boolean
|
### Boolean
|
||||||
|
|
||||||
|
|
||||||
You can pass a boolean value in the form of `<parameter_name>=<value>`.
|
You can pass a boolean value in the form of `<parameter_name>=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Boolean filter"
|
||||||
```bash
|
|
||||||
curl "http://localhost:9000/store/products?is_giftcard=true"
|
curl "http://localhost:9000/store/products?is_giftcard=true"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Date and DateTime
|
### Date and DateTime
|
||||||
|
|
||||||
@@ -342,26 +614,40 @@ curl "http://localhost:9000/store/products?is_giftcard=true"
|
|||||||
You can pass a date value in the form `<parameter_name>=<value>`. The date
|
You can pass a date value in the form `<parameter_name>=<value>`. The date
|
||||||
must be in the format `YYYY-MM-DD`.
|
must be in the format `YYYY-MM-DD`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Date filter"
|
||||||
```bash
|
|
||||||
curl -g "http://localhost:9000/store/products?created_at[$lt]=2023-02-17"
|
curl -g "http://localhost:9000/store/products?created_at[$lt]=2023-02-17"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
You can also pass the time using the format `YYYY-MM-DDTHH:MM:SSZ`. Please
|
You can also pass the time using the format `YYYY-MM-DDTHH:MM:SSZ`. Please
|
||||||
note that the `T` and `Z` here are fixed.
|
note that the `T` and `Z` here are fixed.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Date and time filter"
|
||||||
```bash
|
|
||||||
curl -g "http://localhost:9000/store/products?created_at[$lt]=2023-02-17T07:22:30Z"
|
curl -g "http://localhost:9000/store/products?created_at[$lt]=2023-02-17T07:22:30Z"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Array
|
### Array
|
||||||
|
|
||||||
@@ -370,19 +656,25 @@ Each array value must be passed as a separate query parameter in the form
|
|||||||
`<parameter_name>[]=<value>`. You can also specify the index of each
|
`<parameter_name>[]=<value>`. You can also specify the index of each
|
||||||
parameter in the brackets `<parameter_name>[0]=<value>`.
|
parameter in the brackets `<parameter_name>[0]=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Array filter"
|
||||||
```bash
|
|
||||||
curl -g "http://localhost:9000/store/products?sales_channel_id[]=sc_01GPGVB42PZ7N3YQEP2WDM7PC7&sales_channel_id[]=sc_234PGVB42PZ7N3YQEP2WDM7PC7"
|
curl -g "http://localhost:9000/store/products?sales_channel_id[]=sc_01GPGVB42PZ7N3YQEP2WDM7PC7&sales_channel_id[]=sc_234PGVB42PZ7N3YQEP2WDM7PC7"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
Note that the `-g` parameter passed to `curl` disables errors being thrown
|
Note that the `-g` parameter passed to `curl` disables errors being thrown
|
||||||
for using the brackets. Read more
|
for using the brackets. Read more
|
||||||
[here](https://curl.se/docs/manpage.html#-g).
|
[here](https://curl.se/docs/manpage.html#-g).
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Object
|
### Object
|
||||||
|
|
||||||
@@ -390,14 +682,20 @@ for using the brackets. Read more
|
|||||||
Object parameters must be passed as separate query parameters in the form
|
Object parameters must be passed as separate query parameters in the form
|
||||||
`<parameter_name>[<key>]=<value>`.
|
`<parameter_name>[<key>]=<value>`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Object filter"
|
||||||
```bash
|
|
||||||
curl -g "http://localhost:9000/store/products?created_at[$lt]=2023-02-17&created_at[$gt]=2022-09-17"
|
curl -g "http://localhost:9000/store/products?created_at[$lt]=2023-02-17&created_at[$gt]=2022-09-17"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -410,10 +708,16 @@ curl -g "http://localhost:9000/store/products?created_at[$lt]=2023-02-17&created
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
</SectionContainer>
|
</SectionContainer>
|
||||||
|
|
||||||
<SectionContainer noTopPadding={true}>
|
<SectionContainer noTopPadding={true}>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
## Pagination
|
## Pagination
|
||||||
|
|
||||||
|
|
||||||
@@ -422,19 +726,34 @@ curl -g "http://localhost:9000/store/products?created_at[$lt]=2023-02-17&created
|
|||||||
|
|
||||||
In listing API Routes, such as list products, you can control the pagination using the query parameters `limit` and `offset`.
|
In listing API Routes, such as list products, you can control the pagination using the query parameters `limit` and `offset`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
`limit` is used to specify the maximum number of items to be returned in the response. `offset` is used to specify how many items to skip before returning the resulting records.
|
`limit` is used to specify the maximum number of items to be returned in the response. `offset` is used to specify how many items to skip before returning the resulting records.
|
||||||
|
|
||||||
|
|
||||||
Use the `offset` query parameter to change between pages. For example, if the limit is `50`, at page `1` the offset should be `0`; at page `2` the offset should be `50`, and so on.
|
Use the `offset` query parameter to change between pages. For example, if the limit is `50`, at page `1` the offset should be `0`; at page `2` the offset should be `50`, and so on.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
For example:
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
```bash
|
```bash title="Pagination query parameters"
|
||||||
curl "http://localhost:9000/store/products?limit=5"
|
curl "http://localhost:9000/store/products?limit=5&offset=0"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Response Fields
|
### Response Fields
|
||||||
|
|
||||||
@@ -451,6 +770,13 @@ there are three pagination-related fields returned:
|
|||||||
For example, if the `count` is `100` and the `limit` is `50`, divide the
|
For example, if the `count` is `100` and the `limit` is `50`, divide the
|
||||||
`count` by the `limit` to get the number of pages: `100/50 = 2 pages`.
|
`count` by the `limit` to get the number of pages: `100/50 = 2 pages`.
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing codeContentClassName="mt-3">
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
### Sort Order
|
### Sort Order
|
||||||
|
|
||||||
@@ -458,24 +784,43 @@ For example, if the `count` is `100` and the `limit` is `50`, divide the
|
|||||||
The `order` field (available on API Routes that support pagination) allows you to
|
The `order` field (available on API Routes that support pagination) allows you to
|
||||||
sort the retrieved items by a field of that item.
|
sort the retrieved items by a field of that item.
|
||||||
|
|
||||||
For example, pass the query parameter `order=created_at` to sort products by their `created_at` field:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Ascending sort by a field"
|
||||||
curl "http://localhost:9000/store/products?order=created_at"
|
curl "http://localhost:9000/store/products?order=created_at"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
This sorts the products by their `created_at` field in the ascending order.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout addYSpacing>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
By default, the sort direction is ascending. To change it to
|
By default, the sort direction is ascending. To change it to
|
||||||
descending, pass a dash (`-`) before the field name.
|
descending, pass a dash (`-`) before the field name.
|
||||||
|
|
||||||
For example:
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
```bash
|
<DividedMarkdownCode>
|
||||||
|
|
||||||
|
```bash title="Descending sort by a field"
|
||||||
curl "http://localhost:9000/store/products?order=-created_at"
|
curl "http://localhost:9000/store/products?order=-created_at"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
This sorts the products by their `created_at` field in the descending order.
|
This sorts the products by their `created_at` field in the descending order.
|
||||||
|
|
||||||
|
</DividedMarkdownCode>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
<Feedback
|
<Feedback
|
||||||
event="survey_api-ref"
|
event="survey_api-ref"
|
||||||
extraData={{
|
extraData={{
|
||||||
@@ -488,4 +833,38 @@ This sorts the products by their `created_at` field in the descending order.
|
|||||||
vertical={true}
|
vertical={true}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
</SectionContainer>
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownLayout>
|
||||||
|
|
||||||
|
<DividedMarkdownContent>
|
||||||
|
|
||||||
|
## Workflows
|
||||||
|
|
||||||
|
While browsing this reference, you'll find some API routes mention what workflow is used in them.
|
||||||
|
|
||||||
|
If you click on the workflow, you'll view a reference of that workflow, including its hooks.
|
||||||
|
|
||||||
|
This is useful if you want to extend an API route and pass additional data or perform custom actions.
|
||||||
|
|
||||||
|
Refer to [this guide](https://docs.medusajs.com/v2/customization/extend-models/extend-create-product) to find an example of extending an API route.
|
||||||
|
|
||||||
|
<Feedback
|
||||||
|
event="survey_api-ref"
|
||||||
|
extraData={{
|
||||||
|
area: "admin",
|
||||||
|
section: "workflows"
|
||||||
|
}}
|
||||||
|
reportLink={formatReportLink("admin", "Workflows")}
|
||||||
|
pathName="/api/admin"
|
||||||
|
question="Was this section helpful?"
|
||||||
|
vertical={true}
|
||||||
|
/>
|
||||||
|
|
||||||
|
</DividedMarkdownContent>
|
||||||
|
|
||||||
|
</DividedMarkdownLayout>
|
||||||
|
|
||||||
|
</SectionContainer>
|
||||||
|
|
||||||
|
</Section>
|
||||||
@@ -1,31 +1,17 @@
|
|||||||
import AreaProvider from "@/providers/area"
|
import AreaProvider from "@/providers/area"
|
||||||
import AdminContentV2 from "../_mdx/admin.mdx"
|
import AdminContent from "../_mdx/admin.mdx"
|
||||||
import ClientLibrariesV2 from "../_mdx/client-libraries.mdx"
|
|
||||||
import Section from "@/components/Section"
|
|
||||||
import Tags from "@/components/Tags"
|
import Tags from "@/components/Tags"
|
||||||
import DividedLayout from "@/layouts/Divided"
|
|
||||||
import PageTitleProvider from "@/providers/page-title"
|
import PageTitleProvider from "@/providers/page-title"
|
||||||
|
import { H1 } from "docs-ui"
|
||||||
|
|
||||||
const ReferencePage = async () => {
|
const ReferencePage = async () => {
|
||||||
return (
|
return (
|
||||||
<AreaProvider area={"admin"}>
|
<AreaProvider area={"admin"}>
|
||||||
<PageTitleProvider>
|
<PageTitleProvider>
|
||||||
<h1 className="!text-h2 scroll-m-56 lg:pl-4" id="introduction">
|
<H1 className="!h2-docs scroll-m-56 lg:pl-4" id="introduction">
|
||||||
Medusa V2 Admin API Reference
|
Medusa V2 Admin API Reference
|
||||||
</h1>
|
</H1>
|
||||||
<DividedLayout
|
<AdminContent />
|
||||||
mainContent={
|
|
||||||
<Section checkActiveOnScroll={true}>
|
|
||||||
<AdminContentV2 />
|
|
||||||
</Section>
|
|
||||||
}
|
|
||||||
codeContent={
|
|
||||||
<div className="mb-1 lg:mb-0">
|
|
||||||
<ClientLibrariesV2 />
|
|
||||||
</div>
|
|
||||||
}
|
|
||||||
className="flex-col-reverse"
|
|
||||||
/>
|
|
||||||
<Tags />
|
<Tags />
|
||||||
</PageTitleProvider>
|
</PageTitleProvider>
|
||||||
</AreaProvider>
|
</AreaProvider>
|
||||||
@@ -37,7 +23,7 @@ export default ReferencePage
|
|||||||
export function generateMetadata() {
|
export function generateMetadata() {
|
||||||
return {
|
return {
|
||||||
title: `Medusa Admin API Reference`,
|
title: `Medusa Admin API Reference`,
|
||||||
description: `REST API reference for the Medusa admin API. This reference includes code snippets and examples for Medusa JS Client and cURL.`,
|
description: `REST API reference for the Medusa v2 admin API, with code snippets and examples.`,
|
||||||
metadataBase: process.env.NEXT_PUBLIC_BASE_URL,
|
metadataBase: process.env.NEXT_PUBLIC_BASE_URL,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,30 +1,17 @@
|
|||||||
import AreaProvider from "@/providers/area"
|
import AreaProvider from "@/providers/area"
|
||||||
import StoreContentV2 from "../_mdx/store.mdx"
|
import StoreContent from "../_mdx/store.mdx"
|
||||||
import ClientLibrariesV2 from "../_mdx/client-libraries.mdx"
|
|
||||||
import Section from "@/components/Section"
|
|
||||||
import Tags from "@/components/Tags"
|
import Tags from "@/components/Tags"
|
||||||
import DividedLayout from "@/layouts/Divided"
|
|
||||||
import PageTitleProvider from "@/providers/page-title"
|
import PageTitleProvider from "@/providers/page-title"
|
||||||
|
import { H1 } from "docs-ui"
|
||||||
|
|
||||||
const ReferencePage = async () => {
|
const ReferencePage = async () => {
|
||||||
return (
|
return (
|
||||||
<AreaProvider area={"store"}>
|
<AreaProvider area={"store"}>
|
||||||
<PageTitleProvider>
|
<PageTitleProvider>
|
||||||
<h1 className="!text-h2 scroll-m-56 lg:pl-4" id="introduction">
|
<H1 className="!h2-docs scroll-m-56 lg:pl-4" id="introduction">
|
||||||
Medusa V2 Store API Reference
|
Medusa V2 Store API Reference
|
||||||
</h1>
|
</H1>
|
||||||
<DividedLayout
|
<StoreContent />
|
||||||
mainContent={
|
|
||||||
<Section checkActiveOnScroll={true}>
|
|
||||||
<StoreContentV2 />
|
|
||||||
</Section>
|
|
||||||
}
|
|
||||||
codeContent={
|
|
||||||
<div className="mb-1 lg:mb-0 hidden lg:block">
|
|
||||||
<ClientLibrariesV2 />
|
|
||||||
</div>
|
|
||||||
}
|
|
||||||
/>
|
|
||||||
<Tags />
|
<Tags />
|
||||||
</PageTitleProvider>
|
</PageTitleProvider>
|
||||||
</AreaProvider>
|
</AreaProvider>
|
||||||
@@ -36,7 +23,7 @@ export default ReferencePage
|
|||||||
export function generateMetadata() {
|
export function generateMetadata() {
|
||||||
return {
|
return {
|
||||||
title: `Medusa Store API Reference`,
|
title: `Medusa Store API Reference`,
|
||||||
description: `REST API reference for the Medusa store API. This reference includes code snippets and examples for Medusa JS Client and cURL.`,
|
description: `REST API reference for the Medusa v2 store API, with code snippets and examples.`,
|
||||||
metadataBase: process.env.NEXT_PUBLIC_BASE_URL,
|
metadataBase: process.env.NEXT_PUBLIC_BASE_URL,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
"use client"
|
"use client"
|
||||||
|
|
||||||
import { useScrollController, useSidebar } from "docs-ui"
|
import { useScrollController, useSidebar, H2 as UiH2 } from "docs-ui"
|
||||||
import { useEffect, useMemo, useRef, useState } from "react"
|
import { useEffect, useMemo, useRef, useState } from "react"
|
||||||
import getSectionId from "../../../utils/get-section-id"
|
import getSectionId from "../../../utils/get-section-id"
|
||||||
|
|
||||||
@@ -39,9 +39,9 @@ const H2 = ({ children, ...props }: H2Props) => {
|
|||||||
}, [id])
|
}, [id])
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<h2 {...props} id={id} ref={headingRef}>
|
<UiH2 {...props} id={id} passRef={headingRef}>
|
||||||
{children}
|
{children}
|
||||||
</h2>
|
</UiH2>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -14,9 +14,12 @@ const SectionContainer = forwardRef<HTMLDivElement, SectionContainerProps>(
|
|||||||
ref
|
ref
|
||||||
) {
|
) {
|
||||||
return (
|
return (
|
||||||
<div className={clsx("relative pb-7", !noTopPadding && "pt-7")} ref={ref}>
|
<div
|
||||||
|
className={clsx("relative pb-4 md:pb-7", !noTopPadding && "pt-7")}
|
||||||
|
ref={ref}
|
||||||
|
>
|
||||||
{children}
|
{children}
|
||||||
{!noDivider && <SectionDivider className="-left-1.5 lg:!-left-4" />}
|
{!noDivider && <SectionDivider className="-left-1.5 lg:!-left-full" />}
|
||||||
</div>
|
</div>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,6 +19,7 @@ const Section = ({
|
|||||||
rootElm: sectionRef.current || undefined,
|
rootElm: sectionRef.current || undefined,
|
||||||
enable: checkActiveOnScroll,
|
enable: checkActiveOnScroll,
|
||||||
useDefaultIfNoActive: false,
|
useDefaultIfNoActive: false,
|
||||||
|
maxLevel: 2,
|
||||||
})
|
})
|
||||||
const { setActivePath } = useSidebar()
|
const { setActivePath } = useSidebar()
|
||||||
const router = useRouter()
|
const router = useRouter()
|
||||||
|
|||||||
@@ -90,6 +90,7 @@ const Tags = () => {
|
|||||||
title: tag.name,
|
title: tag.name,
|
||||||
children: childItems,
|
children: childItems,
|
||||||
loaded: childItems.length > 0,
|
loaded: childItems.length > 0,
|
||||||
|
showLoadingIfEmpty: true,
|
||||||
onOpen: () => {
|
onOpen: () => {
|
||||||
if (location.hash !== tagPathName) {
|
if (location.hash !== tagPathName) {
|
||||||
router.push(`#${tagPathName}`, {
|
router.push(`#${tagPathName}`, {
|
||||||
|
|||||||
@@ -1,12 +1,13 @@
|
|||||||
import clsx from "clsx"
|
import clsx from "clsx"
|
||||||
import { forwardRef } from "react"
|
import { forwardRef } from "react"
|
||||||
|
|
||||||
type DividedLayoutProps = {
|
export type DividedLayoutProps = {
|
||||||
mainContent: React.ReactNode
|
mainContent: React.ReactNode
|
||||||
codeContent: React.ReactNode
|
codeContent: React.ReactNode
|
||||||
className?: string
|
className?: string
|
||||||
mainContentClassName?: string
|
mainContentClassName?: string
|
||||||
codeContentClassName?: string
|
codeContentClassName?: string
|
||||||
|
addYSpacing?: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
const DividedLayout = forwardRef<HTMLDivElement, DividedLayoutProps>(
|
const DividedLayout = forwardRef<HTMLDivElement, DividedLayoutProps>(
|
||||||
@@ -17,6 +18,7 @@ const DividedLayout = forwardRef<HTMLDivElement, DividedLayoutProps>(
|
|||||||
className,
|
className,
|
||||||
mainContentClassName,
|
mainContentClassName,
|
||||||
codeContentClassName,
|
codeContentClassName,
|
||||||
|
addYSpacing = false,
|
||||||
},
|
},
|
||||||
ref
|
ref
|
||||||
) {
|
) {
|
||||||
@@ -24,6 +26,7 @@ const DividedLayout = forwardRef<HTMLDivElement, DividedLayoutProps>(
|
|||||||
<div
|
<div
|
||||||
className={clsx(
|
className={clsx(
|
||||||
"flex w-full flex-col justify-between lg:flex-row lg:gap-4",
|
"flex w-full flex-col justify-between lg:flex-row lg:gap-4",
|
||||||
|
addYSpacing && "my-3",
|
||||||
className
|
className
|
||||||
)}
|
)}
|
||||||
ref={ref}
|
ref={ref}
|
||||||
@@ -39,6 +42,7 @@ const DividedLayout = forwardRef<HTMLDivElement, DividedLayoutProps>(
|
|||||||
<div
|
<div
|
||||||
className={clsx(
|
className={clsx(
|
||||||
"w-full flex-shrink-0 flex-grow-0 lg:w-[calc(50%-32px)] lg:basis-[calc(50%-32px)] lg:pr-1.5",
|
"w-full flex-shrink-0 flex-grow-0 lg:w-[calc(50%-32px)] lg:basis-[calc(50%-32px)] lg:pr-1.5",
|
||||||
|
"mt-2 lg:mt-0",
|
||||||
codeContentClassName
|
codeContentClassName
|
||||||
)}
|
)}
|
||||||
>
|
>
|
||||||
|
|||||||
@@ -0,0 +1,10 @@
|
|||||||
|
type DividedMarkdownSectionProps = {
|
||||||
|
children: React.ReactElement[]
|
||||||
|
}
|
||||||
|
|
||||||
|
const DividedMarkdownSection = ({ children }: DividedMarkdownSectionProps) => {
|
||||||
|
return <>{children}</>
|
||||||
|
}
|
||||||
|
|
||||||
|
export const DividedMarkdownContent = DividedMarkdownSection
|
||||||
|
export const DividedMarkdownCode = DividedMarkdownSection
|
||||||
30
www/apps/api-reference/layouts/DividedMarkdown/index.tsx
Normal file
30
www/apps/api-reference/layouts/DividedMarkdown/index.tsx
Normal file
@@ -0,0 +1,30 @@
|
|||||||
|
import React from "react"
|
||||||
|
import DividedLayout, { DividedLayoutProps } from "../Divided"
|
||||||
|
|
||||||
|
type DividedMarkdownLayoutProps = {
|
||||||
|
children: React.ReactNode
|
||||||
|
} & Omit<DividedLayoutProps, "mainContent" | "codeContent">
|
||||||
|
|
||||||
|
const DividedMarkdownLayout = ({
|
||||||
|
children,
|
||||||
|
...props
|
||||||
|
}: DividedMarkdownLayoutProps) => {
|
||||||
|
const childArr = React.isValidElement(children)
|
||||||
|
? [children]
|
||||||
|
: Array.isArray(children)
|
||||||
|
? children
|
||||||
|
: []
|
||||||
|
|
||||||
|
if (!childArr.length) {
|
||||||
|
return <></>
|
||||||
|
}
|
||||||
|
|
||||||
|
const contentElm = childArr[0]
|
||||||
|
const codeElm = childArr.length > 1 ? childArr[1] : <></>
|
||||||
|
|
||||||
|
return (
|
||||||
|
<DividedLayout mainContent={contentElm} codeContent={codeElm} {...props} />
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export default DividedMarkdownLayout
|
||||||
@@ -1,5 +1,7 @@
|
|||||||
import mdx from "@next/mdx"
|
import mdx from "@next/mdx"
|
||||||
import bundleAnalyzer from "@next/bundle-analyzer"
|
import bundleAnalyzer from "@next/bundle-analyzer"
|
||||||
|
import rehypeMdxCodeProps from "rehype-mdx-code-props"
|
||||||
|
import rehypeSlug from "rehype-slug"
|
||||||
|
|
||||||
/** @type {import('next').NextConfig} */
|
/** @type {import('next').NextConfig} */
|
||||||
const nextConfig = {
|
const nextConfig = {
|
||||||
@@ -15,7 +17,15 @@ const nextConfig = {
|
|||||||
const withMDX = mdx({
|
const withMDX = mdx({
|
||||||
extension: /\.mdx?$/,
|
extension: /\.mdx?$/,
|
||||||
options: {
|
options: {
|
||||||
rehypePlugins: [],
|
rehypePlugins: [
|
||||||
|
[
|
||||||
|
rehypeMdxCodeProps,
|
||||||
|
{
|
||||||
|
tagName: "code",
|
||||||
|
},
|
||||||
|
],
|
||||||
|
[rehypeSlug],
|
||||||
|
],
|
||||||
development: process.env.NODE_ENV === "development",
|
development: process.env.NODE_ENV === "development",
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|||||||
@@ -45,6 +45,8 @@
|
|||||||
"react-intersection-observer": "^9.5.3",
|
"react-intersection-observer": "^9.5.3",
|
||||||
"react-tooltip": "^5.19.0",
|
"react-tooltip": "^5.19.0",
|
||||||
"react-transition-group": "^4.4.5",
|
"react-transition-group": "^4.4.5",
|
||||||
|
"rehype-mdx-code-props": "^2.0.0",
|
||||||
|
"rehype-slug": "^6.0.0",
|
||||||
"slugify": "^1.6.6",
|
"slugify": "^1.6.6",
|
||||||
"swr": "^2.2.0",
|
"swr": "^2.2.0",
|
||||||
"tailwind": "*",
|
"tailwind": "*",
|
||||||
|
|||||||
19
www/packages/docs-ui/src/components/Heading/H1/index.tsx
Normal file
19
www/packages/docs-ui/src/components/Heading/H1/index.tsx
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
import clsx from "clsx"
|
||||||
|
import React from "react"
|
||||||
|
|
||||||
|
type H1Props = React.HTMLAttributes<HTMLHeadingElement> & {
|
||||||
|
id?: string
|
||||||
|
}
|
||||||
|
|
||||||
|
export const H1 = ({ className, ...props }: H1Props) => {
|
||||||
|
return (
|
||||||
|
<h1
|
||||||
|
className={clsx(
|
||||||
|
"h1-docs [&_code]:!h1-docs [&_code]:!font-mono mb-docs_1 text-medusa-fg-base",
|
||||||
|
props.id && "scroll-m-56",
|
||||||
|
className
|
||||||
|
)}
|
||||||
|
{...props}
|
||||||
|
/>
|
||||||
|
)
|
||||||
|
}
|
||||||
32
www/packages/docs-ui/src/components/Heading/H2/index.tsx
Normal file
32
www/packages/docs-ui/src/components/Heading/H2/index.tsx
Normal file
@@ -0,0 +1,32 @@
|
|||||||
|
import clsx from "clsx"
|
||||||
|
import React from "react"
|
||||||
|
import { Link } from "@/components"
|
||||||
|
|
||||||
|
type H2Props = React.HTMLAttributes<HTMLHeadingElement> & {
|
||||||
|
id?: string
|
||||||
|
passRef?: React.RefObject<HTMLHeadingElement>
|
||||||
|
}
|
||||||
|
|
||||||
|
export const H2 = ({ className, children, passRef, ...props }: H2Props) => {
|
||||||
|
return (
|
||||||
|
<h2
|
||||||
|
className={clsx(
|
||||||
|
"h2-docs [&_code]:!h2-docs [&_code]:!font-mono mb-docs_1 mt-docs_4 text-medusa-fg-base",
|
||||||
|
props.id && "group/h2 scroll-m-56",
|
||||||
|
className
|
||||||
|
)}
|
||||||
|
{...props}
|
||||||
|
ref={passRef}
|
||||||
|
>
|
||||||
|
{children}
|
||||||
|
{props.id && (
|
||||||
|
<Link
|
||||||
|
href={`#${props.id}`}
|
||||||
|
className="opacity-0 group-hover/h2:opacity-100 transition-opacity ml-docs_0.5 inline-block"
|
||||||
|
>
|
||||||
|
#
|
||||||
|
</Link>
|
||||||
|
)}
|
||||||
|
</h2>
|
||||||
|
)
|
||||||
|
}
|
||||||
30
www/packages/docs-ui/src/components/Heading/H3/index.tsx
Normal file
30
www/packages/docs-ui/src/components/Heading/H3/index.tsx
Normal file
@@ -0,0 +1,30 @@
|
|||||||
|
import clsx from "clsx"
|
||||||
|
import React from "react"
|
||||||
|
import { Link } from "@/components"
|
||||||
|
|
||||||
|
type H3Props = React.HTMLAttributes<HTMLHeadingElement> & {
|
||||||
|
id?: string
|
||||||
|
}
|
||||||
|
|
||||||
|
export const H3 = ({ className, children, ...props }: H3Props) => {
|
||||||
|
return (
|
||||||
|
<h3
|
||||||
|
className={clsx(
|
||||||
|
"h3-docs [&_code]:!h3-docs [&_code]:!font-mono mb-docs_0.5 mt-docs_3 text-medusa-fg-base",
|
||||||
|
props.id && "group/h3 scroll-m-56",
|
||||||
|
className
|
||||||
|
)}
|
||||||
|
{...props}
|
||||||
|
>
|
||||||
|
{children}
|
||||||
|
{props.id && (
|
||||||
|
<Link
|
||||||
|
href={`#${props.id}`}
|
||||||
|
className="opacity-0 group-hover/h3:opacity-100 transition-opacity ml-docs_0.5 inline-block"
|
||||||
|
>
|
||||||
|
#
|
||||||
|
</Link>
|
||||||
|
)}
|
||||||
|
</h3>
|
||||||
|
)
|
||||||
|
}
|
||||||
14
www/packages/docs-ui/src/components/Heading/H4/index.tsx
Normal file
14
www/packages/docs-ui/src/components/Heading/H4/index.tsx
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
import clsx from "clsx"
|
||||||
|
import React from "react"
|
||||||
|
|
||||||
|
export const H4 = ({
|
||||||
|
className,
|
||||||
|
...props
|
||||||
|
}: React.HTMLAttributes<HTMLHeadingElement>) => {
|
||||||
|
return (
|
||||||
|
<h4
|
||||||
|
className={clsx("mb-docs_0.5 text-medusa-fg-base text-h4", className)}
|
||||||
|
{...props}
|
||||||
|
/>
|
||||||
|
)
|
||||||
|
}
|
||||||
4
www/packages/docs-ui/src/components/Heading/index.tsx
Normal file
4
www/packages/docs-ui/src/components/Heading/index.tsx
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
export * from "./H1"
|
||||||
|
export * from "./H2"
|
||||||
|
export * from "./H3"
|
||||||
|
export * from "./H4"
|
||||||
@@ -10,7 +10,10 @@ import {
|
|||||||
DetailsSummary,
|
DetailsSummary,
|
||||||
DetailsProps,
|
DetailsProps,
|
||||||
ZoomImg,
|
ZoomImg,
|
||||||
Link,
|
H1,
|
||||||
|
H2,
|
||||||
|
H3,
|
||||||
|
H4,
|
||||||
} from "@/components"
|
} from "@/components"
|
||||||
import clsx from "clsx"
|
import clsx from "clsx"
|
||||||
import { Text } from "@medusajs/ui"
|
import { Text } from "@medusajs/ui"
|
||||||
@@ -27,78 +30,10 @@ export const MDXComponents: MDXComponentsType = {
|
|||||||
Summary: DetailsSummary,
|
Summary: DetailsSummary,
|
||||||
Card,
|
Card,
|
||||||
CardList,
|
CardList,
|
||||||
h1: ({ className, ...props }: React.HTMLAttributes<HTMLHeadingElement>) => {
|
h1: H1,
|
||||||
return (
|
h2: H2,
|
||||||
<h1
|
h3: H3,
|
||||||
className={clsx(
|
h4: H4,
|
||||||
"h1-docs [&_code]:!h1-docs [&_code]:!font-mono mb-docs_1 text-medusa-fg-base",
|
|
||||||
props.id && "scroll-m-56",
|
|
||||||
className
|
|
||||||
)}
|
|
||||||
{...props}
|
|
||||||
/>
|
|
||||||
)
|
|
||||||
},
|
|
||||||
h2: ({
|
|
||||||
className,
|
|
||||||
children,
|
|
||||||
...props
|
|
||||||
}: React.HTMLAttributes<HTMLHeadingElement>) => {
|
|
||||||
return (
|
|
||||||
<h2
|
|
||||||
className={clsx(
|
|
||||||
"h2-docs [&_code]:!h2-docs [&_code]:!font-mono mb-docs_1 mt-docs_4 text-medusa-fg-base",
|
|
||||||
props.id && "group/h2 scroll-m-56",
|
|
||||||
className
|
|
||||||
)}
|
|
||||||
{...props}
|
|
||||||
>
|
|
||||||
{children}
|
|
||||||
{props.id && (
|
|
||||||
<Link
|
|
||||||
href={`#${props.id}`}
|
|
||||||
className="opacity-0 group-hover/h2:opacity-100 transition-opacity ml-docs_0.5 inline-block"
|
|
||||||
>
|
|
||||||
#
|
|
||||||
</Link>
|
|
||||||
)}
|
|
||||||
</h2>
|
|
||||||
)
|
|
||||||
},
|
|
||||||
h3: ({
|
|
||||||
className,
|
|
||||||
children,
|
|
||||||
...props
|
|
||||||
}: React.HTMLAttributes<HTMLHeadingElement>) => {
|
|
||||||
return (
|
|
||||||
<h3
|
|
||||||
className={clsx(
|
|
||||||
"h3-docs [&_code]:!h3-docs [&_code]:!font-mono mb-docs_0.5 mt-docs_3 text-medusa-fg-base",
|
|
||||||
props.id && "group/h3 scroll-m-56",
|
|
||||||
className
|
|
||||||
)}
|
|
||||||
{...props}
|
|
||||||
>
|
|
||||||
{children}
|
|
||||||
{props.id && (
|
|
||||||
<Link
|
|
||||||
href={`#${props.id}`}
|
|
||||||
className="opacity-0 group-hover/h3:opacity-100 transition-opacity ml-docs_0.5 inline-block"
|
|
||||||
>
|
|
||||||
#
|
|
||||||
</Link>
|
|
||||||
)}
|
|
||||||
</h3>
|
|
||||||
)
|
|
||||||
},
|
|
||||||
h4: ({ className, ...props }: React.HTMLAttributes<HTMLHeadingElement>) => {
|
|
||||||
return (
|
|
||||||
<h4
|
|
||||||
className={clsx("mb-docs_0.5 text-medusa-fg-base text-h4", className)}
|
|
||||||
{...props}
|
|
||||||
/>
|
|
||||||
)
|
|
||||||
},
|
|
||||||
p: ({ className, ...props }: React.HTMLAttributes<HTMLParagraphElement>) => {
|
p: ({ className, ...props }: React.HTMLAttributes<HTMLParagraphElement>) => {
|
||||||
return (
|
return (
|
||||||
<p
|
<p
|
||||||
|
|||||||
@@ -29,18 +29,21 @@ export const SidebarItemCategory = ({
|
|||||||
getPersistedCategoryState,
|
getPersistedCategoryState,
|
||||||
persistState,
|
persistState,
|
||||||
} = useSidebar()
|
} = useSidebar()
|
||||||
|
const itemShowLoading = useMemo(() => {
|
||||||
|
return !item.loaded || (item.showLoadingIfEmpty && !item.children?.length)
|
||||||
|
}, [item])
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (open && !item.loaded) {
|
if (open && itemShowLoading) {
|
||||||
setShowLoading(true)
|
setShowLoading(true)
|
||||||
}
|
}
|
||||||
}, [open])
|
}, [open, itemShowLoading])
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (item.loaded && showLoading) {
|
if (!itemShowLoading && showLoading) {
|
||||||
setShowLoading(false)
|
setShowLoading(false)
|
||||||
}
|
}
|
||||||
}, [item])
|
}, [itemShowLoading, showLoading])
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const isActive = isChildrenActive(item)
|
const isActive = isChildrenActive(item)
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ export * from "./ExpandableNotice"
|
|||||||
export * from "./FeatureFlagNotice"
|
export * from "./FeatureFlagNotice"
|
||||||
export * from "./Feedback"
|
export * from "./Feedback"
|
||||||
export * from "./Feedback/Solutions"
|
export * from "./Feedback/Solutions"
|
||||||
|
export * from "./Heading"
|
||||||
export * from "./HooksLoader"
|
export * from "./HooksLoader"
|
||||||
export * from "./Icons"
|
export * from "./Icons"
|
||||||
export * from "./InlineIcon"
|
export * from "./InlineIcon"
|
||||||
|
|||||||
@@ -14,12 +14,14 @@ export type UseActiveOnScrollProps = {
|
|||||||
rootElm?: Document | HTMLElement
|
rootElm?: Document | HTMLElement
|
||||||
enable?: boolean
|
enable?: boolean
|
||||||
useDefaultIfNoActive?: boolean
|
useDefaultIfNoActive?: boolean
|
||||||
|
maxLevel?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
export const useActiveOnScroll = ({
|
export const useActiveOnScroll = ({
|
||||||
rootElm,
|
rootElm,
|
||||||
enable = true,
|
enable = true,
|
||||||
useDefaultIfNoActive = true,
|
useDefaultIfNoActive = true,
|
||||||
|
maxLevel = 3,
|
||||||
}: UseActiveOnScrollProps) => {
|
}: UseActiveOnScrollProps) => {
|
||||||
const [items, setItems] = useState<ActiveOnScrollItem[]>([])
|
const [items, setItems] = useState<ActiveOnScrollItem[]>([])
|
||||||
const [activeItemId, setActiveItemId] = useState("")
|
const [activeItemId, setActiveItemId] = useState("")
|
||||||
@@ -40,12 +42,23 @@ export const useActiveOnScroll = ({
|
|||||||
|
|
||||||
return document
|
return document
|
||||||
}, [rootElm, isBrowser, enable])
|
}, [rootElm, isBrowser, enable])
|
||||||
|
const querySelector = useMemo(() => {
|
||||||
|
let selector = ""
|
||||||
|
for (let i = 2; i <= maxLevel; i++) {
|
||||||
|
if (i > 2) {
|
||||||
|
selector += `,`
|
||||||
|
}
|
||||||
|
selector += `h${i}`
|
||||||
|
}
|
||||||
|
|
||||||
|
return selector
|
||||||
|
}, [maxLevel])
|
||||||
const getHeadingsInElm = useCallback(() => {
|
const getHeadingsInElm = useCallback(() => {
|
||||||
if (!isBrowser || !enable) {
|
if (!isBrowser || !enable) {
|
||||||
return []
|
return []
|
||||||
}
|
}
|
||||||
|
|
||||||
return root?.querySelectorAll("h2,h3")
|
return root?.querySelectorAll(querySelector)
|
||||||
}, [isBrowser, pathname, root, enable])
|
}, [isBrowser, pathname, root, enable])
|
||||||
const setHeadingItems = useCallback(() => {
|
const setHeadingItems = useCallback(() => {
|
||||||
if (!enable) {
|
if (!enable) {
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import { Bannerv2, MainNav, useIsBrowser } from ".."
|
|||||||
|
|
||||||
export type MainContentLayoutProps = {
|
export type MainContentLayoutProps = {
|
||||||
mainWrapperClasses?: string
|
mainWrapperClasses?: string
|
||||||
|
contentClassName?: string
|
||||||
showBanner?: boolean
|
showBanner?: boolean
|
||||||
children: React.ReactNode
|
children: React.ReactNode
|
||||||
}
|
}
|
||||||
@@ -15,6 +16,7 @@ export const MainContentLayout = ({
|
|||||||
children,
|
children,
|
||||||
mainWrapperClasses,
|
mainWrapperClasses,
|
||||||
showBanner = true,
|
showBanner = true,
|
||||||
|
contentClassName,
|
||||||
}: MainContentLayoutProps) => {
|
}: MainContentLayoutProps) => {
|
||||||
const { isBrowser } = useIsBrowser()
|
const { isBrowser } = useIsBrowser()
|
||||||
const { desktopSidebarOpen } = useSidebar()
|
const { desktopSidebarOpen } = useSidebar()
|
||||||
@@ -57,7 +59,8 @@ export const MainContentLayout = ({
|
|||||||
<div
|
<div
|
||||||
className={clsx(
|
className={clsx(
|
||||||
"flex justify-center",
|
"flex justify-center",
|
||||||
"pt-docs_4 lg:pt-docs_6 pb-docs_8 lg:pb-docs_4"
|
"pt-docs_4 lg:pt-docs_6 pb-docs_8 lg:pb-docs_4",
|
||||||
|
contentClassName
|
||||||
)}
|
)}
|
||||||
>
|
>
|
||||||
{children}
|
{children}
|
||||||
|
|||||||
@@ -14,6 +14,7 @@ export const WideLayout = ({
|
|||||||
<RootLayout
|
<RootLayout
|
||||||
{...props}
|
{...props}
|
||||||
mainWrapperClasses={clsx(props.mainWrapperClasses, "mx-auto flex")}
|
mainWrapperClasses={clsx(props.mainWrapperClasses, "mx-auto flex")}
|
||||||
|
contentClassName="w-full px-1"
|
||||||
>
|
>
|
||||||
<main
|
<main
|
||||||
className={clsx(
|
className={clsx(
|
||||||
|
|||||||
@@ -25,6 +25,7 @@ export type SidebarItemCategory = SidebarItemCommon & {
|
|||||||
type: "category"
|
type: "category"
|
||||||
onOpen?: () => void
|
onOpen?: () => void
|
||||||
initialOpen?: boolean
|
initialOpen?: boolean
|
||||||
|
showLoadingIfEmpty?: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
export type SidebarItemSubCategory = SidebarItemCommon & {
|
export type SidebarItemSubCategory = SidebarItemCommon & {
|
||||||
|
|||||||
@@ -5582,6 +5582,8 @@ __metadata:
|
|||||||
react-intersection-observer: ^9.5.3
|
react-intersection-observer: ^9.5.3
|
||||||
react-tooltip: ^5.19.0
|
react-tooltip: ^5.19.0
|
||||||
react-transition-group: ^4.4.5
|
react-transition-group: ^4.4.5
|
||||||
|
rehype-mdx-code-props: ^2.0.0
|
||||||
|
rehype-slug: ^6.0.0
|
||||||
slugify: ^1.6.6
|
slugify: ^1.6.6
|
||||||
swr: ^2.2.0
|
swr: ^2.2.0
|
||||||
tailwind: "*"
|
tailwind: "*"
|
||||||
|
|||||||
Reference in New Issue
Block a user