Feat: Medusa react price list (#1258)
* export everything from price lists in core * medusa-js price list * feat: add product list for price lists * feat: add product list for price lists * add price list to admin module * add price list hooks initial * refactor: product list controller * fix: add integration test for price list products * update types * add tests for price lists * update medusa react tests * update update request for price lists * Apply suggestions from code review Co-authored-by: Sebastian Rindom <skrindom@gmail.com> * rename methods * pr feedback * list products from price list * fix errors after merge * update medusa react with medusa-js method name changes * redo changes * update hook names * fix: routes in msw handler Co-authored-by: Sebastian Rindom <skrindom@gmail.com> Co-authored-by: Zakaria El Asri <zakaria.elas@gmail.com>
This commit is contained in:
@@ -10,7 +10,7 @@ Thank you for considering contributing to Medusa! This document will outline how
|
|||||||
|
|
||||||
## Issues before PRs
|
## Issues before PRs
|
||||||
|
|
||||||
1. Before you start working on a change please make sure that there is an issue for what you will be working on. You can either find and [existing issue](https://github.com/medusajs/medusa/issues) or [open a new issue](https://github.com/medusajs/medusa/issues/new) if none exists. Doing this makes sure that others can contribute with thoughts or suggest alternatives, ultimately making sure that we only add changes that make
|
1. Before you start working on a change please make sure that there is an issue for what you will be working on. You can either find and [existing issue](https://github.com/medusajs/medusa/issues) or [open a new issue](https://github.com/medusajs/medusa/issues/new) if none exists. Doing this makes sure that others can contribute with thoughts or suggest alternatives, ultimately making sure that we only add changes that make
|
||||||
|
|
||||||
2. When you are ready to start working on a change you should first [fork the Medusa repo](https://help.github.com/en/github/getting-started-with-github/fork-a-repo) and [branch out](https://help.github.com/en/github/collaborating-with-issues-and-pull-requests/creating-and-deleting-branches-within-your-repository) from the `develop` branch.
|
2. When you are ready to start working on a change you should first [fork the Medusa repo](https://help.github.com/en/github/getting-started-with-github/fork-a-repo) and [branch out](https://help.github.com/en/github/collaborating-with-issues-and-pull-requests/creating-and-deleting-branches-within-your-repository) from the `develop` branch.
|
||||||
3. Make your changes.
|
3. Make your changes.
|
||||||
@@ -21,17 +21,21 @@ Thank you for considering contributing to Medusa! This document will outline how
|
|||||||
### Branches
|
### Branches
|
||||||
|
|
||||||
All changes should be part of a branch and submitted as a pull request - your branches should be prefixed with one of:
|
All changes should be part of a branch and submitted as a pull request - your branches should be prefixed with one of:
|
||||||
|
|
||||||
- `fix/` for bug fixes
|
- `fix/` for bug fixes
|
||||||
- `feat/` for features
|
- `feat/` for features
|
||||||
- `docs/` for documentation changes
|
- `docs/` for documentation changes
|
||||||
|
|
||||||
### Commits
|
### Commits
|
||||||
|
|
||||||
Strive towards keeping your commits small and isolated - this helps the reviewer understand what is going on and makes it easier to process your requests.
|
Strive towards keeping your commits small and isolated - this helps the reviewer understand what is going on and makes it easier to process your requests.
|
||||||
|
|
||||||
### Pull Requests
|
### Pull Requests
|
||||||
Once your changes are ready you must submit your branch as a pull request. Your pull request should be opened against the `develop` branch in the main Medusa repo.
|
|
||||||
|
Once your changes are ready you must submit your branch as a pull request. Your pull request should be opened against the `develop` branch in the main Medusa repo.
|
||||||
|
|
||||||
In your PR's description you should follow the structure:
|
In your PR's description you should follow the structure:
|
||||||
|
|
||||||
- **What** - what changes are in this PR
|
- **What** - what changes are in this PR
|
||||||
- **Why** - why are these changes relevant
|
- **Why** - why are these changes relevant
|
||||||
- **How** - how have the changes been implemented
|
- **How** - how have the changes been implemented
|
||||||
@@ -52,8 +56,8 @@ All PRs should include tests for the changes that are included. We have two type
|
|||||||
|
|
||||||
### Documentation
|
### Documentation
|
||||||
|
|
||||||
- We generally encourage to document your changes through comments in your code.
|
- We generally encourage to document your changes through comments in your code.
|
||||||
- If you alter user-facing behaviour you must provide documentation for such changes.
|
- If you alter user-facing behaviour you must provide documentation for such changes.
|
||||||
- All methods and endpoints should be documented using [JSDoc](https://jsdoc.app/) and [`swagger-inline`](https://www.npmjs.com/package/swagger-inline)
|
- All methods and endpoints should be documented using [JSDoc](https://jsdoc.app/) and [`swagger-inline`](https://www.npmjs.com/package/swagger-inline)
|
||||||
|
|
||||||
### Release
|
### Release
|
||||||
|
|||||||
@@ -67,6 +67,7 @@ After these four steps and only a couple of minutes, you now have a complete com
|
|||||||
Write-ups for all features will be made available in [Github discussions](https://github.com/medusajs/medusa/discussions) prior to starting the implementation process.
|
Write-ups for all features will be made available in [Github discussions](https://github.com/medusajs/medusa/discussions) prior to starting the implementation process.
|
||||||
|
|
||||||
### Q1
|
### Q1
|
||||||
|
|
||||||
- [x] Admin revamp
|
- [x] Admin revamp
|
||||||
- [x] Tax API
|
- [x] Tax API
|
||||||
- [x] Strategy pattern
|
- [x] Strategy pattern
|
||||||
@@ -74,12 +75,13 @@ Write-ups for all features will be made available in [Github discussions](https:
|
|||||||
- [ ] Bulk import / export
|
- [ ] Bulk import / export
|
||||||
|
|
||||||
### Q2
|
### Q2
|
||||||
|
|
||||||
- [ ] Extended Product API (custom fields, price lists, publishing control, and more)
|
- [ ] Extended Product API (custom fields, price lists, publishing control, and more)
|
||||||
- [ ] Extended Order API (managing placed orders, improved inventory control, and more)
|
- [ ] Extended Order API (managing placed orders, improved inventory control, and more)
|
||||||
- [ ] Sales Channel API
|
- [ ] Sales Channel API
|
||||||
- [ ] Multi-warehouse support
|
- [ ] Multi-warehouse support
|
||||||
- [ ] GraphQL API
|
- [ ] GraphQL API
|
||||||
|
|
||||||
## Setting up a storefront for your Medusa project
|
## Setting up a storefront for your Medusa project
|
||||||
|
|
||||||
Medusa is a headless commerce engine which means that it can be used for any type of digital commerce experience - you may use it as the backend for an app, a voice application, social commerce experiences or a traditional e-commerce website, you may even want to integrate Medusa into your own software to enable commerce functionality. All of these are use cases that Medusa supports - to learn more read the documentation or reach out.
|
Medusa is a headless commerce engine which means that it can be used for any type of digital commerce experience - you may use it as the backend for an app, a voice application, social commerce experiences or a traditional e-commerce website, you may even want to integrate Medusa into your own software to enable commerce functionality. All of these are use cases that Medusa supports - to learn more read the documentation or reach out.
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -120,8 +120,8 @@ yarn global add create-strapi-app@3.6.8
|
|||||||
|
|
||||||
create-strapi-app strapi-medusa --template https://github.com/Deathwish98/strapi-medusa-template.git
|
create-strapi-app strapi-medusa --template https://github.com/Deathwish98/strapi-medusa-template.git
|
||||||
```
|
```
|
||||||
> Note: The plugin expects node version to be '>= 10.16.0 and <=14.x.x', otherwise it will throw an error.
|
|
||||||
|
|
||||||
|
> Note: The plugin expects node version to be '>= 10.16.0 and <=14.x.x', otherwise it will throw an error.
|
||||||
|
|
||||||
After running the command, you have a full Strapi project configured to synchronize with Medusa. Upon the initial start of the Strapi server, all the required models will be created. They will correlate with models from Medusa to allow for two-way synchronization.
|
After running the command, you have a full Strapi project configured to synchronize with Medusa. Upon the initial start of the Strapi server, all the required models will be created. They will correlate with models from Medusa to allow for two-way synchronization.
|
||||||
|
|
||||||
|
|||||||
@@ -8,7 +8,6 @@
|
|||||||
</video>
|
</video>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
||||||
### Introduction
|
### Introduction
|
||||||
|
|
||||||
Handling payments is at the core of every commerce system; it allows us to run our businesses. Consequently, a vast landscape of payment providers has developed, each with varying cost models, implementational specifications, and analytical capabilities.
|
Handling payments is at the core of every commerce system; it allows us to run our businesses. Consequently, a vast landscape of payment providers has developed, each with varying cost models, implementational specifications, and analytical capabilities.
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ export default () => {
|
|||||||
|
|
||||||
router.get("/admin/hello", (req, res) => {
|
router.get("/admin/hello", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Welcome to Your Store!"
|
message: "Welcome to Your Store!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
@@ -53,8 +53,8 @@ Then, create an object that will hold the CORS configurations:
|
|||||||
|
|
||||||
```js
|
```js
|
||||||
const corsOptions = {
|
const corsOptions = {
|
||||||
origin: projectConfig.admin_cors.split(","),
|
origin: projectConfig.admin_cors.split(","),
|
||||||
credentials: true,
|
credentials: true,
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -64,7 +64,7 @@ Finally, for each route you add, create an `OPTIONS` request:
|
|||||||
router.options("/admin/hello", cors(corsOptions))
|
router.options("/admin/hello", cors(corsOptions))
|
||||||
router.get("/admin/hello", (req, res) => {
|
router.get("/admin/hello", (req, res) => {
|
||||||
//...
|
//...
|
||||||
});
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
## Multiple Endpoints
|
## Multiple Endpoints
|
||||||
@@ -76,13 +76,13 @@ You can add more than one endpoints in `src/api/index.js`:
|
|||||||
```js
|
```js
|
||||||
router.get("/admin/hello", (req, res) => {
|
router.get("/admin/hello", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Welcome to Your Store!"
|
message: "Welcome to Your Store!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
router.get("/admin/bye", (req, res) => {
|
router.get("/admin/bye", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Come back again!"
|
message: "Come back again!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
@@ -97,7 +97,7 @@ To do that with the previous example, first, create the file `src/api/hello.js`
|
|||||||
export default (router) => {
|
export default (router) => {
|
||||||
router.get("/admin/hello", (req, res) => {
|
router.get("/admin/hello", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Welcome to Your Store!"
|
message: "Welcome to Your Store!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@@ -111,7 +111,7 @@ Next, create the file `src/api/bye.js` with the following content:
|
|||||||
export default (router) => {
|
export default (router) => {
|
||||||
router.get("/admin/bye", (req, res) => {
|
router.get("/admin/bye", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Come back again!"
|
message: "Come back again!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@@ -148,17 +148,15 @@ You can retrieve any registered service in your endpoint using `req.scope.resolv
|
|||||||
Here’s an example of an endpoint that retrieves the count of products in your store:
|
Here’s an example of an endpoint that retrieves the count of products in your store:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
router.get('/admin/products/count', (req, res) => {
|
router.get("/admin/products/count", (req, res) => {
|
||||||
const productService = req.scope.resolve('productService')
|
const productService = req.scope.resolve("productService")
|
||||||
|
|
||||||
productService
|
productService.count().then((count) => {
|
||||||
.count()
|
res.json({
|
||||||
.then((count) => {
|
count,
|
||||||
res.json({
|
})
|
||||||
count
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
})
|
||||||
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
The `productService` has a `count` method that returns a Promise. This Promise resolves to the count of the products. You return a JSON of the product count.
|
The `productService` has a `count` method that returns a Promise. This Promise resolves to the count of the products. You return a JSON of the product count.
|
||||||
@@ -170,13 +168,13 @@ Protected routes are routes that should be accessible by logged-in users only.
|
|||||||
To make a route protected, first, import the `authenticate` middleware:
|
To make a route protected, first, import the `authenticate` middleware:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import authenticate from '@medusajs/medusa/dist/api/middlewares/authenticate'
|
import authenticate from "@medusajs/medusa/dist/api/middlewares/authenticate"
|
||||||
```
|
```
|
||||||
|
|
||||||
Then, add the middleware to your route:
|
Then, add the middleware to your route:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
router.get('/store/products/count', authenticate(), (req, res) => {
|
router.get("/store/products/count", authenticate(), (req, res) => {
|
||||||
//...
|
//...
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ export default () => {
|
|||||||
|
|
||||||
router.get("/store/hello", (req, res) => {
|
router.get("/store/hello", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Welcome to My Store!"
|
message: "Welcome to My Store!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
@@ -47,13 +47,13 @@ You can add more than one endpoints in `src/api/index.js`:
|
|||||||
```js
|
```js
|
||||||
router.get("/store/hello", (req, res) => {
|
router.get("/store/hello", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Welcome to My Store!"
|
message: "Welcome to My Store!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
router.get("/store/bye", (req, res) => {
|
router.get("/store/bye", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Come back again!"
|
message: "Come back again!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
@@ -68,7 +68,7 @@ To do that with the previous example, first, create the file `src/api/hello.js`
|
|||||||
export default (router) => {
|
export default (router) => {
|
||||||
router.get("/store/hello", (req, res) => {
|
router.get("/store/hello", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Welcome to My Store!"
|
message: "Welcome to My Store!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@@ -82,7 +82,7 @@ Next, create the file `src/api/bye.js` with the following content:
|
|||||||
export default (router) => {
|
export default (router) => {
|
||||||
router.get("/store/bye", (req, res) => {
|
router.get("/store/bye", (req, res) => {
|
||||||
res.json({
|
res.json({
|
||||||
message: "Come back again!"
|
message: "Come back again!",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@@ -119,17 +119,15 @@ You can retrieve any registered service in your endpoint using `req.scope.resolv
|
|||||||
Here’s an example of an endpoint that retrieves the count of products in your store:
|
Here’s an example of an endpoint that retrieves the count of products in your store:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
router.get('/store/products/count', (req, res) => {
|
router.get("/store/products/count", (req, res) => {
|
||||||
const productService = req.scope.resolve('productService')
|
const productService = req.scope.resolve("productService")
|
||||||
|
|
||||||
productService
|
productService.count().then((count) => {
|
||||||
.count()
|
res.json({
|
||||||
.then((count) => {
|
count,
|
||||||
res.json({
|
})
|
||||||
count
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
})
|
||||||
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
The `productService` has a `count` method that returns a Promise. This Promise resolves to the count of the products. You return a JSON of the product count.
|
The `productService` has a `count` method that returns a Promise. This Promise resolves to the count of the products. You return a JSON of the product count.
|
||||||
@@ -141,13 +139,13 @@ Protected routes are routes that should be accessible by logged-in customers onl
|
|||||||
To make a route protected, first, import the `authenticate` middleware:
|
To make a route protected, first, import the `authenticate` middleware:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import authenticate from '@medusajs/medusa/dist/api/middlewares/authenticate'
|
import authenticate from "@medusajs/medusa/dist/api/middlewares/authenticate"
|
||||||
```
|
```
|
||||||
|
|
||||||
Then, add the middleware to your route:
|
Then, add the middleware to your route:
|
||||||
|
|
||||||
```jsx
|
```jsx
|
||||||
router.get('/store/products/count', authenticate(), (req, res) => {
|
router.get("/store/products/count", authenticate(), (req, res) => {
|
||||||
//...
|
//...
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|||||||
@@ -1,7 +1,5 @@
|
|||||||
---
|
---
|
||||||
|
|
||||||
title: Create a Service
|
title: Create a Service
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
# Create a Service
|
# Create a Service
|
||||||
@@ -31,7 +29,7 @@ To create a service, you should create a JavaScript file in `src/services` to ho
|
|||||||
For example, if you want to create a service `helloService`, create the file `hello.js` in `src/services` with the following content:
|
For example, if you want to create a service `helloService`, create the file `hello.js` in `src/services` with the following content:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
import { BaseService } from "medusa-interfaces";
|
import { BaseService } from "medusa-interfaces"
|
||||||
|
|
||||||
class HelloService extends BaseService {
|
class HelloService extends BaseService {
|
||||||
getMessage() {
|
getMessage() {
|
||||||
@@ -39,7 +37,7 @@ class HelloService extends BaseService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export default HelloService;
|
export default HelloService
|
||||||
```
|
```
|
||||||
|
|
||||||
## Service Constructor
|
## Service Constructor
|
||||||
@@ -85,10 +83,10 @@ constructor({ helloService }) {
|
|||||||
To use your custom service in an endpoint, you can use `req.scope.resolve` passing it the service’s registration name:
|
To use your custom service in an endpoint, you can use `req.scope.resolve` passing it the service’s registration name:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
const helloService = req.scope.resolve('helloService');
|
const helloService = req.scope.resolve("helloService")
|
||||||
|
|
||||||
res.json({
|
res.json({
|
||||||
message: helloService.getMessage()
|
message: helloService.getMessage(),
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,5 @@
|
|||||||
---
|
---
|
||||||
|
|
||||||
title: Introduction
|
title: Introduction
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
## Architecture overview
|
## Architecture overview
|
||||||
@@ -18,11 +16,11 @@ Your Medusa server will include all functionalities related to your store’s ch
|
|||||||
|
|
||||||
### Admin Dashboard
|
### Admin Dashboard
|
||||||
|
|
||||||
The admin dashboard is accessible by store operators. Store operators can use the admin dashboard to view, create, and modify data such as orders and products.
|
The admin dashboard is accessible by store operators. Store operators can use the admin dashboard to view, create, and modify data such as orders and products.
|
||||||
|
|
||||||
Medusa provides a beautiful [admin dashboard](https://demo.medusajs.com) that you can use right off the bat. Our admin dashboard provides a lot of functionalities to manage your store including Order management, product management, user management and more.
|
Medusa provides a beautiful [admin dashboard](https://demo.medusajs.com) that you can use right off the bat. Our admin dashboard provides a lot of functionalities to manage your store including Order management, product management, user management and more.
|
||||||
|
|
||||||
You can also create your own admin dashboard by utilizing the [Admin REST APIs](https://docs.medusajs.com/api/admin/auth).
|
You can also create your own admin dashboard by utilizing the [Admin REST APIs](https://docs.medusajs.com/api/admin/auth).
|
||||||
|
|
||||||
### Storefront
|
### Storefront
|
||||||
|
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ import AdminRegionsResource from "./regions"
|
|||||||
import AdminNotificationsResource from "./notifications"
|
import AdminNotificationsResource from "./notifications"
|
||||||
import AdminUploadsResource from "./uploads"
|
import AdminUploadsResource from "./uploads"
|
||||||
import AdminProductTagsResource from "./product-tags"
|
import AdminProductTagsResource from "./product-tags"
|
||||||
|
import AdminPriceListResource from "./price-lists"
|
||||||
|
|
||||||
class Admin extends BaseResource {
|
class Admin extends BaseResource {
|
||||||
public auth = new AdminAuthResource(this.client)
|
public auth = new AdminAuthResource(this.client)
|
||||||
@@ -35,6 +36,7 @@ class Admin extends BaseResource {
|
|||||||
public giftCards = new AdminGiftCardsResource(this.client)
|
public giftCards = new AdminGiftCardsResource(this.client)
|
||||||
public invites = new AdminInvitesResource(this.client)
|
public invites = new AdminInvitesResource(this.client)
|
||||||
public notes = new AdminNotesResource(this.client)
|
public notes = new AdminNotesResource(this.client)
|
||||||
|
public priceLists = new AdminPriceListResource(this.client)
|
||||||
public products = new AdminProductsResource(this.client)
|
public products = new AdminProductsResource(this.client)
|
||||||
public productTags = new AdminProductTagsResource(this.client)
|
public productTags = new AdminProductTagsResource(this.client)
|
||||||
public productTypes = new AdminProductTypesResource(this.client)
|
public productTypes = new AdminProductTypesResource(this.client)
|
||||||
|
|||||||
99
packages/medusa-js/src/resources/admin/price-lists.ts
Normal file
99
packages/medusa-js/src/resources/admin/price-lists.ts
Normal file
@@ -0,0 +1,99 @@
|
|||||||
|
import {
|
||||||
|
AdminPostPriceListPricesPricesReq,
|
||||||
|
AdminPostPriceListsPriceListPriceListReq,
|
||||||
|
AdminPostPriceListsPriceListReq,
|
||||||
|
AdminPriceListDeleteRes,
|
||||||
|
AdminPriceListRes,
|
||||||
|
AdminGetPriceListPaginationParams,
|
||||||
|
AdminPriceListsListRes,
|
||||||
|
AdminDeletePriceListPricesPricesReq,
|
||||||
|
AdminPriceListDeleteBatchRes,
|
||||||
|
AdminGetPriceListsPriceListProductsParams,
|
||||||
|
} from "@medusajs/medusa"
|
||||||
|
import qs from "qs"
|
||||||
|
import { ResponsePromise } from "../../typings"
|
||||||
|
import BaseResource from "../base"
|
||||||
|
|
||||||
|
class AdminPriceListResource extends BaseResource {
|
||||||
|
create(
|
||||||
|
payload: AdminPostPriceListsPriceListReq,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<AdminPriceListRes> {
|
||||||
|
const path = `/admin/price-lists`
|
||||||
|
return this.client.request("POST", path, payload, {}, customHeaders)
|
||||||
|
}
|
||||||
|
|
||||||
|
update(
|
||||||
|
id: string,
|
||||||
|
payload: AdminPostPriceListsPriceListPriceListReq,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<AdminPriceListRes> {
|
||||||
|
const path = `/admin/price-lists/${id}`
|
||||||
|
return this.client.request("POST", path, payload, {}, customHeaders)
|
||||||
|
}
|
||||||
|
|
||||||
|
delete(
|
||||||
|
id: string,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<AdminPriceListDeleteRes> {
|
||||||
|
const path = `/admin/price-lists/${id}`
|
||||||
|
return this.client.request("DELETE", path, {}, {}, customHeaders)
|
||||||
|
}
|
||||||
|
|
||||||
|
retrieve(
|
||||||
|
id: string,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<AdminPriceListRes> {
|
||||||
|
const path = `/admin/price-lists/${id}`
|
||||||
|
return this.client.request("GET", path, {}, {}, customHeaders)
|
||||||
|
}
|
||||||
|
|
||||||
|
list(
|
||||||
|
query?: AdminGetPriceListPaginationParams,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<AdminPriceListsListRes> {
|
||||||
|
let path = `/admin/price-lists/`
|
||||||
|
|
||||||
|
if (query) {
|
||||||
|
const queryString = qs.stringify(query)
|
||||||
|
path = `/admin/price-lists?${queryString}`
|
||||||
|
}
|
||||||
|
|
||||||
|
return this.client.request("GET", path, {}, {}, customHeaders)
|
||||||
|
}
|
||||||
|
|
||||||
|
listProducts(
|
||||||
|
id: string,
|
||||||
|
query?: AdminGetPriceListsPriceListProductsParams,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<any> {
|
||||||
|
let path = `/admin/price-lists/${id}/products`
|
||||||
|
|
||||||
|
if (query) {
|
||||||
|
const queryString = qs.stringify(query)
|
||||||
|
path = `/admin/price-lists/${id}/products?${queryString}`
|
||||||
|
}
|
||||||
|
|
||||||
|
return this.client.request("GET", path, {}, {}, customHeaders)
|
||||||
|
}
|
||||||
|
|
||||||
|
addPrices(
|
||||||
|
id: string,
|
||||||
|
payload: AdminPostPriceListPricesPricesReq,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<AdminPriceListRes> {
|
||||||
|
const path = `/admin/price-lists/${id}/prices/batch`
|
||||||
|
return this.client.request("POST", path, payload, {}, customHeaders)
|
||||||
|
}
|
||||||
|
|
||||||
|
deletePrices(
|
||||||
|
id: string,
|
||||||
|
payload: AdminDeletePriceListPricesPricesReq,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<AdminPriceListDeleteBatchRes> {
|
||||||
|
const path = `/admin/price-lists/${id}/prices/batch`
|
||||||
|
return this.client.request("DELETE", path, payload, {}, customHeaders)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export default AdminPriceListResource
|
||||||
@@ -22,7 +22,10 @@ class CustomerResource extends BaseResource {
|
|||||||
* @param customHeaders
|
* @param customHeaders
|
||||||
* @return { ResponsePromise<StoreCustomersRes>}
|
* @return { ResponsePromise<StoreCustomersRes>}
|
||||||
*/
|
*/
|
||||||
create(payload: StorePostCustomersReq, customHeaders: Record<string, any> = {}): ResponsePromise<StoreCustomersRes> {
|
create(
|
||||||
|
payload: StorePostCustomersReq,
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<StoreCustomersRes> {
|
||||||
const path = `/store/customers`
|
const path = `/store/customers`
|
||||||
return this.client.request("POST", path, payload, {}, customHeaders)
|
return this.client.request("POST", path, payload, {}, customHeaders)
|
||||||
}
|
}
|
||||||
@@ -32,7 +35,9 @@ class CustomerResource extends BaseResource {
|
|||||||
* @param customHeaders
|
* @param customHeaders
|
||||||
* @return {ResponsePromise<StoreCustomersRes>}
|
* @return {ResponsePromise<StoreCustomersRes>}
|
||||||
*/
|
*/
|
||||||
retrieve(customHeaders: Record<string, any> = {}): ResponsePromise<StoreCustomersRes> {
|
retrieve(
|
||||||
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<StoreCustomersRes> {
|
||||||
const path = `/store/customers/me`
|
const path = `/store/customers/me`
|
||||||
return this.client.request("GET", path, {}, {}, customHeaders)
|
return this.client.request("GET", path, {}, {}, customHeaders)
|
||||||
}
|
}
|
||||||
@@ -45,7 +50,8 @@ class CustomerResource extends BaseResource {
|
|||||||
*/
|
*/
|
||||||
update(
|
update(
|
||||||
payload: StorePostCustomersCustomerReq,
|
payload: StorePostCustomersCustomerReq,
|
||||||
customHeaders: Record<string, any> = {}): ResponsePromise<StoreCustomersRes> {
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<StoreCustomersRes> {
|
||||||
const path = `/store/customers/me`
|
const path = `/store/customers/me`
|
||||||
return this.client.request("POST", path, payload, {}, customHeaders)
|
return this.client.request("POST", path, payload, {}, customHeaders)
|
||||||
}
|
}
|
||||||
@@ -58,7 +64,8 @@ class CustomerResource extends BaseResource {
|
|||||||
*/
|
*/
|
||||||
listOrders(
|
listOrders(
|
||||||
params?: StoreGetCustomersCustomerOrdersParams,
|
params?: StoreGetCustomersCustomerOrdersParams,
|
||||||
customHeaders: Record<string, any> = {}): ResponsePromise<StoreCustomersListOrdersRes> {
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<StoreCustomersListOrdersRes> {
|
||||||
let path = `/store/customers/me/orders`
|
let path = `/store/customers/me/orders`
|
||||||
if (params) {
|
if (params) {
|
||||||
const query = qs.stringify(params)
|
const query = qs.stringify(params)
|
||||||
@@ -77,7 +84,8 @@ class CustomerResource extends BaseResource {
|
|||||||
*/
|
*/
|
||||||
resetPassword(
|
resetPassword(
|
||||||
payload: StorePostCustomersCustomerPasswordTokenReq,
|
payload: StorePostCustomersCustomerPasswordTokenReq,
|
||||||
customHeaders: Record<string, any> = {}): ResponsePromise<StoreCustomersRes> {
|
customHeaders: Record<string, any> = {}
|
||||||
|
): ResponsePromise<StoreCustomersRes> {
|
||||||
const path = `/store/customers/password-reset`
|
const path = `/store/customers/password-reset`
|
||||||
return this.client.request("POST", path, payload, {}, customHeaders)
|
return this.client.request("POST", path, payload, {}, customHeaders)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1076,6 +1076,18 @@
|
|||||||
"deleted_at": null,
|
"deleted_at": null,
|
||||||
"metadata": null
|
"metadata": null
|
||||||
},
|
},
|
||||||
|
"price_list": {
|
||||||
|
"id": "pl_ZXDBABWJVW6115VEMZXDBAB",
|
||||||
|
"name": "test price list",
|
||||||
|
"description": "test price list",
|
||||||
|
"type": "products",
|
||||||
|
"status": "active",
|
||||||
|
"starts_at": null,
|
||||||
|
"ends_at": null,
|
||||||
|
"created_at": "2021-03-16T21:24:35.828Z",
|
||||||
|
"updated_at": "2021-03-16T21:24:35.828Z",
|
||||||
|
"deleted_at": null
|
||||||
|
},
|
||||||
"note": {
|
"note": {
|
||||||
"id": "note_01F0ZXDBAB9KVZWJVW6115VEM7",
|
"id": "note_01F0ZXDBAB9KVZWJVW6115VEM7",
|
||||||
"value": "customer contacted",
|
"value": "customer contacted",
|
||||||
|
|||||||
@@ -170,6 +170,89 @@ export const adminHandlers = [
|
|||||||
)
|
)
|
||||||
}),
|
}),
|
||||||
|
|
||||||
|
rest.post("/admin/price-lists/", (req, res, ctx) => {
|
||||||
|
const body = req.body as Record<string, any>
|
||||||
|
return res(
|
||||||
|
ctx.status(200),
|
||||||
|
ctx.json({
|
||||||
|
price_list: {
|
||||||
|
...fixtures.get("price_list"),
|
||||||
|
...body,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
)
|
||||||
|
}),
|
||||||
|
|
||||||
|
rest.get("/admin/price-lists/", (req, res, ctx) => {
|
||||||
|
return res(
|
||||||
|
ctx.status(200),
|
||||||
|
ctx.json({
|
||||||
|
price_lists: fixtures.list("price_list"),
|
||||||
|
count: 2,
|
||||||
|
offset: 0,
|
||||||
|
limit: 10,
|
||||||
|
})
|
||||||
|
)
|
||||||
|
}),
|
||||||
|
|
||||||
|
rest.get("/admin/price-lists/:id", (req, res, ctx) => {
|
||||||
|
return res(
|
||||||
|
ctx.status(200),
|
||||||
|
ctx.json({
|
||||||
|
price_list: fixtures.get("price_list"),
|
||||||
|
})
|
||||||
|
)
|
||||||
|
}),
|
||||||
|
|
||||||
|
rest.post("/admin/price-lists/:id", (req, res, ctx) => {
|
||||||
|
const body = req.body as Record<string, any>
|
||||||
|
return res(
|
||||||
|
ctx.status(200),
|
||||||
|
ctx.json({
|
||||||
|
price_list: {
|
||||||
|
...fixtures.get("price_list"),
|
||||||
|
...body,
|
||||||
|
id: req.params.id,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
)
|
||||||
|
}),
|
||||||
|
|
||||||
|
rest.delete("/admin/price-lists/:id", (req, res, ctx) => {
|
||||||
|
return res(
|
||||||
|
ctx.status(200),
|
||||||
|
ctx.json({
|
||||||
|
id: req.params.id,
|
||||||
|
object: "price_list",
|
||||||
|
deleted: true,
|
||||||
|
})
|
||||||
|
)
|
||||||
|
}),
|
||||||
|
|
||||||
|
rest.delete("/admin/price-lists/:id/prices/batch", (req, res, ctx) => {
|
||||||
|
const body = req.body as Record<string, any>
|
||||||
|
return res(
|
||||||
|
ctx.status(200),
|
||||||
|
ctx.json({
|
||||||
|
ids: body.price_ids,
|
||||||
|
object: "money-amount",
|
||||||
|
deleted: true,
|
||||||
|
})
|
||||||
|
)
|
||||||
|
}),
|
||||||
|
|
||||||
|
rest.post("/admin/price-lists/:id/prices/batch", (req, res, ctx) => {
|
||||||
|
return res(
|
||||||
|
ctx.status(200),
|
||||||
|
ctx.json({
|
||||||
|
price_list: {
|
||||||
|
...fixtures.get("price_list"),
|
||||||
|
id: req.params.id,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
)
|
||||||
|
}),
|
||||||
|
|
||||||
rest.post("/admin/return-reasons/", (req, res, ctx) => {
|
rest.post("/admin/return-reasons/", (req, res, ctx) => {
|
||||||
const body = req.body as Record<string, any>
|
const body = req.body as Record<string, any>
|
||||||
return res(
|
return res(
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ export * from "./orders"
|
|||||||
export * from "./products"
|
export * from "./products"
|
||||||
export * from "./product-tags"
|
export * from "./product-tags"
|
||||||
export * from "./product-types"
|
export * from "./product-types"
|
||||||
|
export * from "./price-lists"
|
||||||
export * from "./return-reasons"
|
export * from "./return-reasons"
|
||||||
export * from "./regions"
|
export * from "./regions"
|
||||||
export * from "./shipping-options"
|
export * from "./shipping-options"
|
||||||
|
|||||||
@@ -0,0 +1,2 @@
|
|||||||
|
export * from "./queries"
|
||||||
|
export * from "./mutations"
|
||||||
108
packages/medusa-react/src/hooks/admin/price-lists/mutations.ts
Normal file
108
packages/medusa-react/src/hooks/admin/price-lists/mutations.ts
Normal file
@@ -0,0 +1,108 @@
|
|||||||
|
import {
|
||||||
|
AdminPriceListRes,
|
||||||
|
AdminPostPriceListsPriceListPriceListReq,
|
||||||
|
AdminPostPriceListsPriceListReq,
|
||||||
|
AdminPostPriceListPricesPricesReq,
|
||||||
|
AdminDeletePriceListPricesPricesReq,
|
||||||
|
AdminPriceListDeleteRes,
|
||||||
|
AdminPriceListDeleteBatchRes,
|
||||||
|
} from "@medusajs/medusa"
|
||||||
|
import { Response } from "@medusajs/medusa-js"
|
||||||
|
import { useMutation, UseMutationOptions, useQueryClient } from "react-query"
|
||||||
|
import { useMedusa } from "../../../contexts/medusa"
|
||||||
|
import { buildOptions } from "../../utils/buildOptions"
|
||||||
|
import { adminPriceListKeys } from "./queries"
|
||||||
|
|
||||||
|
export const useAdminCreatePriceList = (
|
||||||
|
options?: UseMutationOptions<
|
||||||
|
Response<AdminPriceListRes>,
|
||||||
|
Error,
|
||||||
|
AdminPostPriceListsPriceListReq
|
||||||
|
>
|
||||||
|
) => {
|
||||||
|
const { client } = useMedusa()
|
||||||
|
const queryClient = useQueryClient()
|
||||||
|
return useMutation(
|
||||||
|
(payload: AdminPostPriceListsPriceListReq) =>
|
||||||
|
client.admin.priceLists.create(payload),
|
||||||
|
buildOptions(queryClient, adminPriceListKeys.lists(), options)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useAdminUpdatePriceList = (
|
||||||
|
id: string,
|
||||||
|
options?: UseMutationOptions<
|
||||||
|
Response<AdminPriceListRes>,
|
||||||
|
Error,
|
||||||
|
AdminPostPriceListsPriceListPriceListReq
|
||||||
|
>
|
||||||
|
) => {
|
||||||
|
const { client } = useMedusa()
|
||||||
|
const queryClient = useQueryClient()
|
||||||
|
|
||||||
|
return useMutation(
|
||||||
|
(payload: AdminPostPriceListsPriceListPriceListReq) =>
|
||||||
|
client.admin.priceLists.update(id, payload),
|
||||||
|
buildOptions(
|
||||||
|
queryClient,
|
||||||
|
[adminPriceListKeys.detail(id), adminPriceListKeys.lists()],
|
||||||
|
options
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useAdminDeletePriceList = (
|
||||||
|
id: string,
|
||||||
|
options?: UseMutationOptions<Response<AdminPriceListDeleteRes>, Error, void>
|
||||||
|
) => {
|
||||||
|
const { client } = useMedusa()
|
||||||
|
const queryClient = useQueryClient()
|
||||||
|
|
||||||
|
return useMutation(
|
||||||
|
() => client.admin.priceLists.delete(id),
|
||||||
|
buildOptions(
|
||||||
|
queryClient,
|
||||||
|
[adminPriceListKeys.detail(id), adminPriceListKeys.lists()],
|
||||||
|
options
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useAdminCreatePriceListPrices = (
|
||||||
|
id: string,
|
||||||
|
options?: UseMutationOptions<
|
||||||
|
Response<AdminPriceListRes>,
|
||||||
|
Error,
|
||||||
|
AdminPostPriceListPricesPricesReq
|
||||||
|
>
|
||||||
|
) => {
|
||||||
|
const { client } = useMedusa()
|
||||||
|
const queryClient = useQueryClient()
|
||||||
|
return useMutation(
|
||||||
|
(payload: AdminPostPriceListPricesPricesReq) =>
|
||||||
|
client.admin.priceLists.addPrices(id, payload),
|
||||||
|
buildOptions(queryClient, adminPriceListKeys.lists(), options)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useAdminDeletePriceListPrices = (
|
||||||
|
id: string,
|
||||||
|
options?: UseMutationOptions<
|
||||||
|
Response<AdminPriceListDeleteBatchRes>,
|
||||||
|
Error,
|
||||||
|
AdminDeletePriceListPricesPricesReq
|
||||||
|
>
|
||||||
|
) => {
|
||||||
|
const { client } = useMedusa()
|
||||||
|
const queryClient = useQueryClient()
|
||||||
|
|
||||||
|
return useMutation(
|
||||||
|
(payload: AdminDeletePriceListPricesPricesReq) =>
|
||||||
|
client.admin.priceLists.deletePrices(id, payload),
|
||||||
|
buildOptions(
|
||||||
|
queryClient,
|
||||||
|
[adminPriceListKeys.detail(id), adminPriceListKeys.lists()],
|
||||||
|
options
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
70
packages/medusa-react/src/hooks/admin/price-lists/queries.ts
Normal file
70
packages/medusa-react/src/hooks/admin/price-lists/queries.ts
Normal file
@@ -0,0 +1,70 @@
|
|||||||
|
import {
|
||||||
|
AdminGetPriceListsPriceListProductsParams,
|
||||||
|
AdminGetPriceListPaginationParams,
|
||||||
|
AdminPriceListsListRes,
|
||||||
|
AdminPriceListRes,
|
||||||
|
AdminProductsListRes,
|
||||||
|
} from "@medusajs/medusa"
|
||||||
|
import { Response } from "@medusajs/medusa-js"
|
||||||
|
import { useQuery } from "react-query"
|
||||||
|
import { useMedusa } from "../../../contexts"
|
||||||
|
import { UseQueryOptionsWrapper } from "../../../types"
|
||||||
|
import { queryKeysFactory } from "../../utils/index"
|
||||||
|
|
||||||
|
const ADMIN_PRICE_LISTS_QUERY_KEY = `admin_price_lists` as const
|
||||||
|
|
||||||
|
export const adminPriceListKeys = queryKeysFactory(ADMIN_PRICE_LISTS_QUERY_KEY)
|
||||||
|
|
||||||
|
type PriceListQueryKeys = typeof adminPriceListKeys
|
||||||
|
|
||||||
|
export const useAdminPriceLists = (
|
||||||
|
query?: AdminGetPriceListPaginationParams,
|
||||||
|
options?: UseQueryOptionsWrapper<
|
||||||
|
Response<AdminPriceListsListRes>,
|
||||||
|
Error,
|
||||||
|
ReturnType<PriceListQueryKeys["list"]>
|
||||||
|
>
|
||||||
|
) => {
|
||||||
|
const { client } = useMedusa()
|
||||||
|
const { data, ...rest } = useQuery(
|
||||||
|
adminPriceListKeys.list(query),
|
||||||
|
() => client.admin.priceLists.list(query),
|
||||||
|
options
|
||||||
|
)
|
||||||
|
return { ...data, ...rest } as const
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useAdminPriceListProducts = (
|
||||||
|
id: string,
|
||||||
|
query?: AdminGetPriceListsPriceListProductsParams,
|
||||||
|
options?: UseQueryOptionsWrapper<
|
||||||
|
Response<AdminProductsListRes>,
|
||||||
|
Error,
|
||||||
|
ReturnType<PriceListQueryKeys["detail"]>
|
||||||
|
>
|
||||||
|
) => {
|
||||||
|
const { client } = useMedusa()
|
||||||
|
const { data, ...rest } = useQuery(
|
||||||
|
adminPriceListKeys.detail(id),
|
||||||
|
() => client.admin.priceLists.listProducts(id, query),
|
||||||
|
options
|
||||||
|
)
|
||||||
|
return { ...data, ...rest } as const
|
||||||
|
}
|
||||||
|
|
||||||
|
export const useAdminPriceList = (
|
||||||
|
id: string,
|
||||||
|
options?: UseQueryOptionsWrapper<
|
||||||
|
Response<AdminPriceListRes>,
|
||||||
|
Error,
|
||||||
|
ReturnType<PriceListQueryKeys["detail"]>
|
||||||
|
>
|
||||||
|
) => {
|
||||||
|
const { client } = useMedusa()
|
||||||
|
const { data, ...rest } = useQuery(
|
||||||
|
adminPriceListKeys.detail(id),
|
||||||
|
() => client.admin.priceLists.retrieve(id),
|
||||||
|
options
|
||||||
|
)
|
||||||
|
return { ...data, ...rest } as const
|
||||||
|
}
|
||||||
@@ -0,0 +1,139 @@
|
|||||||
|
import {
|
||||||
|
useAdminCreatePriceList,
|
||||||
|
useAdminCreatePriceListPrices,
|
||||||
|
useAdminDeletePriceList,
|
||||||
|
useAdminDeletePriceListPrices,
|
||||||
|
useAdminUpdatePriceList,
|
||||||
|
} from "../../../../src"
|
||||||
|
import { renderHook } from "@testing-library/react-hooks"
|
||||||
|
import { fixtures } from "../../../../mocks/data"
|
||||||
|
import { createWrapper } from "../../../utils"
|
||||||
|
|
||||||
|
import { PriceListType } from "@medusajs/medusa/dist/types/price-list"
|
||||||
|
|
||||||
|
describe("useAdminCreatePriceList hook", () => {
|
||||||
|
test("creates a price list and returns it", async () => {
|
||||||
|
const priceList = {
|
||||||
|
name: "talked to customer",
|
||||||
|
type: PriceListType.SALE,
|
||||||
|
description: "test",
|
||||||
|
prices: [],
|
||||||
|
}
|
||||||
|
|
||||||
|
const { result, waitFor } = renderHook(() => useAdminCreatePriceList(), {
|
||||||
|
wrapper: createWrapper(),
|
||||||
|
})
|
||||||
|
|
||||||
|
result.current.mutate(priceList)
|
||||||
|
|
||||||
|
await waitFor(() => result.current.isSuccess)
|
||||||
|
|
||||||
|
expect(result.current.data.response.status).toEqual(200)
|
||||||
|
expect(result.current.data.price_list).toEqual(
|
||||||
|
expect.objectContaining({
|
||||||
|
...fixtures.get("price_list"),
|
||||||
|
...priceList,
|
||||||
|
})
|
||||||
|
)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
describe("useAdminUpdatePriceList hook", () => {
|
||||||
|
test("updates a price list and returns it", async () => {
|
||||||
|
const priceList = {
|
||||||
|
name: "talked to customer",
|
||||||
|
type: PriceListType.SALE,
|
||||||
|
prices: [],
|
||||||
|
customer_groups: [],
|
||||||
|
}
|
||||||
|
|
||||||
|
const { result, waitFor } = renderHook(
|
||||||
|
() => useAdminUpdatePriceList(fixtures.get("price_list").id),
|
||||||
|
{
|
||||||
|
wrapper: createWrapper(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
result.current.mutate(priceList)
|
||||||
|
|
||||||
|
await waitFor(() => result.current.isSuccess)
|
||||||
|
|
||||||
|
expect(result.current.data.response.status).toEqual(200)
|
||||||
|
expect(result.current.data.price_list).toEqual(
|
||||||
|
expect.objectContaining({
|
||||||
|
...fixtures.get("price_list"),
|
||||||
|
...priceList,
|
||||||
|
})
|
||||||
|
)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
describe("useAdminDeletePriceList hook", () => {
|
||||||
|
test("deletes a price list", async () => {
|
||||||
|
const { result, waitFor } = renderHook(
|
||||||
|
() => useAdminDeletePriceList(fixtures.get("price_list").id),
|
||||||
|
{
|
||||||
|
wrapper: createWrapper(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
result.current.mutate()
|
||||||
|
|
||||||
|
await waitFor(() => result.current.isSuccess)
|
||||||
|
|
||||||
|
expect(result.current.data.response.status).toEqual(200)
|
||||||
|
expect(result.current.data).toEqual(
|
||||||
|
expect.objectContaining({
|
||||||
|
id: fixtures.get("price_list").id,
|
||||||
|
deleted: true,
|
||||||
|
})
|
||||||
|
)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
describe("useAdminDeletePriceListBatch hook", () => {
|
||||||
|
test("deletes a money amounts from price list", async () => {
|
||||||
|
const { result, waitFor } = renderHook(
|
||||||
|
() => useAdminDeletePriceListPrices(fixtures.get("price_list").id),
|
||||||
|
{
|
||||||
|
wrapper: createWrapper(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
result.current.mutate({ price_ids: [fixtures.get("money_amount").id] })
|
||||||
|
|
||||||
|
await waitFor(() => result.current.isSuccess)
|
||||||
|
|
||||||
|
expect(result.current.data.response.status).toEqual(200)
|
||||||
|
expect(result.current.data).toEqual(
|
||||||
|
expect.objectContaining({
|
||||||
|
ids: [fixtures.get("money_amount").id],
|
||||||
|
deleted: true,
|
||||||
|
})
|
||||||
|
)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
describe("useAdminDeletePriceList hook", () => {
|
||||||
|
test("Adds prices to price list", async () => {
|
||||||
|
const { result, waitFor } = renderHook(
|
||||||
|
() => useAdminCreatePriceListPrices(fixtures.get("price_list").id),
|
||||||
|
{
|
||||||
|
wrapper: createWrapper(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
result.current.mutate({ prices: [] })
|
||||||
|
|
||||||
|
await waitFor(() => result.current.isSuccess)
|
||||||
|
|
||||||
|
expect(result.current.data.response.status).toEqual(200)
|
||||||
|
expect(result.current.data).toEqual(
|
||||||
|
expect.objectContaining({
|
||||||
|
price_list: {
|
||||||
|
...fixtures.get("price_list"),
|
||||||
|
},
|
||||||
|
})
|
||||||
|
)
|
||||||
|
})
|
||||||
|
})
|
||||||
@@ -0,0 +1,35 @@
|
|||||||
|
import { useAdminPriceList, useAdminPriceLists } from "../../../../src"
|
||||||
|
import { renderHook } from "@testing-library/react-hooks"
|
||||||
|
import { fixtures } from "../../../../mocks/data"
|
||||||
|
import { createWrapper } from "../../../utils"
|
||||||
|
|
||||||
|
describe("useAdminPriceLists hook", () => {
|
||||||
|
test("returns a list of price lists", async () => {
|
||||||
|
const priceLists = fixtures.list("price_list")
|
||||||
|
const { result, waitFor } = renderHook(() => useAdminPriceLists(), {
|
||||||
|
wrapper: createWrapper(),
|
||||||
|
})
|
||||||
|
|
||||||
|
await waitFor(() => result.current.isSuccess)
|
||||||
|
|
||||||
|
expect(result.current.response.status).toEqual(200)
|
||||||
|
expect(result.current.price_lists).toEqual(priceLists)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
describe("useAdminPriceList hook", () => {
|
||||||
|
test("returns a price list", async () => {
|
||||||
|
const priceList = fixtures.get("price_list")
|
||||||
|
const { result, waitFor } = renderHook(
|
||||||
|
() => useAdminPriceList(priceList.id),
|
||||||
|
{
|
||||||
|
wrapper: createWrapper(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
await waitFor(() => result.current.isSuccess)
|
||||||
|
|
||||||
|
expect(result.current.response.status).toEqual(200)
|
||||||
|
expect(result.current.price_list).toEqual(priceList)
|
||||||
|
})
|
||||||
|
})
|
||||||
@@ -41,6 +41,7 @@ export * from "./routes/admin/shipping-options"
|
|||||||
export * from "./routes/admin/regions"
|
export * from "./routes/admin/regions"
|
||||||
export * from "./routes/admin/product-tags"
|
export * from "./routes/admin/product-tags"
|
||||||
export * from "./routes/admin/product-types"
|
export * from "./routes/admin/product-types"
|
||||||
|
export * from "./routes/admin/price-lists"
|
||||||
|
|
||||||
// Store
|
// Store
|
||||||
export * from "./routes/store/auth"
|
export * from "./routes/store/auth"
|
||||||
|
|||||||
@@ -58,6 +58,12 @@ export type AdminPriceListRes = {
|
|||||||
price_list: PriceList
|
price_list: PriceList
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export type AdminPriceListDeleteBatchRes = {
|
||||||
|
ids: string[]
|
||||||
|
deleted: boolean
|
||||||
|
object: string
|
||||||
|
}
|
||||||
|
|
||||||
export type AdminPriceListDeleteRes = DeleteResponse
|
export type AdminPriceListDeleteRes = DeleteResponse
|
||||||
|
|
||||||
export type AdminPriceListsListRes = PaginatedResponse & {
|
export type AdminPriceListsListRes = PaginatedResponse & {
|
||||||
@@ -70,4 +76,5 @@ export * from "./delete-price-list"
|
|||||||
export * from "./get-price-list"
|
export * from "./get-price-list"
|
||||||
export * from "./list-price-lists"
|
export * from "./list-price-lists"
|
||||||
export * from "./update-price-list"
|
export * from "./update-price-list"
|
||||||
|
export * from "./delete-prices-batch"
|
||||||
export * from "./list-price-list-products"
|
export * from "./list-price-list-products"
|
||||||
|
|||||||
@@ -9,7 +9,6 @@ import {
|
|||||||
ValidateNested,
|
ValidateNested,
|
||||||
} from "class-validator"
|
} from "class-validator"
|
||||||
import { omit } from "lodash"
|
import { omit } from "lodash"
|
||||||
|
|
||||||
import { Product } from "../../../../models/product"
|
import { Product } from "../../../../models/product"
|
||||||
import { DateComparisonOperator } from "../../../../types/common"
|
import { DateComparisonOperator } from "../../../../types/common"
|
||||||
import {
|
import {
|
||||||
|
|||||||
@@ -5,7 +5,6 @@ import { MedusaError } from "medusa-core-utils"
|
|||||||
import { Product } from "../../models/product"
|
import { Product } from "../../models/product"
|
||||||
import { ProductService } from "../../services"
|
import { ProductService } from "../../services"
|
||||||
import { getListConfig } from "../../utils/get-query-config"
|
import { getListConfig } from "../../utils/get-query-config"
|
||||||
import { FindConfig } from "../../types/common"
|
|
||||||
import { FilterableProductProps } from "../../types/product"
|
import { FilterableProductProps } from "../../types/product"
|
||||||
|
|
||||||
type ListContext = {
|
type ListContext = {
|
||||||
|
|||||||
Reference in New Issue
Block a user