Removed stripe_coupon_id handling from Offers

refs https://github.com/TryGhost/Team/issues/1166

This will be handled by a payments module instead. In order to
disconnect Stripe we must delete all Stripe related data, which means an
Offer doesn't inherently have a stripe coupon id. Instead we can use a
payments service which will get/create the coupon for us when we need
it.
This commit is contained in:
Fabien O'Carroll 2021-10-20 17:40:43 +02:00 committed by Fabien 'egg' O'Carroll
parent 1ae6a2ac44
commit 947fa74b9e
5 changed files with 3 additions and 49 deletions

View File

@ -44,14 +44,13 @@ class OffersModule {
/**
* @param {object} deps
* @param {import('@tryghost/express-dynamic-redirects')} deps.redirectManager
* @param {import('@tryghost/members-stripe-service')} deps.stripeAPIService
* @param {any} deps.OfferModel
* @param {any} deps.OfferRedemptionModel
*
* @returns {OffersModule}
*/
static create(deps) {
const repository = new OfferRepository(deps.OfferModel, deps.OfferRedemptionModel, deps.stripeAPIService);
const repository = new OfferRepository(deps.OfferModel, deps.OfferRedemptionModel);
const offersAPI = new OffersAPI(repository);
return new OffersModule(offersAPI, deps.redirectManager, repository);
}

View File

@ -25,8 +25,6 @@
* @prop {'active'|'archived'} status
* @prop {number} redemption_count
*
* @prop {string} stripe_coupon_id
*
* @prop {object} tier
* @prop {string} tier.id
* @prop {string} tier.name
@ -52,7 +50,6 @@ class OfferMapper {
currency_restriction: offer.type.value === 'fixed',
currency: offer.type.value === 'fixed' ? offer.currency.value : null,
status: offer.status.value,
stripe_coupon_id: offer.stripeCouponId,
redemption_count: offer.redemptionCount,
tier: {
id: offer.tier.id,

View File

@ -46,15 +46,12 @@ class OfferRepository {
/**
* @param {{forge: (data: object) => import('bookshelf').Model<Offer.OfferProps>}} OfferModel
* @param {{forge: (data: object) => import('bookshelf').Model<any>}} OfferRedemptionModel
* @param {import('@tryghost/members-stripe-service')} stripeAPIService
*/
constructor(OfferModel, OfferRedemptionModel, stripeAPIService) {
constructor(OfferModel, OfferRedemptionModel) {
/** @private */
this.OfferModel = OfferModel;
/** @private */
this.OfferRedemptionModel = OfferRedemptionModel;
/** @private */
this.stripeAPIService = stripeAPIService;
}
/**
@ -117,7 +114,6 @@ class OfferRepository {
duration: json.duration,
duration_in_months: json.duration_in_months,
redemptionCount: count,
stripe_coupon_id: json.stripe_coupon_id,
status: json.active ? 'active' : 'archived',
tier: {
id: json.product.id,
@ -193,25 +189,6 @@ class OfferRepository {
}
if (offer.isNew) {
/** @type {import('stripe').Stripe.CouponCreateParams} */
const coupon = {
name: offer.name.value,
duration: offer.duration.value.type
};
if (offer.duration.value.type === 'repeating') {
coupon.duration_in_months = offer.duration.value.months;
}
if (offer.type.value === 'percent') {
coupon.percent_off = offer.amount.value;
} else {
coupon.amount_off = offer.amount.value;
coupon.currency = offer.currency.value;
}
const couponData = await this.stripeAPIService.createCoupon(coupon);
data.stripe_coupon_id = couponData.id;
await this.OfferModel.add(data, options);
} else {
await this.OfferModel.edit(data, {...options, id: data.id});

View File

@ -1,4 +1,4 @@
/** @typedef {import('../domain/models/OfferCode')} OfferCode */
/** @typedef {import('../models/OfferCode')} OfferCode */
/**
* @typedef {object} OfferCodeChangeEventData

View File

@ -24,7 +24,6 @@ const OfferStatus = require('./OfferStatus');
* @prop {OfferAmount} amount
* @prop {OfferDuration} duration
* @prop {OfferCurrency} [currency]
* @prop {string} [stripe_coupon_id]
* @prop {OfferStatus} status
* @prop {OfferTier} tier
* @prop {number} redemptionCount
@ -43,7 +42,6 @@ const OfferStatus = require('./OfferStatus');
* @prop {string} duration
* @prop {number} duration_in_months
* @prop {string} currency
* @prop {string} [stripe_coupon_id]
* @prop {string} status
* @prop {number} redemptionCount
* @prop {TierProps|OfferTier} tier
@ -178,10 +176,6 @@ class Offer {
return !!this.options.isNew;
}
get stripeCouponId() {
return this.props.stripe_coupon_id;
}
/**
* @param {OfferCode} code
* @param {UniqueChecker} uniqueChecker
@ -307,18 +301,6 @@ class Offer {
}
}
if (isNew && data.stripe_coupon_id) {
throw new errors.InvalidOfferCoupon({
message: 'Cannot supply a stripe_coupon_id for new Offers.'
});
}
if (!isNew && !data.stripe_coupon_id) {
throw new errors.InvalidOfferCoupon({
message: 'Offers must have a stripe_coupon_id.'
});
}
const couponId = data.stripe_coupon_id;
const tier = OfferTier.create(data.tier);
return new Offer({
@ -333,7 +315,6 @@ class Offer {
duration,
currency,
tier,
stripe_coupon_id: couponId,
redemptionCount,
status
}, {isNew});