diff --git a/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/AppraisalAmountCondition.ts b/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/AppraisalAmountCondition.ts new file mode 100644 index 000000000..9797f2ede --- /dev/null +++ b/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/AppraisalAmountCondition.ts @@ -0,0 +1,43 @@ +/* eslint-disable unicorn/no-thenable */ +import { SchemaSchema } from '@xyo-network/schema-payload-plugin' + +import type { Condition } from '../types/index.ts' + +/** + * Creates a coupon condition that requires an appraisal amount below a certain value + * @param maximumAppraisalAmount The maximum appraisal amount + * @returns A condition that requires an appraisal amount below a certain value + */ +export const createConditionForMaximumAppraisalAmount = (maximumAppraisalAmount: number): Condition => { + return { + schema: SchemaSchema, + definition: { + allOf: [ + { + type: 'array', + contains: { + type: 'object', + properties: { + schema: { type: 'string', const: 'network.xyo.escrow.terms' }, + appraisals: { type: 'array', minItems: 1 }, + }, + required: ['schema', 'appraisals'], + }, + }, + { + type: 'array', + contains: { + type: 'object', + properties: { schema: { type: 'string', const: 'network.xyo.hash.lease.estimate' } }, + required: ['schema'], + }, + items: { + type: 'object', + if: { properties: { schema: { type: 'string', const: 'network.xyo.hash.lease.estimate' } } }, + then: { properties: { price: { type: 'number', maximum: maximumAppraisalAmount } }, required: ['price'] }, + }, + }, + ], + }, + } +} diff --git a/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/AssetQuantityCondition.ts b/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/AssetQuantityCondition.ts new file mode 100644 index 000000000..5d3071888 --- /dev/null +++ b/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/AssetQuantityCondition.ts @@ -0,0 +1,25 @@ +import { SchemaSchema } from '@xyo-network/schema-payload-plugin' + +import type { Condition } from '../types/index.ts' + +/** + * Returns a coupon condition that requires a minimum quantity of assets + * @param minimumAssetQuantity The minimum quantity of assets required + * @returns A condition that requires a minimum quantity of assets + */ +export const createConditionForMinimumAssetQuantity = (minimumAssetQuantity: number): Condition => { + return { + schema: SchemaSchema, + definition: { + type: 'array', + contains: { + type: 'object', + properties: { + schema: { type: 'string', const: 'network.xyo.escrow.terms' }, + assets: { type: 'array', minItems: minimumAssetQuantity }, + }, + required: ['schema', 'assets'], + }, + }, + } +} diff --git a/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/BuyerCondition.ts b/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/BuyerCondition.ts new file mode 100644 index 000000000..75fdff65e --- /dev/null +++ b/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/BuyerCondition.ts @@ -0,0 +1,50 @@ +import type { Address } from '@xylabs/hex' +import { SchemaSchema } from '@xyo-network/schema-payload-plugin' + +import type { Condition } from '../types/index.ts' + +export type BuyerCondition = Condition & { + definition: { + contains: { + properties: { + buyer: { + items: { + const: Address + type: 'string' + } + minItems: 1 + type: 'array' + } + schema: { const: 'network.xyo.escrow.terms'; type: 'string' } + } + required: ['schema', 'buyer'] + type: 'object' + } + type: 'array' + } + schema: SchemaSchema +} + +/** + * Creates a coupon condition that requires a specific buyer + * @param buyer The buyer's address + * @returns A coupon condition that requires a specific buyer + */ +export const createConditionForRequiredBuyer = (buyer: Address): BuyerCondition => { + return { + schema: SchemaSchema, + definition: { + type: 'array', + contains: { + type: 'object', + properties: { + schema: { type: 'string', const: 'network.xyo.escrow.terms' }, + buyer: { + type: 'array', items: { type: 'string', const: buyer }, minItems: 1, + }, + }, + required: ['schema', 'buyer'], + }, + }, + } +} diff --git a/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/index.ts b/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/index.ts new file mode 100644 index 000000000..f7e4db797 --- /dev/null +++ b/packages/payload/packages/payments/src/Discount/Payload/Coupon/Conditions/index.ts @@ -0,0 +1,3 @@ +export * from './AppraisalAmountCondition.ts' +export * from './AssetQuantityCondition.ts' +export * from './BuyerCondition.ts' diff --git a/packages/payload/packages/payments/src/Discount/Payload/Coupon/index.ts b/packages/payload/packages/payments/src/Discount/Payload/Coupon/index.ts index 02c47de6f..5e0a4eded 100644 --- a/packages/payload/packages/payments/src/Discount/Payload/Coupon/index.ts +++ b/packages/payload/packages/payments/src/Discount/Payload/Coupon/index.ts @@ -1,3 +1,4 @@ +export * from './Conditions/index.ts' export * from './Coupons/index.ts' export * from './Payload.ts' export * from './Schema.ts' diff --git a/packages/payloadset/packages/payments/src/Discount/lib/spec/findUnfulfilledConditions.spec.ts b/packages/payloadset/packages/payments/src/Discount/lib/spec/findUnfulfilledConditions.spec.ts index d4f16c637..266b5465a 100644 --- a/packages/payloadset/packages/payments/src/Discount/lib/spec/findUnfulfilledConditions.spec.ts +++ b/packages/payloadset/packages/payments/src/Discount/lib/spec/findUnfulfilledConditions.spec.ts @@ -1,14 +1,20 @@ /* eslint-disable unicorn/no-thenable */ +import type { Address } from '@xylabs/hex' import type { WalletInstance } from '@xyo-network/account' import { HDWallet } from '@xyo-network/account' import { type HashLeaseEstimate, HashLeaseEstimateSchema } from '@xyo-network/diviner-hash-lease' import type { IdPayload } from '@xyo-network/id-payload-plugin' import { IdSchema } from '@xyo-network/id-payload-plugin' import { PayloadBuilder } from '@xyo-network/payload-builder' -import type { Coupon, EscrowTerms } from '@xyo-network/payment-payload-plugins' -import { EscrowTermsSchema, FixedAmountCouponSchema } from '@xyo-network/payment-payload-plugins' +import type { + BuyerCondition, + Condition, Coupon, EscrowTerms, +} from '@xyo-network/payment-payload-plugins' +import { + createConditionForMaximumAppraisalAmount, + createConditionForMinimumAssetQuantity, createConditionForRequiredBuyer, EscrowTermsSchema, FixedAmountCouponSchema, +} from '@xyo-network/payment-payload-plugins' import type { SchemaPayload } from '@xyo-network/schema-payload-plugin' -import { SchemaSchema } from '@xyo-network/schema-payload-plugin' import { beforeEach, describe, it, } from 'vitest' @@ -24,68 +30,9 @@ describe('findUnfulfilledConditions', () => { } // Conditions - const CONDITION_REQUIRES_BUYING_TWO = { - schema: SchemaSchema, - definition: { - type: 'array', - contains: { - type: 'object', - properties: { - schema: { type: 'string', const: 'network.xyo.escrow.terms' }, - assets: { type: 'array', minItems: 2 }, - }, - required: ['schema', 'assets'], - }, - }, - } - const CONDITION_REQUIRES_APPRAISAL_DOES_NOT_EXCEED_AMOUNT = { - schema: SchemaSchema, - definition: { - allOf: [ - { - type: 'array', - contains: { - type: 'object', - properties: { - schema: { type: 'string', const: 'network.xyo.escrow.terms' }, - appraisals: { type: 'array', minItems: 1 }, - }, - required: ['schema', 'appraisals'], - }, - }, - { - type: 'array', - contains: { - type: 'object', - properties: { schema: { type: 'string', const: 'network.xyo.hash.lease.estimate' } }, - required: ['schema'], - }, - items: { - type: 'object', - if: { properties: { schema: { type: 'string', const: 'network.xyo.hash.lease.estimate' } } }, - then: { properties: { price: { type: 'number', maximum: 20 } }, required: ['price'] }, - }, - }, - ], - }, - } - - const CONDITION_FOR_SPECIFIC_BUYER = { - schema: SchemaSchema, - definition: { - type: 'array', - contains: { - type: 'object', - properties: { - schema: { type: 'string', const: 'network.xyo.escrow.terms' }, - buyer: { - type: 'array', items: { type: 'string', const: '' }, minItems: 1, - }, - }, - required: ['schema', 'buyer'], - }, - }, - } + const CONDITION_REQUIRES_BUYING_TWO: Condition = createConditionForMinimumAssetQuantity(2) + const CONDITION_REQUIRES_APPRAISAL_DOES_NOT_EXCEED_AMOUNT: Condition = createConditionForMaximumAppraisalAmount(20) + const CONDITION_FOR_SPECIFIC_BUYER: BuyerCondition = createConditionForRequiredBuyer('TODO: Replace in beforeAll' as Address) const allConditions: SchemaPayload[] = [ CONDITION_REQUIRES_BUYING_TWO,