Plantask.php 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321
  1. <?php
  2. namespace app\index\controller;
  3. use think\Controller;
  4. use think\Db;
  5. use app\common\library\Email;
  6. class Plantask extends Controller
  7. {
  8. //关于本文件里的计划任务
  9. //只有 public 方法,auto_开头的才是计划任务,其他private 方法都是工具方法
  10. ////////////////////////////////////////下面都是计划任务方法///////////////////////////////////////////////////////////////
  11. //明天有课,通知。计划任务1小时执行一次
  12. public function auto_lesson_slot_notice(){
  13. $starttime = strtotime(date('Y-m-d')) + 86400;
  14. $endtime = $starttime + 86399;
  15. $map = [
  16. 'status' => 0,
  17. 'starttime' => ['BETWEEN',[$starttime,$endtime]],
  18. 'notice_status' => 0,
  19. ];
  20. $task_list = Db::name('lesson_slot')->where($map)->order('starttime asc')->limit(1)->select();
  21. if(empty($task_list)){
  22. echo 'empty';
  23. exit;
  24. }
  25. foreach($task_list as $slot){
  26. //找出这节课时的预约单
  27. $map = [
  28. 'order.order_status' => 10,
  29. 'order.slot_id' => $slot['id'],
  30. ];
  31. $order_list = Db::name('lesson_order')->alias('order')
  32. ->field('lesson.name,lesson.name_en,user.firstname,user.lastname,user.email,user.lang,user.notice_type,user.whatsapp')
  33. ->join('user','order.user_id = user.id','LEFT')
  34. ->join('lesson','order.lesson_id = lesson.id','LEFT')
  35. ->where($map)->order('order.id asc')->select();
  36. //$order_list = $this->list_lang($order_list,['name']);
  37. if(empty($order_list)){
  38. continue;
  39. }
  40. //给这些预约单的用户发邮件
  41. $obj = new Email();
  42. foreach($order_list as $order){
  43. $result = $obj
  44. ->to($order['email'])
  45. ->subject('Don’t forget about your class tomorrow!')
  46. ->message('Hi,'.$order['firstname']. ' ' .$order['lastname'].',您预约的['.$order['name'].']将于'.date('Y-m-d H:i',$slot['starttime']).'开课,请合理安排时间,准时来上课哦!')
  47. ->send();
  48. //发whatsapp
  49. $parameters = [
  50. [
  51. 'type' => 'text',
  52. 'text' => $order['firstname'].' '.$order['lastname'],
  53. ],
  54. [
  55. 'type' => 'text',
  56. 'text' => $order['name_en'],
  57. ],
  58. [
  59. 'type' => 'text',
  60. 'text' => date('Y-m-d H:i',$slot['starttime']),
  61. ],
  62. ];
  63. $this->whatapp($order['whatsapp'],'the_class_will_start_tomorrow','en_US',$parameters);
  64. }
  65. //这节课时,任务完成
  66. $update = [
  67. 'notice_status' => 1,
  68. ];
  69. Db::name('lesson_slot')->where('id',$slot['id'])->update($update);
  70. }
  71. }
  72. //课程取消,通知。计划任务1小时执行一次
  73. public function auto_lesson_slot_cancel(){
  74. $starttime = strtotime(date('Y-m-d')) + 86400;
  75. $endtime = $starttime + 86399;
  76. $map = [
  77. 'status' => 30,
  78. // 'starttime' => ['BETWEEN',[$starttime,$endtime]],
  79. 'cancel_notice_status' => 0,
  80. ];
  81. $task_list = Db::name('lesson_slot')->where($map)->order('starttime asc')->limit(1)->select();
  82. if(empty($task_list)){
  83. echo 'empty';
  84. exit;
  85. }
  86. foreach($task_list as $slot){
  87. //找出这节课时的预约单
  88. $map = [
  89. 'order.order_status' => 10,
  90. 'order.slot_id' => $slot['id'],
  91. ];
  92. $order_list = Db::name('lesson_order')->alias('order')
  93. ->field('lesson.name,lesson.name_en,user.firstname,user.lastname,user.email,user.lang,user.notice_type,user.whatsapp')
  94. ->join('user','order.user_id = user.id','LEFT')
  95. ->join('lesson','order.lesson_id = lesson.id','LEFT')
  96. ->where($map)->order('order.id asc')->select();
  97. //$order_list = $this->list_lang($order_list,['name']);
  98. if(empty($order_list)){
  99. continue;
  100. }
  101. //给这些预约单的用户发邮件
  102. $obj = new Email();
  103. foreach($order_list as $order){
  104. $result = $obj
  105. ->to($order['email'])
  106. ->subject('Class is Cancelled!')
  107. ->message('Hi,'.$order['firstname']. ' ' .$order['lastname'].',您预约的['.$order['name'].']将于'.date('Y-m-d H:i:s',$slot['starttime']).'开课,请合理安排时间,准时来上课哦!')
  108. ->send();
  109. }
  110. //这节课时,任务完成
  111. $update = [
  112. 'cancel_notice_status' => 1,
  113. ];
  114. Db::name('lesson_slot')->where('id',$slot['id'])->update($update);
  115. }
  116. }
  117. //套餐将要到期,一个月,两周,一周,逐级通知,提醒三次。计划任务分别一小时执行一次
  118. public function auto_package_order_notice_mon(){
  119. $map = [
  120. 'order.order_status' => 1,
  121. 'order.remain' => ['gt',0],
  122. 'order.endtime' => ['lt',time()+(86400*30)],
  123. 'order.notice_status' => 0,
  124. ];
  125. $task_list = Db::name('package_order')->alias('order')
  126. ->field('order.id,order.endtime,p.name,p.name_en,user.firstname,user.lastname,user.email,user.lang,user.notice_type,user.whatsapp')
  127. ->join('lesson_package p','order.package_id = p.id','LEFT')
  128. ->join('user','order.user_id = user.id','LEFT')
  129. ->where($map)->order('endtime asc')->limit(5)->select();
  130. if(empty($task_list)){
  131. echo 'empty';
  132. exit;
  133. }
  134. $obj = new Email();
  135. foreach($task_list as $order){
  136. //给这些用户发邮件
  137. $result = $obj
  138. ->to($order['email'])
  139. ->subject('Elin Dance Studio 套餐一个月内到期提醒!')
  140. ->message('Hi,'.$order['firstname']. ' ' .$order['lastname'].',您购买的套餐['.$order['name'].']将于'.date('Y-m-d H:i:s',$order['endtime']).'过期,建议您在过期内使用完毕!')
  141. ->send();
  142. //任务完成
  143. $update = [
  144. 'notice_status' => 1,//月通知已发送
  145. ];
  146. Db::name('package_order')->where('id',$order['id'])->update($update);
  147. }
  148. }
  149. public function auto_package_order_notice_2week(){
  150. $map = [
  151. 'order.order_status' => 1,
  152. 'order.remain' => ['gt',0],
  153. 'order.endtime' => ['lt',time()+(86400*14)],
  154. 'order.notice_status' => 1,
  155. ];
  156. $task_list = Db::name('package_order')->alias('order')
  157. ->field('order.id,order.endtime,p.name,p.name_en,user.firstname,user.lastname,user.email,user.lang,user.notice_type,user.whatsapp')
  158. ->join('lesson_package p','order.package_id = p.id','LEFT')
  159. ->join('user','order.user_id = user.id','LEFT')
  160. ->where($map)->order('endtime asc')->limit(5)->select();
  161. if(empty($task_list)){
  162. echo 'empty';
  163. exit;
  164. }
  165. $obj = new Email();
  166. foreach($task_list as $order){
  167. //给这些用户发邮件
  168. $result = $obj
  169. ->to($order['email'])
  170. ->subject('Elin Dance Studio 套餐两周内到期提醒!')
  171. ->message('Hi,'.$order['firstname']. ' ' .$order['lastname'].',您购买的套餐['.$order['name'].']将于'.date('Y-m-d H:i:s',$order['endtime']).'过期,建议您在过期内使用完毕!')
  172. ->send();
  173. //任务完成
  174. $update = [
  175. 'notice_status' => 2,//2周通知已发送
  176. ];
  177. Db::name('package_order')->where('id',$order['id'])->update($update);
  178. }
  179. }
  180. public function auto_package_order_notice_1week(){
  181. $map = [
  182. 'order.order_status' => 1,
  183. 'order.remain' => ['gt',0],
  184. 'order.endtime' => ['lt',time()+(86400*7)],
  185. 'order.notice_status' => 2,
  186. ];
  187. $task_list = Db::name('package_order')->alias('order')
  188. ->field('order.id,order.endtime,p.name,p.name_en,user.firstname,user.lastname,user.email,user.lang,user.notice_type,user.whatsapp')
  189. ->join('lesson_package p','order.package_id = p.id','LEFT')
  190. ->join('user','order.user_id = user.id','LEFT')
  191. ->where($map)->order('endtime asc')->limit(5)->select();
  192. if(empty($task_list)){
  193. echo 'empty';
  194. exit;
  195. }
  196. $obj = new Email();
  197. foreach($task_list as $order){
  198. //给这些用户发邮件
  199. $result = $obj
  200. ->to($order['email'])
  201. ->subject('Elin Dance Studio 套餐一周内到期提醒!')
  202. ->message('Hi,'.$order['firstname']. ' ' .$order['lastname'].',您购买的套餐['.$order['name'].']将于'.date('Y-m-d H:i:s',$order['endtime']).'过期,建议您在过期内使用完毕!')
  203. ->send();
  204. //任务完成
  205. $update = [
  206. 'notice_status' => 3,//2周通知已发送
  207. ];
  208. Db::name('package_order')->where('id',$order['id'])->update($update);
  209. }
  210. }
  211. /////////////////////////////////////////下面都是工具方法////////////////////////////////////////////////
  212. public function whatapp($receive_mobile,$template,$code,$parameters){
  213. if(empty($receive_mobile)){return true;}
  214. $token = config('site.whatsapp_token');
  215. //发送者
  216. $mobile_id = '337736419413019'; //Elin Dance Stuido 2:+65 8015 4154 , WhatsApp Business Account ID: 336509229537586
  217. //发送
  218. $url = 'https://graph.facebook.com/v19.0/'.$mobile_id.'/messages';
  219. $header = [
  220. 'Authorization: Bearer ' . $token,
  221. 'Content-Type: application/json',
  222. ];
  223. $body = [
  224. 'messaging_product' => 'whatsapp',
  225. 'recipient_type' => 'individual',
  226. 'to' => $receive_mobile,
  227. 'type' => 'template',
  228. 'template' => [
  229. 'name' => $template,
  230. 'language' => [
  231. 'code' => $code
  232. ],
  233. 'components' => [
  234. [
  235. 'type' => 'body',
  236. 'parameters' => $parameters
  237. ]
  238. ],
  239. ],
  240. ];
  241. $body = json_encode($body);
  242. $rs = curl_post($url,$body,$header);
  243. return true;
  244. }
  245. //结果集信息里,多个字段需要翻译
  246. private function list_lang($list,$field,$lang = ''){
  247. if(!$list || empty($list)){
  248. return $list;
  249. }
  250. foreach($list as $vo => $info){
  251. $list[$vo] = $this->info_lang($info,$field);
  252. }
  253. return $list;
  254. }
  255. //单条信息里,多个字段需要翻译
  256. private function info_lang($data,$field,$lang = ''){
  257. if(!$data || empty($data)){
  258. return $data;
  259. }
  260. foreach($data as $key => $val){
  261. if(in_array($key,$field)){
  262. if($lang == 'EN'){
  263. $data[$key] = $data[$key.'_en'];
  264. unset($data[$key.'_en']);
  265. }else{
  266. unset($data[$key.'_en']);
  267. }
  268. }
  269. }
  270. return $data;
  271. }
  272. }