继承和 REST API 控制器 - 处理子类



我正在开发的优惠券和交易平台有以下类层次结构:

Promotion - abstract
- Coupon
- Sale
- Deal

(优惠券、促销和促销继承。促销具有一个名为type的字符串属性和一个将子类的类型属性初始化为字符串值的抽象方法。例如,优惠券中的type获得值"优惠券">等...

对于每个子类,我都有一个DAO和服务类,如CouponDAOCouponService等。

在前端,用户可以通过Angular 2界面创建优惠券销售交易,所以我决定使用以下控制器:

PromotionController - abstract
- CouponController
- SaleController
- DealController

(优惠券控制器、销售控制器、交易控制器继承自促销控制器)

PromotionController将包含所有子类通用的所有常见 CRUD 函数,在特定控制器中,我将处理针对这些类的特定操作。

A) 现在面临的问题是如何实例化来自客户端的正确对象。例如,当用户提交优惠券销售交易时,我如何实例化正确的对象。例如,在促销控制器中,我有一个这样的函数:

@RequestMapping(value=CREATE_PROMO, method=RequestMethod.POST)
public ResponseEntity<?> create(@RequestBody Promotion promotion){
promotionService.save(promotion);
return new ResponseEntity<>("", HttpStatus.OK); 
}

抽象的提升是函数的参数。我应该使用工厂模式和**type**属性来创建正确的对象吗?例如,如果type="优惠券">,那么我创建优惠券对象,如果它是"销售">,那么我创建 Sale 对象

B) 由于控制器使用服务对象,这意味着我必须在促销控制器中声明所有三个服务对象。因为在实例化正确的对象后,我需要调用它对应的服务来完成这项工作。在上面的方法中,我有促销服务,我认为应该用子类的正确服务代替

C) 我正在寻找如何处理处理现实世界中的子类的 REST API,就像我上面描述的情况一样

D) 我正在考虑通过将所有 CRUD 操作复制到其特定控制器来简化自己,但这似乎是重复的代码。

我认为有一个更好的方法可以做到。

我也尝试过是否可以找到一个处理这种情况的开源项目,但似乎我找到的所有项目都使用一个类而不是继承。他们的 REST/API 不处理继承情况

在我看来,保持端点简单。从 REST API 的角度来看,创建单个或仅一个控制器,并在控制器层之后使用以下模式。从我所看到的情况来看,最好让 REST 端点远离继承/重用,并在接收和验证请求后稍后应用它。

若要从控制器实例化服务/帮助程序层,请使用工厂方法模式:

https://en.wikipedia.org/wiki/Factory_method_pattern

创建一个促销服务工厂,该工厂根据促销类型返回促销服务实现。

在控制器中,使用工厂调用相应的升级服务方法。工厂仍然接受促销类型的参数。

@RequestMapping(value=CREATE_COUPON, method=RequestMethod.POST)
public ResponseEntity<?> create(@RequestBody Promotion promotion){
//helper if adding one more helper layer. The factory invocation is then //transferred to the helper layer
PromotionService couponService = promotionServiceFactory.get(PROMOTYPES.COUPON);
couponService.save(promotion);
return new ResponseEntity<>("", HttpStatus.OK); 
}

从您的问题来看,似乎有不同的促销类型有常见的 CRUD/其他方法。如果每个升级的某些步骤/子任务相同,而其他步骤/子任务不同,则这是服务层中模板模式的良好候选者。否则,您可以通过创建抽象升级服务来存储常见的 CRUD 方法。

https://en.wikipedia.org/wiki/Template_method_pattern

使用常见 CRUD 方法的主要方法和实现创建抽象升级服务。使用各自的不同方法创建其他促销服务类型的单独实现。

我认为你可以根据逻辑以两种方式处理这个问题。如果您想将所有内容分开,请为优惠券/交易/销售创建差异端点。这样,每个端点都将调用其控制器,依此类推。

2)如果你认为代码是相同的,你可以使用抽象工厂模式来实例化正确的服务和DAO对象。

这完全取决于您的业务需求,如果代码逻辑几乎相同,我更喜欢第二种方式。每个继承一个控制器,这样将来如果层次结构增加,则在需要时不需要创建多个类。

来回答你(A),我认为你可以使用requestObject.instanceOf()方法来告诉正确的子类类型,然后使用正确的处理程序进行处理。

最新更新