Adds create order transactiom
This commit is contained in:
@@ -44,6 +44,13 @@ class BaseModel {
|
|||||||
return mongoose.model(this.getModelName(), this.getSchema())
|
return mongoose.model(this.getModelName(), this.getSchema())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @private
|
||||||
|
*/
|
||||||
|
startSession() {
|
||||||
|
return this.mongooseModel_.startSession()
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Queries the mongoose model via the mongoose's findOne.
|
* Queries the mongoose model via the mongoose's findOne.
|
||||||
* @param query {object} a mongoose selector query
|
* @param query {object} a mongoose selector query
|
||||||
|
|||||||
@@ -35,7 +35,7 @@ class StripeProviderService extends PaymentService {
|
|||||||
return status
|
return status
|
||||||
}
|
}
|
||||||
|
|
||||||
if (paymentIntent.status === "requires_action") {
|
if (paymentIntent.status === "requires_capture") {
|
||||||
status = "authorized"
|
status = "authorized"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -18,7 +18,7 @@ class OrderModel extends BaseModel {
|
|||||||
// awaiting, captured, refunded
|
// awaiting, captured, refunded
|
||||||
payment_status: { type: String, default: "awaiting" },
|
payment_status: { type: String, default: "awaiting" },
|
||||||
email: { type: String, required: true },
|
email: { type: String, required: true },
|
||||||
cart_id: { type: String },
|
cart_id: { type: String, unique: true, sparse: true },
|
||||||
billing_address: { type: AddressSchema, required: true },
|
billing_address: { type: AddressSchema, required: true },
|
||||||
shipping_address: { type: AddressSchema, required: true },
|
shipping_address: { type: AddressSchema, required: true },
|
||||||
items: { type: [LineItemSchema], required: true },
|
items: { type: [LineItemSchema], required: true },
|
||||||
|
|||||||
@@ -174,6 +174,24 @@ class OrderService extends BaseService {
|
|||||||
return order
|
return order
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks the existence of an order by cart id.
|
||||||
|
* @param {string} cartId - cart id to find order
|
||||||
|
* @return {Promise<Order>} the order document
|
||||||
|
*/
|
||||||
|
async existsByCartId(cartId) {
|
||||||
|
const order = await this.orderModel_
|
||||||
|
.findOne({ metadata: { cart_id: cartId } })
|
||||||
|
.catch(err => {
|
||||||
|
throw new MedusaError(MedusaError.Types.DB_ERROR, err.message)
|
||||||
|
})
|
||||||
|
|
||||||
|
if (!order) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param {Object} selector - the query object for find
|
* @param {Object} selector - the query object for find
|
||||||
* @return {Promise} the result of the find operation
|
* @return {Promise} the result of the find operation
|
||||||
@@ -188,28 +206,72 @@ class OrderService extends BaseService {
|
|||||||
* @return {Promise} resolves to the creation result.
|
* @return {Promise} resolves to the creation result.
|
||||||
*/
|
*/
|
||||||
async createFromCart(cart) {
|
async createFromCart(cart) {
|
||||||
const o = {
|
// Create DB session for transaction
|
||||||
payment_method: cart.payment_method,
|
const dbSession = await this.orderModel_.startSession()
|
||||||
shipping_methods: cart.shipping_methods,
|
|
||||||
items: cart.items,
|
|
||||||
shipping_address: cart.shipping_address,
|
|
||||||
billing_address: cart.shipping_address,
|
|
||||||
region_id: cart.region_id,
|
|
||||||
email: cart.email,
|
|
||||||
customer_id: cart.customer_id,
|
|
||||||
cart_id: cart._id,
|
|
||||||
}
|
|
||||||
|
|
||||||
return this.orderModel_
|
try {
|
||||||
.create(o)
|
// Initialize DB transaction
|
||||||
.then(result => {
|
await dbSession.withTransaction(async () => {
|
||||||
// Notify subscribers
|
// Check if order from cart already exists
|
||||||
this.eventBus_.emit(OrderService.Events.PLACED, result)
|
// If so, this function throws
|
||||||
return result
|
const exists = await this.existsByCartId(cart._id)
|
||||||
})
|
if (exists) {
|
||||||
.catch(err => {
|
throw new MedusaError(
|
||||||
throw new MedusaError(MedusaError.Types.DB_ERROR, err.message)
|
MedusaError.types.INVALID_ARGUMENT,
|
||||||
|
"Order from cart already exists"
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Throw if payment method does not exist
|
||||||
|
if (!cart.payment_method) {
|
||||||
|
throw new MedusaError(
|
||||||
|
MedusaError.types.INVALID_ARGUMENT,
|
||||||
|
"Cart does not contain a payment method"
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
const { payment_method } = cart
|
||||||
|
|
||||||
|
const paymentProvider = await this.paymentProviderService_.retrieveProvider(
|
||||||
|
payment_method.provider_id
|
||||||
|
)
|
||||||
|
const paymentStatus = await paymentProvider.getStatus(
|
||||||
|
payment_method.data
|
||||||
|
)
|
||||||
|
|
||||||
|
// If payment status is not authorized, we throw
|
||||||
|
if (paymentStatus !== "authorized") {
|
||||||
|
throw new MedusaError(
|
||||||
|
MedusaError.types.INVALID_ARGUMENT,
|
||||||
|
"Payment method is not authorized"
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
const o = {
|
||||||
|
payment_method: cart.payment_method,
|
||||||
|
shipping_methods: cart.shipping_methods,
|
||||||
|
items: cart.items,
|
||||||
|
shipping_address: cart.shipping_address,
|
||||||
|
billing_address: cart.shipping_address,
|
||||||
|
region_id: cart.region_id,
|
||||||
|
email: cart.email,
|
||||||
|
customer_id: cart.customer_id,
|
||||||
|
cart_id: cart._id,
|
||||||
|
}
|
||||||
|
|
||||||
|
const orderDocument = await this.orderModel_.create(o)
|
||||||
|
// Commit transaction
|
||||||
|
await dbSession.commitTransaction()
|
||||||
|
// Emit and return
|
||||||
|
this.eventBus_emit(OrderService.Events.PLACED, orderDocument)
|
||||||
|
return orderDocument
|
||||||
})
|
})
|
||||||
|
} catch (error) {
|
||||||
|
console.log(error)
|
||||||
|
await dbSession.abortTransaction()
|
||||||
|
} finally {
|
||||||
|
await dbSession.endSession()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
Reference in New Issue
Block a user