module_attendance_person.h 9.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262
  1. #ifndef MODULE_ATTENDANCE_PERSON_H
  2. #define MODULE_ATTENDANCE_PERSON_H
  3. /**
  4. *@brief 人员考勤模块 2018-08-26 戴月腾修改
  5. *主要是针对人卡进行考勤,人卡从井上切换到井下为考勤开始,人卡从井下切换到井上为考勤结束
  6. *@author 陈欧美
  7. *@date 2018-08-03
  8. */
  9. #include"math.h"
  10. #include <memory>
  11. #include <mutex>
  12. #include <map>
  13. #include <string>
  14. #include <chrono>
  15. #include <vector>
  16. #include<card.h>
  17. #include"ant.h"
  18. #include"area.h"
  19. #include"site_area.h"
  20. #include"module_const.h"
  21. #include"module_area.h"
  22. #include "module_meta_date_changed.h"
  23. #include "mine_module/MineCardManager.h"
  24. /**
  25. * @brief 主要是针对人卡进行考勤,人卡从井上切换到井下为考勤开始,人卡从井下切换到井上为考勤结束
  26. */
  27. class module_attendance_person:public singleton_base<module_attendance_person>
  28. {
  29. private:
  30. friend class singleton_base<module_attendance_person>;
  31. module_attendance_person()
  32. {
  33. }
  34. public:
  35. /**
  36. * @brief 进入分站覆盖区域处理,考勤
  37. * @param card_ptr
  38. * @param site_ptr
  39. */
  40. void enter_site(std::shared_ptr<card_location_base> card_ptr, std::shared_ptr<site> site_ptr)
  41. {
  42. // 从井下切换到井上为考勤结束
  43. if(site_ptr->is_up_site())
  44. {
  45. up_mine(card_ptr, site_ptr);
  46. //检查井下是否超员--是否需要取消
  47. CMineCardManager::instance()->OnPersonUp(card_ptr);
  48. }
  49. else// 从井上切换到井下为考勤开始
  50. {
  51. auto mine_tool_ptr = card_ptr->get_mine_tool();
  52. if(!mine_tool_ptr->is_attendance())
  53. {
  54. //考勤开始
  55. mine_tool_ptr->m_stat_attendance=AS_ATTENDANCE;
  56. mine_tool_ptr->m_attendance_start_time=std::chrono::system_clock::now();
  57. //作为一条开始考勤记录保存到数据库
  58. db_tool::save_attendance(card_ptr);
  59. log_info("人卡考勤开始:卡id=%d,卡type=%d,分站id=%d,分站reader_type_id=%d,stat_attendance=%d",
  60. card_ptr->m_id, card_ptr->m_type,
  61. site_ptr->m_id,site_ptr->m_reader_type_id,mine_tool_ptr->m_stat_attendance);
  62. }
  63. //检查井下是否超员
  64. CMineCardManager::instance()->OnPersonDown(card_ptr);
  65. }
  66. }
  67. // /**
  68. // * @brief 离开现有分站处理,记录现有分站的进出时间和地点
  69. // * @param card_ptr
  70. // * @param site_ptr
  71. // */
  72. // void leave_site(std::shared_ptr<card_location_base> card_ptr, std::shared_ptr<site> site_ptr)
  73. // {
  74. // }
  75. ///升井或收到web的删除卡命令 site_ptr==nullptr表示收到web的删除卡命令
  76. /// 保存考勤记录,发升井json,清理卡
  77. static void up_mine(std::shared_ptr<card_location_base> card_ptr, std::shared_ptr<site> site_ptr)
  78. {
  79. auto mine_tool_ptr = card_ptr->get_mine_tool();
  80. if(!mine_tool_ptr->is_attendance())
  81. {
  82. return;
  83. }
  84. //考勤结束
  85. mine_tool_ptr->m_stat_attendance=AS_NOT_ATTENDANCE;
  86. //作为一条结束考勤记录保存到数据库
  87. db_tool::save_attendance(card_ptr);
  88. rapidjson::Document doc(rapidjson::kObjectType);
  89. rapidjson::Value datas(rapidjson::kArrayType);
  90. rapidjson::Document::AllocatorType& allocator=doc.GetAllocator();
  91. to_json_card_up_one(card_ptr, datas, allocator);
  92. module_meta_date_changed::clear_card(card_ptr);
  93. //升井json发给web
  94. if(datas.Size() > 0)
  95. {
  96. doc.AddMember(JSON_ROOT_KEY_CMD,JSON_CMD_VALUE_UP_MINE, allocator);
  97. //doc.AddMember(JSON_ROOT_KEY_VERSION,INTERFACE_VERSION, allocator);
  98. doc.AddMember(JSON_ROOT_KEY_DATA, datas, allocator);
  99. tool_other::send_json(JSON_CMD_VALUE_PUSH, tool_json::doc_to_json(doc));
  100. }
  101. if(site_ptr)
  102. {
  103. log_info("人卡考勤结束:卡id=%d,卡type=%d,分站id=%d,分站reader_type_id=%d,stat_attendance=%d",
  104. card_ptr->m_id, card_ptr->m_type,
  105. site_ptr->m_id,site_ptr->m_reader_type_id,mine_tool_ptr->m_stat_attendance);
  106. }
  107. else
  108. {
  109. log_info("收到web的删除卡命令,人卡考勤结束:卡id=%d,卡type=%d, stat_attendance=%d",
  110. card_ptr->m_id, card_ptr->m_type, mine_tool_ptr->m_stat_attendance);
  111. }
  112. }
  113. /**
  114. * @brief 手工升井函数
  115. */
  116. void handle_up_mine(sio::message::ptr const& data)
  117. {
  118. std::vector<sio::message::ptr> card_vec;
  119. if(!tool_map::try_get_value(card_vec, JSON_ROOT_KEY_DATA, data) || card_vec.size() == 0)
  120. {
  121. log_error("手工升井,web发来的数据data字段为空 或者不是数组");
  122. return;
  123. }
  124. rapidjson::Document doc(rapidjson::kObjectType);
  125. rapidjson::Value datas(rapidjson::kArrayType);
  126. rapidjson::Document::AllocatorType& allocator=doc.GetAllocator();
  127. std::vector<sio::message::ptr>::const_iterator it_card = card_vec.begin();
  128. int type = 0;
  129. std::string s_card_id;
  130. for(; it_card != card_vec.end(); ++it_card)
  131. {
  132. if(!tool_map::try_get_value(s_card_id, JSON_KEY_CALL_CARD_CARD_ID, (*it_card))
  133. ||!tool_map::try_get_value(type, JSON_KEY_CALL_CARD_CARD_TYPE_ID, (*it_card)))
  134. {
  135. log_error("手工升井,web发来的数据 card_id 或 card_type格式不对");
  136. continue;
  137. }
  138. uint32_t id = tool_other::id64_to_id(s_card_id);
  139. auto card_ptr = card_list::instance()->get(tool_other::type_id_to_u64(type, id));
  140. if(card_ptr && card_ptr->is_person())
  141. {
  142. std_debug("手工升井,处理,卡id=%d,卡type=%d", id, type);
  143. log_info("手工升井,处理,卡id=%d,卡type=%d", id, type);
  144. auto mine_tool_ptr = card_ptr->get_mine_tool();
  145. if(mine_tool_ptr->is_attendance())
  146. {
  147. //考勤结束
  148. mine_tool_ptr->m_stat_attendance=AS_NOT_ATTENDANCE;
  149. //作为一条结束考勤记录保存到数据库
  150. db_tool::save_attendance(card_ptr);
  151. }
  152. //检查井下是否超员--是否需要取消
  153. CMineCardManager::instance()->OnPersonUp(card_ptr);
  154. auto area_hover_ptr = card_ptr->get_area_hover();
  155. if(area_hover_ptr && 0!=area_hover_ptr->id() && 0!=area_hover_ptr->mapid())
  156. {
  157. module_area::on_leave(card_ptr->m_id, area_hover_ptr, card_ptr->m_type);
  158. }
  159. to_json_card_up_one(card_ptr, datas, allocator);
  160. module_meta_date_changed::clear_card(card_ptr);
  161. }
  162. else
  163. {
  164. log_error("手工升井,在全局列表中找不到卡,卡id=%d,卡type=%d", id, type);
  165. }
  166. }
  167. //升井json发给web
  168. if(datas.Size() > 0)
  169. {
  170. doc.AddMember(JSON_ROOT_KEY_CMD,JSON_CMD_VALUE_UP_MINE, allocator);
  171. //doc.AddMember(JSON_ROOT_KEY_VERSION,INTERFACE_VERSION, allocator);
  172. doc.AddMember(JSON_ROOT_KEY_DATA, datas, allocator);
  173. tool_other::send_json(JSON_CMD_VALUE_PUSH, tool_json::doc_to_json(doc));
  174. }
  175. }
  176. private:
  177. ///升井json
  178. static void to_json_card_up_one(std::shared_ptr<card_location_base> card_ptr,
  179. rapidjson::Value& out_datas, rapidjson::Document::AllocatorType& allocator)
  180. {
  181. auto site_area_ptr = card_ptr->get_site_area();
  182. if(!card_ptr->m_display || !site_area_ptr || site_area_ptr->is_invalid())
  183. {
  184. return;
  185. }
  186. auto mine_tool_ptr = card_ptr->get_mine_tool();
  187. rapidjson::Value data(rapidjson::kArrayType);
  188. //卡号
  189. std::string id = tool_other::type_id_to_str(card_ptr->m_type, card_ptr->m_id);
  190. tool_json::push_back(data, id, allocator);
  191. //x,y坐标
  192. data.PushBack(card_ptr->x, allocator);
  193. data.PushBack(card_ptr->y, allocator); //CFunctions::round(card->y_offset_after(),2)
  194. //入井时间戳
  195. uint64_t t = tool_time::to_ms(mine_tool_ptr->m_attendance_start_time); //转为ms
  196. data.PushBack(t, allocator);
  197. //进入区域时间戳
  198. data.PushBack(0, allocator);
  199. //接收时间戳
  200. data.PushBack(0, allocator);
  201. //工作时长
  202. t = tool_time::elapse_ms(mine_tool_ptr->m_attendance_start_time); //转为ms
  203. data.PushBack(t, allocator);
  204. //地图编号
  205. data.PushBack(0, allocator);
  206. //区域编号
  207. data.PushBack(0, allocator);
  208. //部门编号
  209. data.PushBack(card_ptr->m_deptid, allocator);
  210. //状态
  211. data.PushBack(0, allocator);
  212. //运行状态
  213. data.PushBack(card_ptr->m_stat, allocator);
  214. //业务状态
  215. data.PushBack(0, allocator);
  216. //速度
  217. data.PushBack(card_ptr->m_speed, allocator);
  218. out_datas.PushBack(data, allocator);
  219. }
  220. };
  221. #endif // MODULE_ATTENDANCE_PERSON_H