目录

  • 一、预约下单功能(一)
    • 1、需求
    • 2、搭建订单模块
    • 3、封装Feign调用获取就诊人接口
    • 4、封装Feign调用获取排班下单信息接口
  • 二、预约下单功能(二)
    • 1、实现生成订单接口
  • 三、预约下单功能(三)
  • 四、预约下单功能(四)
    • 1、生成订单后处理逻辑-封装短信接口
    • 2、生成订单后处理逻辑-更新排班数量
    • 3、生成订单后处理逻辑-完善订单接口
  • 五、订单列表功能
    • 1、订单列表接口
    • 2、订单列表前端
  • 六、订单详情功能

一、预约下单功能(一)

1、需求

(1)订单表结构

(2)生成订单分析
生成订单需要的参数:就诊人id与 排班id
第一、生成订单需要获取就诊人信息
第二、获取排班下单信息与规则信息
第三、下单后,然后通过接口去医院预约下单
第四、下单成功更新排班信息与发送短信

2、搭建订单模块

(1)搭建service_order模块
(2)引入依赖

<dependencies><dependency><groupId>com.donglin</groupId><artifactId>service_cmn_client</artifactId><version>0.0.1-SNAPSHOT</version></dependency>
</dependencies>

(3)添加配置文件

# 服务端口
server.port=8207
# 服务名
spring.application.name=service-orders
# 环境设置:dev、test、prod
spring.profiles.active=dev# mysql数据库连接
spring.datasource.driver-class-name=com.mysql.jdbc.Driver
spring.datasource.url=jdbc:mysql://192.168.121.140:3306/yygh_order?characterEncoding=utf-8&useSSL=false
spring.datasource.username=root
spring.datasource.password=123456#返回json的全局时间格式
spring.jackson.date-format=yyyy-MM-dd HH:mm:ss
spring.jackson.time-zone=GMT+8spring.data.mongodb.uri=mongodb://192.168.121.140:27017/test# nacos服务地址
spring.cloud.nacos.discovery.server-addr=127.0.0.1:8848#rabbitmq地址
#spring.rabbitmq.host=192.168.44.165
#spring.rabbitmq.port=5672
#spring.rabbitmq.username=guest
#spring.rabbitmq.password=guestspring.redis.host=127.0.0.1
spring.redis.port=6379
spring.redis.database= 0
spring.redis.timeout=1800000spring.redis.lettuce.pool.max-active=20
spring.redis.lettuce.pool.max-wait=-1
#最大阻塞等待时间(负数表示没限制)
spring.redis.lettuce.pool.max-idle=5
spring.redis.lettuce.pool.min-idle=0

(4)创建启动类

@SpringBootApplication
@MapperScan("com.donglin.yygh.order.mapper")
@ComponentScan(basePackages = {"com.donglin"})
@EnableDiscoveryClient
@EnableFeignClients(basePackages = {"com.donglin"})
public class ServiceOrderApplication {public static void main(String[] args) {SpringApplication.run(ServiceOrderApplication.class, args);}
}

(5)配置网关
properties

#设置路由id
spring.cloud.gateway.routes[7].id=service-orders
#设置路由的uri
spring.cloud.gateway.routes[7].uri=lb://service-orders
#设置路由断言,代理servicerId为auth-service的/auth/路径
spring.cloud.gateway.routes[7].predicates= Path=/*/order/**

yml

        - id: service-ordersuri: lb://service-orderspredicates:- Path=/*/order/** # 路径匹配

(6)创建订单的Mapper、Service和Controller

//创建mapper
public interface OrderInfoMapper extends BaseMapper<OrderInfo> {}//创建service
public interface OrderInfoService extends IService<OrderInfo> {//保存订单Long submitOrder(String scheduleId, Long patientId);
}//创建service实现类
@Service
public class OrderInfoServiceImpl extends ServiceImpl<OrderInfoMapper, OrderInfo> implements OrderInfoService {@Overridepublic Long submitOrder(String scheduleId, Long patientId) {return null;}
}@Api(tags = "订单接口")
@RestController
@RequestMapping("/api/order/orderInfo")
public class OrderInfoController {@Autowiredprivate OrderInfoService orderInfoService;@ApiOperation(value = "创建订单")@PostMapping("/{scheduleId}/{patientId}")public R submitOrder(@ApiParam(name = "scheduleId", value = "排班id", required = true)@PathVariable String scheduleId,@ApiParam(name = "patientId", value = "就诊人id", required = true)@PathVariable Long patientId) {Long orderId = orderInfoService.submitOrder(scheduleId, patientId);return R.ok().data("orderId",orderId);}}

3、封装Feign调用获取就诊人接口

(1)在PatientController类添加方法
操作模块service_user

    @ApiOperation(value = "获取就诊人")@GetMapping("{id}")public Patient getPatientOrder(@ApiParam(name = "id", value = "就诊人id", required = true)@PathVariable("id") Long id) {return patientService.getById(id);}

(2)搭建service_user_client模块
(3)添加Feign接口类

@FeignClient(value = "service-user")
@Repository
public interface PatientFeignClient {//获取就诊人@GetMapping("/user/userinfo/patient/{id}")public Patient getPatientOrder(@PathVariable("id") Long id);
}

4、封装Feign调用获取排班下单信息接口

(1)在ScheduleService添加接口和实现
操作模块service_hosp

    //根据排班id获取预约下单数据实现@Overridepublic ScheduleOrderVo getScheduleOrderVo(String scheduleId) {ScheduleOrderVo scheduleOrderVo = new ScheduleOrderVo();//排班信息Schedule schedule = scheduleRepository.findById(scheduleId).get();if(null == schedule) {throw new YyghException();}//获取预约规则信息Hospital hospital = hospitalService.getByHoscode(schedule.getHoscode());if(null == hospital) {throw new YyghException();}BookingRule bookingRule = hospital.getBookingRule();if(null == bookingRule) {throw new YyghException();}scheduleOrderVo.setHoscode(schedule.getHoscode());scheduleOrderVo.setHosname(hospital.getHosname());scheduleOrderVo.setDepcode(schedule.getDepcode());scheduleOrderVo.setDepname(departmentService.getDepartment(schedule.getHoscode(), schedule.getDepcode()).getDepname());scheduleOrderVo.setHosScheduleId(schedule.getHosScheduleId());scheduleOrderVo.setAvailableNumber(schedule.getAvailableNumber());scheduleOrderVo.setTitle(schedule.getTitle());scheduleOrderVo.setReserveDate(schedule.getWorkDate());scheduleOrderVo.setReserveTime(schedule.getWorkTime());scheduleOrderVo.setAmount(schedule.getAmount());//退号截止天数(如:就诊前一天为-1,当天为0)int quitDay = bookingRule.getQuitDay();DateTime quitTime = this.getDateTime(new DateTime(schedule.getWorkDate()).plusDays(quitDay).toDate(), bookingRule.getQuitTime());scheduleOrderVo.setQuitTime(quitTime.toDate());//预约开始时间DateTime startTime = this.getDateTime(new Date(), bookingRule.getReleaseTime());scheduleOrderVo.setStartTime(startTime.toDate());//预约截止时间DateTime endTime = this.getDateTime(new DateTime().plusDays(bookingRule.getCycle()).toDate(), bookingRule.getStopTime());scheduleOrderVo.setEndTime(endTime.toDate());//当天停止挂号时间DateTime stopTime = this.getDateTime(schedule.getWorkDate(), bookingRule.getStopTime());scheduleOrderVo.setStopTime(stopTime.toDate());return scheduleOrderVo;}

(3)搭建service_hosp_client
(4)添加Feign接口类
注意调用的时候两方都加上@PathVariable,以免之后报错

@FeignClient(value = "service-hosp")
@Repository
public interface HospitalFeignClient {@GetMapping("/user/hosp/schedule/{scheduleId}")public ScheduleOrderVo getScheduleOrderVo(@PathVariable("scheduleId") String scheduleId);
}

二、预约下单功能(二)

1、实现生成订单接口

(1)service_order引入依赖

<dependencies><dependency><groupId>com.donglin</groupId><artifactId>service_cmn_client</artifactId><version>0.0.1-SNAPSHOT</version></dependency><dependency><groupId>com.donglin</groupId><artifactId>service_hosp_client</artifactId><version>0.0.1-SNAPSHOT</version></dependency><dependency><groupId>com.donglin</groupId><artifactId>service_user_client</artifactId><version>0.0.1-SNAPSHOT</version></dependency>
</dependencies>

(2)封装工具类

(3)实现生成订单

@Service
public class OrderInfoServiceImpl extends ServiceImpl<OrderInfoMapper, OrderInfo> implements OrderInfoService {@Autowiredprivate HospitalFeignClient hospitalFeignClient;@Autowiredprivate PatientFeignClient patientFeignClient;@Autowiredprivate RabbitService rabbitService;//生成订单@Overridepublic Long submitOrder(String scheduleId, Long patientId) {//1 根据scheduleId获取排班数据ScheduleOrderVo scheduleOrderVo = hospitalFeignClient.getScheduleOrderVo(scheduleId);//2 根据patientId获取就诊人信息Patient patient = patientFeignClient.getPatientOrder(patientId);//3 平台里面 ==> 调用医院订单确认接口,// 3.1 如果医院返回失败,挂号失败//使用map集合封装需要传过医院数据Map<String, Object> paramMap = new HashMap<>();paramMap.put("hoscode",scheduleOrderVo.getHoscode());paramMap.put("depcode",scheduleOrderVo.getDepcode());paramMap.put("hosScheduleId",scheduleOrderVo.getHosScheduleId());paramMap.put("reserveDate",new DateTime(scheduleOrderVo.getReserveDate()).toString("yyyy-MM-dd"));paramMap.put("reserveTime", scheduleOrderVo.getReserveTime());paramMap.put("amount",scheduleOrderVo.getAmount()); //挂号费用paramMap.put("name", patient.getName());paramMap.put("certificatesType",patient.getCertificatesType());paramMap.put("certificatesNo", patient.getCertificatesNo());paramMap.put("sex",patient.getSex());paramMap.put("birthdate", patient.getBirthdate());paramMap.put("phone",patient.getPhone());paramMap.put("isMarry", patient.getIsMarry());paramMap.put("provinceCode",patient.getProvinceCode());paramMap.put("cityCode", patient.getCityCode());paramMap.put("districtCode",patient.getDistrictCode());paramMap.put("address",patient.getAddress());//联系人paramMap.put("contactsName",patient.getContactsName());paramMap.put("contactsCertificatesType", patient.getContactsCertificatesType());paramMap.put("contactsCertificatesNo",patient.getContactsCertificatesNo());paramMap.put("contactsPhone",patient.getContactsPhone());paramMap.put("timestamp", HttpRequestHelper.getTimestamp());//String sign = HttpRequestHelper.getSign(paramMap, signInfoVo.getSignKey());paramMap.put("sign", "");//使用httpclient发送请求,请求医院接口JSONObject result =HttpRequestHelper.sendRequest(paramMap, "http://localhost:9998/order/submitOrder");//根据医院接口返回状态码判断  200 成功if(result.getInteger("code") == 200) { //挂号成功// 3.2 如果返回成功,得到返回其他数据JSONObject jsonObject = result.getJSONObject("data");//预约记录唯一标识(医院预约记录主键)String hosRecordId = jsonObject.getString("hosRecordId");//预约序号Integer number = jsonObject.getInteger("number");;//取号时间String fetchTime = jsonObject.getString("fetchTime");;//取号地址String fetchAddress = jsonObject.getString("fetchAddress");;//4 如果医院接口返回成功,添加上面三部分数据到数据库OrderInfo orderInfo = new OrderInfo();//设置添加数据--排班数据BeanUtils.copyProperties(scheduleOrderVo, orderInfo);//设置添加数据--就诊人数据//订单号String outTradeNo = System.currentTimeMillis() + ""+ new Random().nextInt(100);orderInfo.setOutTradeNo(outTradeNo);orderInfo.setScheduleId(scheduleOrderVo.getHosScheduleId());orderInfo.setUserId(patient.getUserId());orderInfo.setPatientId(patientId);orderInfo.setPatientName(patient.getName());orderInfo.setPatientPhone(patient.getPhone());orderInfo.setOrderStatus(OrderStatusEnum.UNPAID.getStatus());//设置添加数据--医院接口返回数据orderInfo.setHosRecordId(hosRecordId);orderInfo.setNumber(number);orderInfo.setFetchTime(fetchTime);orderInfo.setFetchAddress(fetchAddress);//调用方法添加baseMapper.insert(orderInfo);//TODO 5 根据医院返回数据,更新排班数量//排班可预约数Integer reservedNumber = jsonObject.getInteger("reservedNumber");//排班剩余预约数Integer availableNumber = jsonObject.getInteger("availableNumber");//TODO 6 给就诊人发送短信//7.返回订单的idreturn orderInfo.getId();} else {throw new YyghException(20001, "号源已满");}}}

三、预约下单功能(三)

1、生成订单前端整合
(1)封装api方法
创建api/order.js

import request from '@/utils/request'const api_name = `/api/order/orderInfo`export default {submitOrder(scheduleId, patientId) {return request({url: `${api_name}/${scheduleId}/${patientId}`,method: 'post'})}
}

(2)在booking.vue组件完善下单方法

import orderInfoApi from '@/api/order'submitOrder() {if(this.patient.id == null) {this.$message.error('请选择就诊人')return}// 防止重复提交if(this.submitBnt == '正在提交...') {this.$message.error('重复提交')return}this.submitBnt = '正在提交...'orderInfoApi.submitOrder(this.scheduleId, this.patient.id).then(response => {let orderId = response.data.orderIdwindow.location.href = '/order/show?orderId=' + orderId}).catch(e => {this.submitBnt = '确认挂号'})
},

2、生成订单后处理逻辑-更新订单信息
预约成功后我们要 更新订单信息,更新预约数 和 短信提醒预约成功,为了提高下单的并发性,这部分逻辑我们就交给mq为我们完成,预约成功发送消息即可
(1)修改OrderServiceImpl方法

//生成预约挂号订单
@Override
public Long submitOrder(String scheduleId, Long patientId) {...............//TODO 5 根据医院返回数据,更新排班数量//排班可预约数Integer reservedNumber = jsonObject.getInteger("reservedNumber");//排班剩余预约数Integer availableNumber = jsonObject.getInteger("availableNumber");//发送mq信息更新号源和短信通知OrderMqVo orderMqVo = new OrderMqVo();orderMqVo.setScheduleId(scheduleId);orderMqVo.setReservedNumber(reservedNumber);orderMqVo.setAvailableNumber(availableNumber);//TODO 6 给就诊人发送短信//短信提示SmsVo msmVo = new SmsVo();msmVo.setPhone(orderInfo.getPatientPhone());String reserveDate =new DateTime(orderInfo.getReserveDate()).toString("yyyy-MM-dd")+ (orderInfo.getReserveTime()==0 ? "上午": "下午");Map<String,Object> param = new HashMap<String,Object>(){{put("title", orderInfo.getHosname()+"|"+orderInfo.getDepname()+"|"+orderInfo.getTitle());put("amount", orderInfo.getAmount());put("reserveDate", reserveDate);put("name", orderInfo.getPatientName());put("quitTime", new DateTime(orderInfo.getQuitTime()).toString("yyyy-MM-dd HH:mm"));}};msmVo.setParam(param);orderMqVo.setSmsVo(msmVo);rabbitService.sendMessage(MqConst.EXCHANGE_DIRECT_ORDER, MqConst.ROUTING_ORDER, orderMqVo);//返回订单号return orderInfo.getId();

3、生成订单后处理逻辑-rabbit-util模块封装
(1)rabbitMQ简介
以商品订单场景为例,
如果商品服务和订单服务是两个不同的微服务,在下单的过程中订单服务需要调用商品服务进行扣库存操作。按照传统的方式,下单过程要等到调用完毕之后才能返回下单成功,如果网络产生波动等原因使得商品服务扣库存延迟或者失败,会带来较差的用户体验,如果在高并发的场景下,这样的处理显然是不合适的,那怎么进行优化呢?这就需要消息队列登场了。
消息队列提供一个异步通信机制,消息的发送者不必一直等待到消息被成功处理才返回,而是立即返回。消息中间件负责处理网络通信,如果网络连接不可用,消息被暂存于队列当中,当网络畅通的时候在将消息转发给相应的应用程序或者服务,当然前提是这些服务订阅了该队列。如果在商品服务和订单服务之间使用消息中间件,既可以提高并发量,又降低服务之间的耦合度。
RabbitMQ就是这样一款消息队列。RabbitMQ是一个开源的消息代理的队列服务器,用来通过普通协议在完全不同的应用之间共享数据。
典型应用场景:
异步处理。把消息放入消息中间件中,等到需要的时候再去处理。
流量削峰。例如秒杀活动,在短时间内访问量急剧增加,使用消息队列,当消息队列满了就拒绝响应,跳转到错误页面,这样就可以使得系统不会因为超负载而崩溃
(2)安装rabbitMQ

#拉取镜像
docker pull rabbitmq:3.8-management#创建容器启动
docker run -d --restart=always -p 5672:5672 -p 15672:15672 --name rabbitmq rabbitmq:3.8-management

(3)服务rabbitMQ后台

管理后台:http://IP:15672


(4)在common搭建rabbit_util模块

(4)在rabbit_util引入依赖

<dependencies><!--rabbitmq消息队列--><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-bus-amqp</artifactId></dependency><dependency><groupId>com.alibaba</groupId><artifactId>fastjson</artifactId></dependency>
</dependencies>

(5)添加service方法

@Component
public class RabbitService {@Autowiredprivate RabbitTemplate rabbitTemplate;//rabbirmq: String.getBytes()//{//  key:value1,// }public boolean sendMessage(String exchange,String routingkey,Object message){rabbitTemplate.convertAndSend(exchange,routingkey,message);return true;}
}

(6)配置mq消息转换器

@SpringBootConfiguration
public class RabbitConfig {//作用:就是将发送到RabbitMQ中的pojo对象自动就行转换为json格式存储//   从rabbitmq中消费消息时,自动把json格式的字符串转换为pojo对象@Beanpublic MessageConverter getMessageConverter(){return new Jackson2JsonMessageConverter();}
}

说明:默认是字符串转换器
(7)添加常量类

public class MqConst {/*** 预约下单*/public static final String EXCHANGE_DIRECT_ORDER = "exchange.direct.order";public static final String ROUTING_ORDER = "order";//队列public static final String QUEUE_ORDER  = "queue.order";/*** 短信*/public static final String EXCHANGE_DIRECT_SMS = "exchange.direct.msm";public static final String ROUTING_SMS_ITEM = "msm.item";//队列public static final String QUEUE_MSM_SMS  = "queue.msm.item";
}

四、预约下单功能(四)

1、生成订单后处理逻辑-封装短信接口

操作service_sms模块
(1)service_sms引入依赖

<dependency><groupId>com.donglin</groupId><artifactId>rabbit_util</artifactId><version>0.0.1-SNAPSHOT</version>
</dependency>

(2)service_sms添加配置

#rabbitmq地址
spring.rabbitmq.host=192.168.121.140
spring.rabbitmq.port=5672
spring.rabbitmq.virtual-host=/
spring.rabbitmq.username=admin
spring.rabbitmq.password=admin

(3)在model模块封装短信实体

@Data
@ApiModel(description = "短信实体")
public class SmsVo {@ApiModelProperty(value = "phone")private String phone;@ApiModelProperty(value = "短信模板code")private String templateCode;@ApiModelProperty(value = "短信模板参数")private Map<String,Object> param;
}

(4)service_sms封装service接口和实现

    //发送短信接口boolean sendMessage(SmsVo smsVo);//发送短信实现@Overridepublic boolean sendMessage(SmsVo smsVo) {if (!StringUtils.isEmpty(smsVo.getPhone())) {//给就诊人短信提醒System.out.println("给就诊人短信提醒");//仅为了测试return this.sendCode(smsVo.getPhone());}return false;}

(5)封装mq监听器

@Component
public class SmsListener {@Autowiredprivate SmsService smsService;@RabbitListener(bindings = {@QueueBinding(value = @Queue(name = MqConst.QUEUE_MSM_SMS),exchange = @Exchange(name = MqConst.EXCHANGE_DIRECT_SMS),key = MqConst.ROUTING_SMS_ITEM)})public void consume(SmsVo msmVo, Message message, Channel channel){smsService.sendMessage(msmVo);}
}

2、生成订单后处理逻辑-更新排班数量

操作模块:service_hosp
(1)service_hosp引入依赖

<!--rabbitmq消息队列-->
<dependency><groupId>com.donglin</groupId><artifactId>rabbit_util</artifactId><version>0.0.1-SNAPSHOT</version>
</dependency>

(2)添加配置

rabbitmq地址
spring.rabbitmq.host=192.168.121.140
spring.rabbitmq.port=5672
spring.rabbitmq.virtual-host=/
spring.rabbitmq.username=admin
spring.rabbitmq.password=admin

(3)在model模块封装更新排班实体

@Data
@ApiModel(description = "OrderMqVo")
public class OrderMqVo {@ApiModelProperty(value = "可预约数")private Integer reservedNumber;@ApiModelProperty(value = "剩余预约数")private Integer availableNumber;@ApiModelProperty(value = "排班id")private String scheduleId;@ApiModelProperty(value = "短信实体")private SmsVo smsVo;}

(4)封装更新排班方法
操作ScheduleService

boolean updateAvailableNumber(String scheduleId, Integer availableNumber);@Overridepublic boolean updateAvailableNumber(String scheduleId, Integer availableNumber) {Schedule schedule = scheduleRepository.findById(scheduleId).get();schedule.setAvailableNumber(availableNumber);schedule.setUpdateTime(new Date());scheduleRepository.save(schedule);return true;}

(5)封装mq监听器

@Component
public class OrderMqListener {@Autowiredprivate ScheduleService scheduleService;@Autowiredprivate RabbitService rabbitService;@RabbitListener(bindings = {@QueueBinding(value =@Queue(name = MqConst.QUEUE_ORDER,durable = "true"),//创建队列exchange = @Exchange(name = MqConst.EXCHANGE_DIRECT_ORDER), //创建交换机key=MqConst.ROUTING_ORDER)})public void consume(OrderMqVo orderMqVo, Message message, Channel channel){String scheduleId = orderMqVo.getScheduleId();Integer availableNumber = orderMqVo.getAvailableNumber();boolean flag= scheduleService.updateAvailableNumber(scheduleId,availableNumber);SmsVo msmVo = orderMqVo.getSmsVo();if(flag && msmVo != null){rabbitService.sendMessage(MqConst.EXCHANGE_DIRECT_SMS,MqConst.ROUTING_SMS_ITEM,msmVo);}}
}

3、生成订单后处理逻辑-完善订单接口

操作service_order
(1)引入依赖

<dependency><groupId>com.donglin</groupId><artifactId>rabbit_util</artifactId><version>0.0.1-SNAPSHOT</version>
</dependency>

(2)添加配置

#rabbitmq地址
spring.rabbitmq.host=192.168.121.140
spring.rabbitmq.port=5672
spring.rabbitmq.virtual-host=/
spring.rabbitmq.username=admin
spring.rabbitmq.password=admin

(3)修改OrderServiceImpl类下单方法

@Autowired
private RabbitService rabbitService;//生成预约挂号订单
@Override
public Long submitOrder(String scheduleId, Long patientId) {.....................................//TODO 5 根据医院返回数据,更新排班数量//排班可预约数Integer reservedNumber = jsonObject.getInteger("reservedNumber");//排班剩余预约数Integer availableNumber = jsonObject.getInteger("availableNumber");//TODO 6 给就诊人发送短信//发送mq信息更新号源和短信通知OrderMqVo orderMqVo = new OrderMqVo();orderMqVo.setScheduleId(scheduleId);orderMqVo.setReservedNumber(reservedNumber);orderMqVo.setAvailableNumber(availableNumber);//短信提示SmsVo smsVo = new SmsVo();smsVo.setPhone(orderInfo.getPatientPhone());String reserveDate =new DateTime(orderInfo.getReserveDate()).toString("yyyy-MM-dd")+ (orderInfo.getReserveTime()==0 ? "上午": "下午");Map<String,Object> param = new HashMap<String,Object>(){{put("title", orderInfo.getHosname()+"|"+orderInfo.getDepname()+"|"+orderInfo.getTitle());put("amount", orderInfo.getAmount());put("reserveDate", reserveDate);put("name", orderInfo.getPatientName());put("quitTime", new DateTime(orderInfo.getQuitTime()).toString("yyyy-MM-dd HH:mm"));}};smsVo.setParam(param);orderMqVo.setSmsVo(smsVo);rabbitService.sendMessage(MqConst.EXCHANGE_DIRECT_ORDER, MqConst.ROUTING_ORDER, orderMqVo);//7 返回订单号return orderInfo.getId();} else { //挂号失败throw new YyghException(20001, "挂号失败");}

五、订单列表功能


1、订单列表接口

(1)创建service接口和实现
OrderInfoService接口和实现类

     /*** 分页列表*/Page<OrderInfo> getOrderInfoPage(Integer pageNum, Integer pageSize, OrderQueryVo orderQueryVo);//实现列表//(条件查询带分页)@Overridepublic Page<OrderInfo> getOrderInfoPage(Integer pageNum, Integer pageSize, OrderQueryVo orderQueryVo) {Page page=new Page(pageNum,pageSize);QueryWrapper<OrderInfo> queryWrapper=new QueryWrapper<OrderInfo>();Long userId = orderQueryVo.getUserId(); //用户idString outTradeNo = orderQueryVo.getOutTradeNo();//订单号String keyword = orderQueryVo.getKeyword();//医院名称Long patientId = orderQueryVo.getPatientId(); //就诊人idString orderStatus = orderQueryVo.getOrderStatus();//订单状态String reserveDate = orderQueryVo.getReserveDate(); //预约日期String createTimeBegin = orderQueryVo.getCreateTimeBegin();//下订单时间String createTimeEnd = orderQueryVo.getCreateTimeEnd();//下订单时间if(!StringUtils.isEmpty(userId)){queryWrapper.eq("user_id", userId);}if(!StringUtils.isEmpty(outTradeNo)){queryWrapper.eq("out_trade_no", outTradeNo);}if(!StringUtils.isEmpty(keyword)){queryWrapper.like("hosname", keyword);}if(!StringUtils.isEmpty(patientId)){queryWrapper.eq("patient_id", patientId);}if(!StringUtils.isEmpty(orderStatus)){queryWrapper.eq("order_status", orderStatus);}if(!StringUtils.isEmpty(reserveDate)){queryWrapper.ge("reserve_date", reserveDate);}if(!StringUtils.isEmpty(createTimeBegin)){queryWrapper.ge("create_time", createTimeBegin);}if(!StringUtils.isEmpty(createTimeEnd)){queryWrapper.le("create_time", createTimeEnd);}Page<OrderInfo> page1 = baseMapper.selectPage(page, queryWrapper);page1.getRecords().parallelStream().forEach(item->{this.packageOrderInfo(item);});return page1;}private void packageOrderInfo(OrderInfo item) {item.getParam().put("orderStatusString",OrderStatusEnum.getStatusNameByStatus(item.getOrderStatus()));}

(2)创建controller
在OrderInfoController类添加方法

    @GetMapping("/list")public R getOrderList(){List<Map<String, Object>> statusList = OrderStatusEnum.getStatusList();return R.ok().data("list",statusList);}@GetMapping("/{pageNum}/{pageSize}")public R getOrderInfoPage(@PathVariable Integer pageNum,@PathVariable Integer pageSize,OrderQueryVo orderQueryVo,@RequestHeader String token){Long userId = JwtHelper.getUserId(token);orderQueryVo.setUserId(userId);Page<OrderInfo>  page= orderInfoService.getOrderInfoPage(pageNum,pageSize,orderQueryVo);return R.ok().data("page",page);}

2、订单列表前端

(1)封装api请求
在api/order.js定义方法

 //订单列表getPageList(pageNum, pageSize, searchObj) {return request({url: `${api_name}/${pageNum}/${pageSize}`,method: `get`,params: searchObj})
},
//订单状态getStatusList() {return request({url: `${api_name}/list`,method: 'get'})},

(2)页面显示
创建/pages/order/index.vue组件

<template><!-- header --><div class="nav-container page-component"><!--左侧导航 #start --><div class="nav left-nav"><div class="nav-item "><span class="v-link clickable dark" onclick="javascript:window.location='/user'">实名认证 </span></div><div class="nav-item selected"><span class="v-link selected dark" onclick="javascript:window.location='/order'"> 挂号订单 </span></div><div class="nav-item "><span class="v-link clickable dark" onclick="javascript:window.location='/patient'"> 就诊人管理 </span></div><div class="nav-item "><span class="v-link clickable dark"> 修改账号信息 </span></div><div class="nav-item "><span class="v-link clickable dark"> 意见反馈 </span></div></div><!-- 左侧导航 #end --><!-- 右侧内容 #start --><div class="page-container"><div class="personal-order"><div class="title"> 挂号订单</div><el-form :inline="true"><el-form-item label="就诊人:"><el-select v-model="searchObj.patientId" placeholder="请选择就诊人" class="v-select patient-select"><el-optionv-for="item in patientList":key="item.id":label="item.name + '【' + item.certificatesNo + '】'":value="item.id"></el-option></el-select></el-form-item><el-form-item label="订单状态:" style="margin-left: 80px"><el-select v-model="searchObj.orderStatus" placeholder="全部" class="v-select patient-select" style="width: 200px;"><el-optionv-for="item in statusList":key="item.status":label="item.comment":value="item.status"></el-option></el-select></el-form-item><el-form-item><el-button type="text" class="search-button v-link highlight clickable selected" @click="fetchData()">查询</el-button></el-form-item></el-form><div class="table-wrapper table"><el-table:data="list"stripestyle="width: 100%"><el-table-columnlabel="就诊时间"width="120"><template slot-scope="scope">{{ scope.row.reserveDate }} {{ scope.row.reserveTime === 0 ? '上午' : '下午' }}</template></el-table-column><el-table-columnprop="hosname"label="医院"width="100"></el-table-column><el-table-columnprop="depname"label="科室"></el-table-column><el-table-columnprop="title"label="医生"></el-table-column><el-table-columnprop="amount"label="医事服务费"></el-table-column><el-table-columnprop="patientName"label="就诊人"></el-table-column><el-table-columnprop="param.orderStatusString"label="订单状态"></el-table-column><el-table-column label="操作"><template slot-scope="scope"><el-button type="text" class="v-link highlight clickable selected" @click="show(scope.row.id)">详情</el-button></template></el-table-column></el-table></div><!-- 分页 --><el-paginationclass="pagination"layout="prev, pager, next":current-page="page":total="total":page-size="limit"@current-change="fetchData"></el-pagination></div></div><!-- 右侧内容 #end --></div><!-- footer --></template><script>import '~/assets/css/hospital_personal.css'import '~/assets/css/hospital.css'import orderInfoApi from '@/api/order'import patientApi from '@/api/patient'export default {data() {return {list: [], // banner列表total: 0, // 数据库中的总记录数page: 1, // 默认页码limit: 10, // 每页记录数searchObj: {}, // 查询表单对象patientList: [],statusList: []}},created() {this.orderId = this.$route.query.orderIdthis.fetchData()this.findPatientList()this.getStatusList()},methods: {fetchData(page = 1) {this.page = pageorderInfoApi.getPageList(this.page, this.limit, this.searchObj).then(response => {console.log(response.data);this.list = response.data.page.recordsthis.total = response.data.page.total})},findPatientList() {patientApi.findList().then(response => {this.patientList = response.data.listconsole.log(this.patientList);})},getStatusList() {orderInfoApi.getStatusList().then(response => {this.statusList = response.data.listconsole.log(this.statusList);})},changeSize(size) {console.log(size)this.limit = sizethis.fetchData(1)},show(id) {window.location.href = '/order/show?orderId=' + id}}}</script>

六、订单详情功能

1、订单详情接口
(1)OrderInfoService添加方法

/*** 获取订单详情*/OrderInfo detail(Long orderId);//实现方法@Overridepublic OrderInfo detail(Long orderId) {OrderInfo orderInfo = baseMapper.selectById(orderId);this.packageOrderInfo(orderInfo);return orderInfo;}

(2)OrderApiCont添加方法
在OrderInfoController类添加方法

    //根据订单id查询订单详情@GetMapping("/{orderId}")public R detail(@PathVariable Long orderId){OrderInfo orderInfo = orderInfoService.detail(orderId);return R.ok().data("orderInfo",orderInfo);}

2、订单详情前端
(1)封装api方法
在order.js添加方法定义

//订单详情
getOrders(orderId) {return request({url: `${api_name}/${orderId}`,method: `get`})
},

(2)添加页面
创建/pages/order/show.vue组件

<template><!-- header --><div class="nav-container page-component"><!--左侧导航 #start --><div class="nav left-nav"><div class="nav-item "><span class="v-link clickable dark" onclick="javascript:window.location='/user'">实名认证 </span></div><div class="nav-item selected"><span class="v-link selected dark" onclick="javascript:window.location='/order'"> 挂号订单 </span></div><div class="nav-item "><span class="v-link clickable dark" onclick="javascript:window.location='/patient'"> 就诊人管理 </span></div><div class="nav-item "><span class="v-link clickable dark"> 修改账号信息 </span></div><div class="nav-item "><span class="v-link clickable dark"> 意见反馈 </span></div></div><!-- 左侧导航 #end --><!-- 右侧内容 #start --><div class="page-container"><div class="order-detail"><div class="title"> 挂号详情</div><div class="status-bar"><div class="left-wrapper"><div class="status-wrapper BOOKING_SUCCESS"><span class="iconfont"></span> {{ orderInfo.param.orderStatusString }}</div></div><div class="right-wrapper"><img src="//img.114yygh.com/static/web/code_order_detail.png" class="code-img"><div class="content-wrapper"><div> 微信<span class="iconfont"></span>关注“北京114预约挂号”</div><div class="watch-wrapper"> 快速挂号,轻松就医</div></div></div></div><div class="info-wrapper"><div class="title-wrapper"><div class="block"></div><div>挂号信息</div></div><div class="info-form"><el-form ref="form" :model="form"><el-form-item label="就诊人信息:"><div class="content"><span>{{ orderInfo.patientName }}</span></div></el-form-item><el-form-item label="就诊日期:"><div class="content"><span>{{ orderInfo.reserveDate }} {{ orderInfo.reserveTime == 0 ? '上午' : '下午' }}</span></div></el-form-item><el-form-item label="就诊医院:"><div class="content"><span>{{ orderInfo.hosname }} </span></div></el-form-item><el-form-item label="就诊科室:"><div class="content"><span>{{ orderInfo.depname }} </span></div></el-form-item><el-form-item label="医生职称:"><div class="content"><span>{{ orderInfo.title }} </span></div></el-form-item><el-form-item label="医事服务费:"><div class="content"><div class="fee">{{ orderInfo.amount }}元</div></div></el-form-item><el-form-item label="挂号单号:"><div class="content"><span>{{ orderInfo.outTradeNo }} </span></div></el-form-item><el-form-item label="挂号时间:"><div class="content"><span>{{ orderInfo.createTime }}</span></div></el-form-item></el-form></div></div><div class="rule-wrapper mt40"><div class="rule-title"> 注意事项</div><div>1、请确认就诊人信息是否准确,若填写错误将无法取号就诊,损失由本人承担;<br><span style="color:red">2、【取号】就诊当天需在{{ orderInfo.fetchTime }}在医院取号,未取号视为爽约,该号不退不换;</span><br>3、【退号】在{{ orderInfo.quitTime }}前可在线退号 ,逾期将不可办理退号退费;<br>4、北京114预约挂号支持自费患者使用身份证预约,同时支持北京市医保患者使用北京社保卡在平台预约挂号。请于就诊当日,携带预约挂号所使用的有效身份证件到院取号;<br>5、请注意北京市医保患者在住院期间不能使用社保卡在门诊取号。</div></div><div class="bottom-wrapper mt60" v-if="orderInfo.orderStatus == 0 || orderInfo.orderStatus == 1"><div class="button-wrapper"><div class="v-button white" @click="cancelOrder()">取消预约</div></div><div class="button-wrapper ml20" v-if="orderInfo.orderStatus == 0"><div class="v-button" @click="pay()">支付</div></div></div></div></div><!-- 右侧内容 #end --><!-- 微信支付弹出框 --><el-dialog :visible.sync="dialogPayVisible" style="text-align: left" :append-to-body="true" width="500px" @close="closeDialog"><div class="container"><div class="operate-view" style="height: 350px;"><div class="wrapper wechat"><div><img src="data:images/weixin.jpg" alt=""><div style="text-align: center;line-height: 25px;margin-bottom: 40px;">请使用微信扫一扫<br/>扫描二维码支付</div></div></div></div></div></el-dialog></div><!-- footer --></template><script>import '~/assets/css/hospital_personal.css'import '~/assets/css/hospital.css'import orderInfoApi from '@/api/order'export default {data() {return {orderId: null,orderInfo: {param: {}},dialogPayVisible: false,payObj: {},timer: null  // 定时器名称}},created() {this.orderId = this.$route.query.orderIdthis.init()},methods: {init() {orderInfoApi.getOrders(this.orderId).then(response => {console.log(response.data);this.orderInfo = response.data.orderInfo})}}}</script><style>.info-wrapper {padding-left: 0;padding-top: 0;}.content-wrapper {color: #333;font-size: 14px;padding-bottom: 0;}.bottom-wrapper {width: 100%;}.button-wrapper {margin: 0;}.el-form-item {margin-bottom: 5px;}.bottom-wrapper .button-wrapper {margin-top: 0;}</style>

尚医通 (二十二)预约下单相关推荐

  1. 尚医通 (三十五) --------- 预约下单

    目录 一.预约下单前端 1. 封装 api 请求 2. 页面修改 二.后端逻辑 1. 需求分析 2. 搭建 service-order 模块 3. 添加订单基础类 4. 封装 Feign 调用获取就诊 ...

  2. 尚医通 (三十六) --------- 微信支付

    目录 一.微信支付介绍 二.微信支付开发 1. api 接口 2. 前端 3. 处理支付结果 三.取消预约 1. 需求描述 2. 开发微信退款接口 3. 前端 一.微信支付介绍 A.微信扫码支付申请 ...

  3. 尚医通项目150-170:预约挂号、微信支付功能

    前台用户系统 预约挂号 1.接口分析 (1)根据预约周期,展示可预约日期数据,按分页展示 (2)选择日期展示当天可预约列表(该接口后台已经实现过) 2.页面展示分析 (1)分页展示可预约日期,根据有号 ...

  4. 尚医通 (十八)微信登录

    目录 一.生成微信登录二维码 1.准备工作 2.后端开发service_user 3.前端显示登录二维码 4.二维码出现不了进行调试 二.开发微信扫描回调 1.准备工作 2.后台开发 3.前台开发 三 ...

  5. 尚医通 (十九)用户认证

    目录 一.对象存储OSS 1.开通"对象存储OSS"服务 2.创建Bucket 3.上传默认头像 4.创建RAM用户 5.使用SDK 二.后端集成OSS 1.新建云存储微服务 2. ...

  6. 尚医通(十五)医院排班管理

    目录 一.医院排班管理需求 1.页面效果 2.接口分析 二.科室列表(接口) 1.添加service接口和实现 2.添加DepartmentController方法 三.科室列表(前端) 1.添加隐藏 ...

  7. 尚医通【预约挂号系统】总结

    这里写目录标题 1.项目介绍 2.技术点 3.业务流程 4.项目架构 5.项目源码(包含sql) 6.启动步骤 7.项目模块说明 8.项目功能总结 9.效果图 后台管理端 前端展示端 数据库 1.项目 ...

  8. 尚医通_第1章-项目简介

    尚医通_第1章-项目简介 文章目录 尚医通_第1章-项目简介 二.业务流程 三.系统架构 一.功能简介 尚医通即为网上预约挂号系统,网上预约挂号是近年来开展的一项便民就医服务,旨在缓解看病难.挂号难的 ...

  9. 尚医通 (一)项目介绍

    目录 一.功能简介 二.技术点 三.业务流程 四.系统架构 一.功能简介 尚医通即为网上预约挂号系统,网上预约挂号是近年来开展的一项便民就医服务,旨在缓解看病难.挂号难的就医难题,许多患者为看一次病要 ...

  10. 尚医通 (一) --------- 项目介绍

    目录 一.简介 二.将会学到 三.业务流程 四.服务架构 一.简介 尚医通即为网上预约挂号系统,网上预约挂号是近年来开展的一项便民就医服务,旨在缓解看病难.挂号难的就医难题,许多患者为看一次病要跑很多 ...

最新文章

  1. JQuery笔记(一)
  2. 每日一皮:资深程序员调试代码的样子...
  3. 荣耀10 Turbo版将上线发布,游戏玩家欢呼的手游利器
  4. OpenKruise 2021 规划曝光:More than workloads
  5. Tomcat Instance in Eclipse and in local folder
  6. Mac OSX使用VMware Fusion安装windows虚拟机教程
  7. java url接口_javaweb 后台使用url接口
  8. 计算机网络-第2章 数据通信基础
  9. vod系统必须要用服务器吗,架设美萍VOD点播系统服务器
  10. 微信小程序云开发实现一对一聊天
  11. linux/android中aplay/arecord用法以及命令
  12. matlab 行 读取文件 跳过_matlab中textscan跳行使用
  13. Ubuntu Server 21.10静态IP地址设置
  14. 围棋大师阿里,产品经理腾讯
  15. python画多边形太阳花
  16. 分享一些嵌入式相关的开源项目
  17. 股票交易接口实现方式
  18. win10如何修改dns服务器地址,win10如何修改dns服务器地址
  19. Verilog 代码编写 DDS信号发生器(幅频相可调正弦波、方波、三角波、锯齿波)纯VIVADO编写仿真
  20. 《瘗旅文》 作者:王阳明(正德四年己巳作)

热门文章

  1. 师傅带徒弟学:Python正则表达式-关东升-专题视频课程
  2. Lotus Notes Domino 数据恢复案例记录
  3. 荐书:《计算机视觉:模型、学习和推理》
  4. Hulu推荐 | 传奇嘻哈音乐组合的美国梦:《武当帮成名录》
  5. 如何应对HR小姐姐的千年历史遗留问题:你为什么从上家公司离职?
  6. 辽宁省哪所大学计算机专业好,「毕业之家」辽宁省最好的大学排名以及强势专业,你知道几所?...
  7. 区块链在人力资源领域的应用
  8. NVIC_EnableIRQ使能无法进行的原因
  9. css权重,权值与优先级解析
  10. R语言 mac X11 library is missing: install XQuartz from xquartz.macosforge.org