如何 return 使用 Strapi GraphQL 条带化优惠券

How to return Stripe coupons using Strapi GraphQL

我有一个带结帐页面的 Nuxt 应用程序,在后端我使用的是 Strapi GraphQL。我在 Stripe 中创建了几张优惠券,我希望能够从结帐页面验证优惠券,但我正在努力弄清楚如何执行此操作。这是我目前所拥有的:

前端 (Nuxt)

Cart.vue:

this.$apollo.query({
  query: validateCouponQuery,
  variables: {
    coupon: this.coupon
  }
})

validateCoupon.gql:

query($coupon: String!) {
  validateCoupon(coupon: $coupon) {
    id
    name
    valid
  }
}

后端(Strapi): ./order/config/routes.json:

{
  "method": "GET",
  "path": "/orders/validateCoupon",
  "handler": "order.validateCoupon",
  "config": {
    "policies": []
  }
}

./order/config/schema.graphql.js:

const { sanitizeEntity } = require('strapi-utils');

module.exports = {
  query: `
    validateCoupon(coupon: String): Order
  `,
  resolver: {
    Query: {
      validateCoupon: {
        resolverOf: 'Order.validateCoupon',
        async resolver(_, { coupon }) {
          const entity = await strapi.services.order.validateCoupon({ coupon });
          return sanitizeEntity(entity, { model: strapi.models.order });
        }
      }
    }
  }
}

./order/controllers/order.js:

'use strict';
require('dotenv').config();

const stripe = require('stripe')(`${process.env.STRIPE_SECRET_KEY}`);

module.exports = {
  validateCoupon: async ctx => {
    const { coupon } = ctx.request.body;
    console.log('request coupon: ', coupon);

    try {
      const coupons = await stripe.coupons.list({ limit: 3 }, function (err, coupons) {
        console.log('err: ', err);
        console.log('coupons: ', coupons);
      });

      return coupons;
    } catch (err) {
      console.error('error validating coupon: ', err)
    }
  }
};

现在,当我尝试 运行 GraphQL Playground 中的查询时,出现错误 strapi.services.order.validateCoupon is not a function

我是 GraphQL 的新手...有没有比 运行 查询更好的获取外部数据的方法?

****更新****

我添加了我的订单服务,它消除了原来的错误。现在的问题是,即使服务似乎正确返回优惠券,schema.graphql.js returns 中的 const entity 由于某种原因未定义。请问解析器是不是不能async/await?

./order/services/order.js:

'use strict';
const stripe = require('stripe')(`${process.env.STRIPE_SECRET_KEY}`);

module.exports = {
  validateCoupon: ({ coupon }) => {
    stripe.coupons.list()
      .then(coupons => {
        return coupons.data.filter(c => {
          return (c.name === coupon && c.valid) ? c : null;
        });
        console.log('found: ', found);
      })
      .catch(err => console.error(err));
  }
};

好吧,您在 Stripe 上查找优惠券的代码看起来不错!看起来 Strapi 期望您的服务达到 ./order/services/order.js——能就这么简单吗?您的示例显示在 ./order/controllers/order.jshttps://strapi.io/documentation/3.0.0-beta.x/concepts/services.html#custom-services

所以我最终在 Strapi 内容生成器中创建了一个优惠券模型。这使我能够更轻松地 return 来自我的 GraphQL 查询的 Coupon 对象。这并不理想,因为我必须确保我创建了一个 Stripe 和 Strapi 优惠券对象来匹配,但是我也不希望首先创建太多优惠券。

我更新后的代码如下所示: schema.graphql.js:

const { sanitizeEntity } = require('strapi-utils/lib');

module.exports = {
  query: `
    validateCoupon(coupon: String): Coupon
  `,
  resolver: {
    Query: {
      validateCoupon: {
        description: 'Validate Stripe coupon',
        resolver: 'application::order.order.validateCoupon',
      }
    }
  }
}

./order/controllers/order.js:

'use strict';
require('dotenv').config();

const { sanitizeEntity } = require('strapi-utils');

module.exports = {
  validateCoupon: async ctx => {
    const coupon = ctx.query._coupon;
    const found = await strapi.services.order.validateCoupon({ coupon });
    return sanitizeEntity(found, { model: strapi.models.order });
  }
};

./order/services/order.js:

'use strict';

const stripe = require('stripe')(`${process.env.STRIPE_SECRET_KEY}`);

module.exports = {
  async validateCoupon({ coupon }) {
    let foundCoupon = null;

    try {
      const coupons = await stripe.coupons.list();
      const found = coupons.data.filter(c => {
        return (c.name === coupon && c.valid) ? c : null;
      });
      if (found) foundCoupon = found[0];
    } catch (err) {
      console.error(err);
    }

    return foundCoupon;
  }
};