Browse Source

refs #1 Syncronizing with release commit: 4a2c3a9218

qt5
parent
commit
113eba50d5
100 changed files with 17289 additions and 18829 deletions
  1. +120
    -117
      3.0/scripts/build/runtimes/terminal_ru.xml
  2. +1
    -1
      3.0/src/apps/PaymentProcessor/msvc/PaymentProcessor.vcxproj
  3. +299
    -295
      3.0/src/apps/PaymentProcessor/src/SchedulerTasks/LogArchiver.cpp
  4. +44
    -36
      3.0/src/apps/PaymentProcessor/src/SchedulerTasks/LogRotate.cpp
  5. +639
    -638
      3.0/src/apps/PaymentProcessor/src/Services/DeviceService.cpp
  6. +208
    -208
      3.0/src/apps/PaymentProcessor/src/Services/DeviceService.h
  7. +364
    -363
      3.0/src/apps/PaymentProcessor/src/Services/FirmwareUploadScenario.cpp
  8. +88
    -88
      3.0/src/apps/PaymentProcessor/src/Services/FundsService.h
  9. +716
    -717
      3.0/src/apps/PaymentProcessor/src/Services/GUIService.cpp
  10. +819
    -815
      3.0/src/apps/PaymentProcessor/src/Services/NetworkService.cpp
  11. +1509
    -1507
      3.0/src/apps/PaymentProcessor/src/Services/PaymentService.cpp
  12. +61
    -60
      3.0/src/apps/PaymentProcessor/src/Services/PrintConstants.h
  13. +464
    -432
      3.0/src/apps/PaymentProcessor/src/Services/PrintingCommands.cpp
  14. +184
    -179
      3.0/src/apps/PaymentProcessor/src/Services/PrintingCommands.h
  15. +1540
    -1519
      3.0/src/apps/PaymentProcessor/src/Services/PrintingService.cpp
  16. +240
    -240
      3.0/src/apps/PaymentProcessor/src/Services/PrintingService.h
  17. +1135
    -1134
      3.0/src/apps/PaymentProcessor/src/Services/RemoteService.cpp
  18. +577
    -573
      3.0/src/apps/PaymentProcessor/src/Services/SchedulerService.cpp
  19. +61
    -129
      3.0/src/apps/PaymentProcessor/src/locale/paymentprocessor_de.ts
  20. +61
    -129
      3.0/src/apps/PaymentProcessor/src/locale/paymentprocessor_en.ts
  21. +61
    -129
      3.0/src/apps/PaymentProcessor/src/locale/paymentprocessor_en_bankomat.ts
  22. +61
    -129
      3.0/src/apps/PaymentProcessor/src/locale/paymentprocessor_kk.ts
  23. +61
    -133
      3.0/src/apps/PaymentProcessor/src/locale/paymentprocessor_ru.ts
  24. +61
    -133
      3.0/src/apps/PaymentProcessor/src/locale/paymentprocessor_ru_bankomat.ts
  25. +76
    -76
      3.0/src/apps/Updater/src/locale/updater_en.ts
  26. +76
    -76
      3.0/src/apps/Updater/src/locale/updater_kk.ts
  27. +76
    -76
      3.0/src/apps/Updater/src/locale/updater_ru.ts
  28. +76
    -76
      3.0/src/apps/Updater/src/locale/updater_ru_bankomat.ts
  29. +4
    -0
      3.0/src/includes/Common/.gitignore
  30. +351
    -318
      3.0/src/includes/Common/PropertyTree.h
  31. +204
    -204
      3.0/src/includes/Hardware/CashAcceptors/CashAcceptorStatusesDescriptions.h
  32. +36
    -33
      3.0/src/includes/Hardware/Common/CodecDescriptions.h
  33. +1
    -0
      3.0/src/includes/Hardware/Common/DeviceConfigManager.h
  34. +198
    -195
      3.0/src/includes/Hardware/Common/DeviceDataConstants.h
  35. +39
    -0
      3.0/src/includes/Hardware/Common/DeviceLogManager.h
  36. +29
    -0
      3.0/src/includes/Hardware/Common/DeviceLogicManager.h
  37. +294
    -290
      3.0/src/includes/Hardware/Common/HardwareConstants.h
  38. +17
    -0
      3.0/src/includes/Hardware/Common/WaitingData.h
  39. +46
    -0
      3.0/src/includes/Hardware/FR/AtolOnlinePrinters.h
  40. +511
    -377
      3.0/src/includes/Hardware/FR/FRBaseConstants.h
  41. +48
    -47
      3.0/src/includes/Hardware/FR/FRStatusCodes.h
  42. +123
    -122
      3.0/src/includes/Hardware/FR/FRStatusesDescriptions.h
  43. +219
    -274
      3.0/src/includes/Hardware/FR/FiscalFieldDescriptions.h
  44. +114
    -96
      3.0/src/includes/Hardware/FR/OFDServerData.h
  45. +1
    -1
      3.0/src/includes/Hardware/Printers/CustomVKP80.h
  46. +84
    -80
      3.0/src/includes/Hardware/Printers/POSPrinterData.h
  47. +64
    -40
      3.0/src/includes/Hardware/Printers/PrinterConstants.h
  48. +21
    -21
      3.0/src/includes/Hardware/Printers/PrinterDevices.h
  49. +211
    -194
      3.0/src/includes/SDK/Drivers/FR/FiscalDataTypes.h
  50. +76
    -82
      3.0/src/includes/SDK/Drivers/FR/FiscalFields.h
  51. +103
    -100
      3.0/src/includes/SDK/Drivers/HardwareConstants.h
  52. +102
    -102
      3.0/src/includes/SDK/Drivers/IDevice.h
  53. +197
    -199
      3.0/src/includes/SDK/Drivers/IOPort/COMParameters.h
  54. +186
    -186
      3.0/src/includes/SDK/PaymentProcessor/Core/Encashment.h
  55. +125
    -125
      3.0/src/includes/SDK/PaymentProcessor/Core/IDeviceService.h
  56. +76
    -75
      3.0/src/includes/SDK/PaymentProcessor/Payment/Parameters.h
  57. +404
    -405
      3.0/src/includes/SDK/PaymentProcessor/Scripting/PaymentService.h
  58. +106
    -106
      3.0/src/includes/SDK/Plugins/PluginParameters.h
  59. +267
    -252
      3.0/src/interface/modern/addinfo_scene.qml
  60. +31
    -29
      3.0/src/interface/modern/build.cmd
  61. +214
    -209
      3.0/src/interface/modern/edit_payment_scene.qml
  62. +27
    -27
      3.0/src/interface/modern/locale/addinfo_scene_de.ts
  63. +27
    -27
      3.0/src/interface/modern/locale/addinfo_scene_en.ts
  64. +27
    -27
      3.0/src/interface/modern/locale/addinfo_scene_kk.ts
  65. +27
    -27
      3.0/src/interface/modern/locale/addinfo_scene_ru.ts
  66. +44
    -39
      3.0/src/interface/modern/locale/editor_de.ts
  67. +44
    -39
      3.0/src/interface/modern/locale/editor_en.ts
  68. +44
    -39
      3.0/src/interface/modern/locale/editor_kk.ts
  69. +44
    -39
      3.0/src/interface/modern/locale/editor_ru.ts
  70. +42
    -42
      3.0/src/interface/modern/locale/main_menu_scene_de.ts
  71. +42
    -42
      3.0/src/interface/modern/locale/main_menu_scene_en.ts
  72. +42
    -42
      3.0/src/interface/modern/locale/main_menu_scene_ru.ts
  73. +23
    -31
      3.0/src/interface/modern/locale/payment_method_selector_scene_ru.ts
  74. +50
    -50
      3.0/src/interface/modern/locale/payment_scenario_de.ts
  75. +50
    -50
      3.0/src/interface/modern/locale/payment_scenario_en.ts
  76. +50
    -50
      3.0/src/interface/modern/locale/payment_scenario_kk.ts
  77. +50
    -50
      3.0/src/interface/modern/locale/payment_scenario_ru.ts
  78. +149
    -145
      3.0/src/interface/modern/locale/result_scene_de.ts
  79. +149
    -145
      3.0/src/interface/modern/locale/result_scene_en.ts
  80. +149
    -144
      3.0/src/interface/modern/locale/result_scene_kk.ts
  81. +149
    -145
      3.0/src/interface/modern/locale/result_scene_ru.ts
  82. +304
    -302
      3.0/src/interface/modern/main_menu_scene.qml
  83. +414
    -414
      3.0/src/interface/modern/pay_scene.qml
  84. +387
    -384
      3.0/src/interface/modern/result_scene.qml
  85. +775
    -775
      3.0/src/interface/modern/scenario/payment_scenario.js
  86. +0
    -141
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car.qml
  87. +0
    -150
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car1.qml
  88. +0
    -71
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car2.qml
  89. +0
    -102
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car3.qml
  90. +0
    -83
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car3Talgo.qml
  91. +0
    -81
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car4.qml
  92. +0
    -81
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car4Talgo.qml
  93. +0
    -7
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car5.qml
  94. +0
    -62
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car6.qml
  95. +0
    -162
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Car6Talgo.qml
  96. +0
    -43
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Error.qml
  97. +0
    -220
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/List.qml
  98. +0
    -55
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Place.qml
  99. +0
    -133
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Places.qml
  100. +0
    -193
      3.0/src/interface/modern/scene_with_context/operators/11611/widgets/Train.qml

+ 120
- 117
3.0/scripts/build/runtimes/terminal_ru.xml View File

@@ -1,117 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Сборка терминального ПО с русской локализацией -->
<runtime base="terminal_common">
<!-- Общий контент Российской площадки -->
<directory source="src/runtimes/ru/common" target="" recursive="true"/>

<!-- Интерфейс Modern, компонент interface -->
<directory source="src/interface/modern/build" target="interface/interface/modern" recursive="true">
<exclude>*.wav</exclude>
</directory>
<file source="{QBS_RESULT_PATH}/plugins/interface/utils.dll" target="interface/interface/modern/plugins/utils.dll"/>
<!-- Звуки интерфейса modern -->
<directory source="src/interface/modern/build/sounds" target="sounds/interface/modern/sounds" recursive="true"/>

<!-- Логотипы Россия, компонент logo -->
<directory source="{BUILD_HOME}/Logo/ru" target="logo/interface/logo" recursive="true"/>
<directory source="{BUILD_HOME}/Logo/root_groups" target="logo/interface/logo/root_groups" recursive="true"/>

<!-- Установка Modern интерфейса по умолчанию -->
<option target="data/client.ini" key="common/interface_path" value="interface/modern" />

<!-- Установка имени конфигурации -->
<option target="data/client.ini" key="common/configuration" value="terminal_ru" />

<!-- Включаем в интерфейсе возможность переключения на Русский язык -->
<option target="interface/interface/modern/interface.ini" key="locale/ru" value="Русский" />
<option target="interface/interface/modern/interface.ini" key="locale/default" value="ru" />

<!-- Настройка параметров интерфейса -->
<option target="interface/interface/modern/interface.ini" key="ui/build_name" value="ru_common" />
<option target="interface/interface/modern/interface.ini" key="ui/show_platru" value="true" />
<option target="interface/interface/modern/interface.ini" key="ui/show_language" value="false" />
<option target="interface/interface/modern/interface.ini" key="ui/show_search" value="true" />
<option target="interface/interface/modern/interface.ini" key="ui/show_info" value="true" />
<option target="interface/interface/modern/interface.ini" key="ui/show_sms_spam" value="true" />
<option target="interface/interface/modern/interface.ini" key="ui/icon_set" value="modern" />
<option target="interface/interface/modern/interface.ini" key="ui/layouts" value="ru,en" />
<!-- Настройка ГосУслуг -->
<option target="interface/interface/modern/interface.ini" key="ui/use_smart_grid" value="9144,9176,9196,9200,9209,9210,9211" />
<!-- Настройка автоматического перевода остатка на ПК -->
<option target="interface/interface/modern/interface.ini" key="ui/use_platru_changeback" value="true" />
<!-- Настройка URL для помощника абонента -->
<option target="user/user/plugins/user_assistant.ini" key="PaymentProcessor.ScenarioFactory.UserAssistant/url" value="https://mon.cyberplat.ru/cgi-bin/get_payments.cgi" />
<!-- Плагин plat.ru, компонент plugins -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/platru.dll" target="plugins/plugins/platru.dll"/>

<!-- Плагин рекламы, компонент plugins -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/ad.dll" target="plugins/plugins/ad.dll"/>
<!-- Сценарии для сервиса Киберсдача, компонент plugins -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/cyberchange.dll" target="plugins/plugins/cyberchange.dll"/>

<!-- Uniteller plugin -->
<!-- <file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/uniteller.dll" target="plugins/plugins/uniteller.dll"/> -->

<!-- Драйверы, компонент drivers -->
<file source="{QBS_RESULT_PATH}/plugins/drivers/fr.dll" target="drivers/plugins/drivers/fr.dll"/>

<!-- Локализации исполняемых файлов -->
<file source="{QBS_RESULT_PATH}/locale/WatchService_ru.qm" target="locale/guard_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/WatchServiceController_ru.qm" target="locale/tray_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/Updater_ru.qm" target="locale/updater_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/PaymentProcessor_ru.qm" target="locale/client_ru.qm"/>

<!-- Локализации драйверов -->
<file source="{QBS_RESULT_PATH}/locale/ioports_ru.qm" target="locale/plugins/drivers/ioports_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/bill_acceptors_ru.qm" target="locale/plugins/drivers/bill_acceptors_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/bill_dispensers_ru.qm" target="locale/plugins/drivers/bill_dispensers_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/coin_acceptors_ru.qm" target="locale/plugins/drivers/coin_acceptors_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/printers_ru.qm" target="locale/plugins/drivers/printers_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/modems_ru.qm" target="locale/plugins/drivers/modems_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/watchdogs_ru.qm" target="locale/plugins/drivers/watchdogs_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/fr_ru.qm" target="locale/plugins/drivers/fr_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/scanners_ru.qm" target="locale/plugins/drivers/scanners_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/card_readers_ru.qm" target="locale/plugins/drivers/card_readers_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/health_ru.qm" target="locale/plugins/drivers/health_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/camera_ru.qm" target="locale/plugins/drivers/camera_ru.qm"/>

<!-- Локализации плагинов -->
<file source="{QBS_RESULT_PATH}/locale/service_menu_ru.qm" target="locale/plugins/service_menu_ru.qm"/>
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/user_assistant_ru.qm" target="locale/plugins/user_assistant_ru.qm"/>
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/cyberplat_monitoring_ru.qm" target="locale/plugins/cyberplat_monitoring_ru.qm"/>
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/platru_ru.qm" target="locale/plugins/platru_ru.qm"/>
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/cyberchange_ru.qm" target="locale/plugins/cyberchange_ru.qm"/>
<!-- <file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/uniteller_ru.qm" target="locale/plugins/uniteller_ru.qm"/> -->
<!-- ###################################################################################### -->

<!-- Шрифты для терминалов Beeline -->
<directory source="src/runtimes/ru/dealers/_interface_beeline" target="_interface_beeline" recursive="true"/>

<!-- Интерфейс ИОН/Ноу-Хау -->
<directory source="src/runtimes/ru/dealers/_interface_ion" target="_interface_ion" recursive="true"/>

<!-- Интерфейс МТС -->
<directory source="src/runtimes/ru/dealers/_interface_mts" target="_interface_mts" recursive="true"/>

<!-- ###################################################################################### -->

<!-- Контент Самарского дистрибутива -->
<directory source="src/runtimes/ru/samara" target="" recursive="true"/>

<!-- Плагин сценария samaraticket, компонент plugins -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/samara_ticket.dll" target="_tclib/plugins/samara_ticket.dll"/>
<!-- Локализации плагинов -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/samara_ticket_ru.qm" target="_tclib/plugins/samara_ticket_ru.qm"/>

<!-- Token plugin -->
<file if="{TC_USE_TOKEN} &amp;&amp; {CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/drivers/token.dll" target="drivers/plugins/drivers/token.dll"/>
<!-- ###################################################################################### -->
</runtime>
<?xml version="1.0" encoding="utf-8"?>
<!-- Сборка терминального ПО с русской локализацией -->
<runtime base="terminal_common">
<!-- Общий контент Российской площадки -->
<directory source="src/runtimes/ru/common" target="" recursive="true"/>
<!-- Интерфейс Modern, компонент interface -->
<directory source="src/interface/modern/build" target="interface/interface/modern" recursive="true">
<exclude>*.wav</exclude>
</directory>
<file source="{QBS_RESULT_PATH}/plugins/interface/utils.dll" target="interface/interface/modern/plugins/utils.dll"/>
<!-- Звуки интерфейса modern -->
<directory source="src/interface/modern/build/sounds" target="sounds/interface/modern/sounds" recursive="true"/>
<!-- Логотипы Россия, компонент logo -->
<directory source="{BUILD_HOME}/Logo/ru" target="logo/interface/logo" recursive="true"/>
<directory source="{BUILD_HOME}/Logo/root_groups" target="logo/interface/logo/root_groups" recursive="true"/>
<!-- Установка Modern интерфейса по умолчанию -->
<option target="data/client.ini" key="common/interface_path" value="interface/modern" />
<!-- Установка имени конфигурации -->
<option target="data/client.ini" key="common/configuration" value="terminal_ru" />
<!-- Включаем в интерфейсе возможность переключения на Русский язык -->
<option target="interface/interface/modern/interface.ini" key="locale/ru" value="Русский" />
<option target="interface/interface/modern/interface.ini" key="locale/default" value="ru" />
<!-- Настройка параметров интерфейса -->
<option target="interface/interface/modern/interface.ini" key="ui/build_name" value="ru_common" />
<option target="interface/interface/modern/interface.ini" key="ui/show_platru" value="true" />
<option target="interface/interface/modern/interface.ini" key="ui/show_language" value="false" />
<option target="interface/interface/modern/interface.ini" key="ui/show_search" value="true" />
<option target="interface/interface/modern/interface.ini" key="ui/show_info" value="true" />
<option target="interface/interface/modern/interface.ini" key="ui/show_sms_spam" value="true" />
<option target="interface/interface/modern/interface.ini" key="ui/icon_set" value="modern" />
<option target="interface/interface/modern/interface.ini" key="ui/layouts" value="ru,en" />
<!-- Настройка ГосУслуг -->
<option target="interface/interface/modern/interface.ini" key="ui/use_smart_grid" value="9144,9176,9196,9200,9209,9210,9211" />
<!-- Настройка автоматического перевода остатка на ПК -->
<option target="interface/interface/modern/interface.ini" key="ui/use_platru_changeback" value="true" />
<!-- Настройка URL для помощника абонента -->
<option target="user/user/plugins/user_assistant.ini" key="PaymentProcessor.ScenarioFactory.UserAssistant/url" value="https://mon.cyberplat.ru/cgi-bin/get_payments.cgi" />
<!-- Плагин plat.ru, компонент plugins -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/platru.dll" target="plugins/plugins/platru.dll"/>
<!-- Плагин рекламы, компонент plugins -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/ad.dll" target="plugins/plugins/ad.dll"/>
<!-- Сценарии для сервиса Киберсдача, компонент plugins -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/cyberchange.dll" target="plugins/plugins/cyberchange.dll"/>
<!-- Uniteller plugin -->
<!-- <file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/uniteller.dll" target="plugins/plugins/uniteller.dll"/> -->
<!-- Драйверы, компонент drivers -->
<file source="{QBS_RESULT_PATH}/plugins/drivers/fr.dll" target="drivers/plugins/drivers/fr.dll"/>
<!-- Локализации исполняемых файлов -->
<file source="{QBS_RESULT_PATH}/locale/WatchService_ru.qm" target="locale/guard_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/WatchServiceController_ru.qm" target="locale/tray_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/Updater_ru.qm" target="locale/updater_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/PaymentProcessor_ru.qm" target="locale/client_ru.qm"/>
<!-- Локализации драйверов -->
<file source="{QBS_RESULT_PATH}/locale/ioports_ru.qm" target="locale/plugins/drivers/ioports_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/bill_acceptors_ru.qm" target="locale/plugins/drivers/bill_acceptors_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/bill_dispensers_ru.qm" target="locale/plugins/drivers/bill_dispensers_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/coin_acceptors_ru.qm" target="locale/plugins/drivers/coin_acceptors_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/printers_ru.qm" target="locale/plugins/drivers/printers_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/modems_ru.qm" target="locale/plugins/drivers/modems_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/watchdogs_ru.qm" target="locale/plugins/drivers/watchdogs_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/fr_ru.qm" target="locale/plugins/drivers/fr_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/scanners_ru.qm" target="locale/plugins/drivers/scanners_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/card_readers_ru.qm" target="locale/plugins/drivers/card_readers_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/health_ru.qm" target="locale/plugins/drivers/health_ru.qm"/>
<file source="{QBS_RESULT_PATH}/locale/camera_ru.qm" target="locale/plugins/drivers/camera_ru.qm"/>
<!-- Локализации плагинов -->
<file source="{QBS_RESULT_PATH}/locale/service_menu_ru.qm" target="locale/plugins/service_menu_ru.qm"/>
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/user_assistant_ru.qm" target="locale/plugins/user_assistant_ru.qm"/>
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/cyberplat_monitoring_ru.qm" target="locale/plugins/cyberplat_monitoring_ru.qm"/>
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/platru_ru.qm" target="locale/plugins/platru_ru.qm"/>
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/cyberchange_ru.qm" target="locale/plugins/cyberchange_ru.qm"/>
<!-- <file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/uniteller_ru.qm" target="locale/plugins/uniteller_ru.qm"/> -->
<!-- ###################################################################################### -->
<!-- Шрифты для терминалов Beeline -->
<directory source="src/runtimes/ru/dealers/_interface_beeline" target="_interface_beeline" recursive="true"/>
<!-- Интерфейс ИОН/Ноу-Хау -->
<directory source="src/runtimes/ru/dealers/_interface_ion" target="_interface_ion" recursive="true"/>
<!-- Интерфейс МТС -->
<directory source="src/runtimes/ru/dealers/_interface_mts" target="_interface_mts" recursive="true"/>
<!-- ###################################################################################### -->
<!-- Контент Самарского дистрибутива -->
<directory source="src/runtimes/ru/samara" target="" recursive="true"/>
<!-- Плагин сценария samaraticket, компонент plugins -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/samara_ticket.dll" target="_tclib/plugins/samara_ticket.dll"/>
<!-- Локализации плагинов -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/locale/samara_ticket_ru.qm" target="_tclib/plugins/samara_ticket_ru.qm"/>
<!-- Token plugin -->
<file if="{TC_USE_TOKEN} &amp;&amp; {CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/drivers/token.dll" target="drivers/plugins/drivers/token.dll"/>
<!-- Fiscal client plugin -->
<file if="{CYBERPLAT_BUILD}" source="{QBS_RESULT_PATH}/plugins/fiscal_client.dll" target="plugins/plugins/fiscal_client.dll"/>
<!-- ###################################################################################### -->
</runtime>

+ 1
- 1
3.0/src/apps/PaymentProcessor/msvc/PaymentProcessor.vcxproj View File

@@ -1038,7 +1038,7 @@
</ImportGroup>
<ProjectExtensions>
<VisualStudio>
<UserProperties MocDir=".\GeneratedFiles\$(ProjectName)\$(ConfigurationName)" QtVersion_x0020_Win32="$(DefaultQtVersion)" RccDir=".\GeneratedFiles\$(ProjectName)" UicDir=".\GeneratedFiles\$(ProjectName)" Qt5Version_x0020_Win32="$(DefaultQtVersion)" />
<UserProperties MocDir=".\GeneratedFiles\$(ProjectName)\$(ConfigurationName)" QtVersion_x0020_Win32="$(DefaultQtVersion)" RccDir=".\GeneratedFiles\$(ProjectName)" UicDir=".\GeneratedFiles\$(ProjectName)" />
</VisualStudio>
</ProjectExtensions>
</Project>

+ 299
- 295
3.0/src/apps/PaymentProcessor/src/SchedulerTasks/LogArchiver.cpp View File

@@ -1,295 +1,299 @@
/* @file Реализация задачи архивации журнальных файлов. */

// Qt
#include <Common/QtHeadersBegin.h>
#include <QtCore/QFileInfo>
#include <QtCore/QSet>
#include <Common/QtHeadersEnd.h>

// SDK
#include <SDK/PaymentProcessor/Settings/TerminalSettings.h>
#include <SDK/PaymentProcessor/Core/ISettingsService.h>

// Модули
#include <System/IApplication.h>
#include <Common/Application.h>
#include <Packer/Packer.h>

// Проект
#include "LogArchiver.h"

namespace PPSDK = SDK::PaymentProcessor;

namespace CLogArchiver
{
const QString DateFormat = "yyyy.MM.dd";
const int BytesInMB = 1048576; // 2^20
}

//---------------------------------------------------------------------------
bool isArchive(const QFileInfo & aFileInfo)
{
return aFileInfo.suffix().toLower() == "zip" ||
aFileInfo.suffix().toLower() == "7z";
}

//---------------------------------------------------------------------------
LogArchiver::LogArchiver(const QString & aName, const QString & aLogName, const QString & aParams)
: ITask(aName, aLogName, aParams),
ILogable(aLogName),
mCanceled(false),
mPacker("", nullptr)
{
IApplication * app = dynamic_cast<IApplication *>(BasicApplication::getInstance());

PPSDK::ICore * core = app->getCore();
PPSDK::TerminalSettings * terminalSettings = static_cast<PPSDK::TerminalSettings *>(core->getSettingsService()->
getAdapter(PPSDK::CAdapterNames::TerminalAdapter));

mMaxSize = terminalSettings->getLogsMaxSize();
mLogDir = QDir(app->getWorkingDirectory() + "/logs");
mKernelPath = app->getWorkingDirectory();

mPacker.setLog(getLog());
mPacker.setToolPath(mKernelPath);
}

//---------------------------------------------------------------------------
LogArchiver::~LogArchiver()
{
}

//---------------------------------------------------------------------------
inline uint qHash(QDate key)
{
return key.toJulianDay();
}

//---------------------------------------------------------------------------
void LogArchiver::execute()
{
if (mMaxSize < 1 || !mLogDir.exists())
{
toLog(LogLevel::Error, "Failed execute: (max_size < 1) OR (log_dir not exist)");

emit finished(mName, false);
return;
}

ILog::logRotateAll();

foreach(auto date, getDatesForPack())
{
if (!mCanceled)
{
packLogs(date);
}
}

if (!mCanceled)
{
checkArchiveSize();
}

emit finished(mName, true);
}

//---------------------------------------------------------------------------
bool LogArchiver::cancel()
{
mCanceled = true;
mPacker.terminate();

return true;
}

//---------------------------------------------------------------------------
bool LogArchiver::subscribeOnComplete(QObject * aReceiver, const char * aSlot)
{
return connect(this, SIGNAL(finished(const QString &, bool)), aReceiver, aSlot);
}

//---------------------------------------------------------------------------
QString LogArchiver::logArchiveFileName(QDate aDate)
{
return mLogDir.absoluteFilePath(QString("%1_logs.7z").arg(aDate.toString(CLogArchiver::DateFormat)));
}

//---------------------------------------------------------------------------
void LogArchiver::packLogs(QDate aDate)
{
toLog(LogLevel::Normal, QString("Packs logs '%1'").arg(aDate.toString(CLogArchiver::DateFormat)));

bool updateArchive = QFile::exists(logArchiveFileName(aDate));

// pack files to archive
mPacker.setUpdateMode(updateArchive);
mPacker.setFormat(Packer::SevenZip);
mPacker.setLevel(7);
mPacker.setTimeout(60 * 60 * 1000); // 1 час в милисекундах
mPacker.setRecursive(true);

QStringList toCompress;
toCompress
<< QString("logs/%1*").arg(aDate.toString("yyyy.MM.dd"))
<< QString("receipts/%1*").arg(aDate.toString("yyyy.MM.dd"));

QStringList archiveWildcards;
archiveWildcards << "*.zip" << "*.7z";

if (!mPacker.pack(logArchiveFileName(aDate), mKernelPath, toCompress, archiveWildcards).isEmpty())
{
if (!mPacker.exitCode())
{
toLog(LogLevel::Normal, QString("Result code: %1; Output: %2").arg(mPacker.exitCode()).arg(mPacker.messages()));
}
toLog(LogLevel::Normal, "Pack OK");

if (!mCanceled)
{
removeLogs(aDate);
}
}
else
{
toLog(LogLevel::Error, QString("Pack failed: exitCode=%1 message='%2'").arg(mPacker.exitCode()).arg(mPacker.messages()));

// если мы не обновляем архив - удаляем неудачный архив
if (!updateArchive)
{
removeFile(QFileInfo(logArchiveFileName(aDate)));
}
}
}

//---------------------------------------------------------------------------
QList<QDate> LogArchiver::getDatesForPack() const
{
QSet<QDate> result;

foreach (auto file, mLogDir.entryInfoList(QDir::Files | QDir::Dirs, QDir::Name))
{
if (mCanceled)
{
break;
}

QDate date = QDate::fromString(file.fileName().left(10), CLogArchiver::DateFormat);
if (date.isValid() && date != QDate::currentDate())
{
if ((file.isFile() && !isArchive(file)) || file.isDir())
{
result << date;
}
}
}

foreach (auto dir, QDir(mKernelPath + "/receipts").entryInfoList(QDir::Dirs, QDir::Name))
{
if (mCanceled)
{
break;
}

QDate date = QDate::fromString(dir.fileName().left(10), CLogArchiver::DateFormat);
if (date.isValid() && date != QDate::currentDate())
{
result << date;
}
}

auto list = result.toList();
qSort(list);

return list;
}

//---------------------------------------------------------------------------
void LogArchiver::removeLogs(QDate aDate)
{
auto clearLogDir = [this](const QDir & aDir, const QDate & aDate)
{
foreach(auto file, aDir.entryInfoList(QStringList(aDate.toString("yyyy.MM.dd*")), QDir::Files))
{
if (!isArchive(file))
{
removeFile(file);
}
}
};

clearLogDir(mLogDir, aDate);

// чистим подпапки
foreach(auto dir, mLogDir.entryInfoList(QDir::Dirs | QDir::NoDot | QDir::NoDotDot))
{
clearLogDir(dir.filePath(), aDate);
}

auto clearSubdir = [&](QFileInfo & aFileInfo)
{
QDir dir(aFileInfo.absoluteFilePath());

foreach (auto file, dir.entryInfoList(QDir::Files))
{
removeFile(file);
}
};

QList<QDir> dirsToRemove;
dirsToRemove << mLogDir << QDir(mKernelPath + "/receipts");

foreach (auto dir, dirsToRemove)
{
foreach (auto file, dir.entryInfoList(QStringList(aDate.toString("yyyy.MM.dd*")), QDir::Dirs))
{
clearSubdir(file);

toLog(LogLevel::Debug, QString("Remove dir %1").arg(file.absoluteFilePath()));

mLogDir.rmdir(file.absoluteFilePath());
}
}
}

//---------------------------------------------------------------------------
void LogArchiver::checkArchiveSize()
{
toLog(LogLevel::Normal, QString("Check logs size limit. Max size is %1 Mb").arg(mMaxSize));

QStringList archiveWildcards;
archiveWildcards << "*.zip" << "*.7z";

QList<QFileInfo> files = mLogDir.entryInfoList(archiveWildcards, QDir::Files, QDir::Name);

auto fileSizeSumm = [](const QList<QFileInfo> & files) -> qint64
{
qint64 summ = 0;
foreach (auto file, files)
{
summ += file.size();
}
return summ;
};

while (!files.isEmpty() && fileSizeSumm(files) > mMaxSize * CLogArchiver::BytesInMB && !mCanceled)
{
removeFile(files.takeFirst());
}

toLog(LogLevel::Normal, QString("Logs archive size is %1 Mb").arg(fileSizeSumm(files) / double(CLogArchiver::BytesInMB), 0, 'f', 2));
}

//---------------------------------------------------------------------------
bool LogArchiver::removeFile(const QFileInfo & aFile)
{
bool result = QFile::remove(aFile.absoluteFilePath());

toLog(result ? LogLevel::Normal : LogLevel::Error, QString("Remove [%1] %2").arg(aFile.absoluteFilePath()).arg(result ? "OK" : "Error"));

return result;
}

//---------------------------------------------------------------------------

/* @file Реализация задачи архивации журнальных файлов. */
// Qt
#include <Common/QtHeadersBegin.h>
#include <QtCore/QFileInfo>
#include <QtCore/QSet>
#include <Common/QtHeadersEnd.h>
// SDK
#include <SDK/PaymentProcessor/Settings/TerminalSettings.h>
#include <SDK/PaymentProcessor/Core/ISettingsService.h>
// Модули
#include <System/IApplication.h>
#include <Common/Application.h>
#include <Packer/Packer.h>
// Проект
#include "LogArchiver.h"
namespace PPSDK = SDK::PaymentProcessor;
namespace CLogArchiver
{
const QString DateFormat = "yyyy.MM.dd";
const int BytesInMB = 1048576; // 2^20
}
//---------------------------------------------------------------------------
bool isArchive(const QFileInfo & aFileInfo)
{
return aFileInfo.suffix().toLower() == "zip" ||
aFileInfo.suffix().toLower() == "7z";
}
//---------------------------------------------------------------------------
LogArchiver::LogArchiver(const QString & aName, const QString & aLogName, const QString & aParams)
: ITask(aName, aLogName, aParams),
ILogable(aLogName),
mCanceled(false),
mPacker("", nullptr)
{
IApplication * app = dynamic_cast<IApplication *>(BasicApplication::getInstance());
if (app)
{
PPSDK::ICore * core = app->getCore();
PPSDK::TerminalSettings * terminalSettings = static_cast<PPSDK::TerminalSettings *>(core->getSettingsService()->
getAdapter(PPSDK::CAdapterNames::TerminalAdapter));
mMaxSize = terminalSettings->getLogsMaxSize();
mLogDir = QDir(app->getWorkingDirectory() + "/logs");
mKernelPath = app->getWorkingDirectory();
mPacker.setToolPath(mKernelPath);
}
mPacker.setLog(getLog());
}
//---------------------------------------------------------------------------
LogArchiver::~LogArchiver()
{
}
//---------------------------------------------------------------------------
inline uint qHash(QDate key)
{
return key.toJulianDay();
}
//---------------------------------------------------------------------------
void LogArchiver::execute()
{
if (mMaxSize < 1 || !mLogDir.exists())
{
toLog(LogLevel::Error, "Failed execute: (max_size < 1) OR (log_dir not exist)");
emit finished(mName, false);
return;
}
ILog::logRotateAll();
foreach(auto date, getDatesForPack())
{
if (!mCanceled)
{
packLogs(date);
}
}
if (!mCanceled)
{
checkArchiveSize();
}
emit finished(mName, true);
}
//---------------------------------------------------------------------------
bool LogArchiver::cancel()
{
mCanceled = true;
mPacker.terminate();
return true;
}
//---------------------------------------------------------------------------
bool LogArchiver::subscribeOnComplete(QObject * aReceiver, const char * aSlot)
{
return connect(this, SIGNAL(finished(const QString &, bool)), aReceiver, aSlot);
}
//---------------------------------------------------------------------------
QString LogArchiver::logArchiveFileName(QDate aDate)
{
return mLogDir.absoluteFilePath(QString("%1_logs.7z").arg(aDate.toString(CLogArchiver::DateFormat)));
}
//---------------------------------------------------------------------------
void LogArchiver::packLogs(QDate aDate)
{
toLog(LogLevel::Normal, QString("Packs logs '%1'").arg(aDate.toString(CLogArchiver::DateFormat)));
bool updateArchive = QFile::exists(logArchiveFileName(aDate));
// pack files to archive
mPacker.setUpdateMode(updateArchive);
mPacker.setFormat(Packer::SevenZip);
mPacker.setLevel(7);
mPacker.setTimeout(60 * 60 * 1000); // 1 час в милисекундах
mPacker.setRecursive(true);
QStringList toCompress;
toCompress
<< QString("logs/%1*").arg(aDate.toString("yyyy.MM.dd"))
<< QString("receipts/%1*").arg(aDate.toString("yyyy.MM.dd"));
QStringList archiveWildcards;
archiveWildcards << "*.zip" << "*.7z";
if (!mPacker.pack(logArchiveFileName(aDate), mKernelPath, toCompress, archiveWildcards).isEmpty())
{
if (!mPacker.exitCode())
{
toLog(LogLevel::Normal, QString("Result code: %1; Output: %2").arg(mPacker.exitCode()).arg(mPacker.messages()));
}
toLog(LogLevel::Normal, "Pack OK");
if (!mCanceled)
{
removeLogs(aDate);
}
}
else
{
toLog(LogLevel::Error, QString("Pack failed: exitCode=%1 message='%2'").arg(mPacker.exitCode()).arg(mPacker.messages()));
// если мы не обновляем архив - удаляем неудачный архив
if (!updateArchive)
{
removeFile(QFileInfo(logArchiveFileName(aDate)));
}
}
}
//---------------------------------------------------------------------------
QList<QDate> LogArchiver::getDatesForPack() const
{
QSet<QDate> result;
foreach (auto file, mLogDir.entryInfoList(QDir::Files | QDir::Dirs, QDir::Name))
{
if (mCanceled)
{
break;
}
QDate date = QDate::fromString(file.fileName().left(10), CLogArchiver::DateFormat);
if (date.isValid() && date != QDate::currentDate())
{
if ((file.isFile() && !isArchive(file)) || file.isDir())
{
result << date;
}
}
}
foreach (auto dir, QDir(mKernelPath + "/receipts").entryInfoList(QDir::Dirs, QDir::Name))
{
if (mCanceled)
{
break;
}
QDate date = QDate::fromString(dir.fileName().left(10), CLogArchiver::DateFormat);
if (date.isValid() && date != QDate::currentDate())
{
result << date;
}
}
auto list = result.toList();
qSort(list);
return list;
}
//---------------------------------------------------------------------------
void LogArchiver::removeLogs(QDate aDate)
{
auto clearLogDir = [this](const QDir & aDir, const QDate & aDate)
{
foreach(auto file, aDir.entryInfoList(QStringList(aDate.toString("yyyy.MM.dd*")), QDir::Files))
{
if (!isArchive(file))
{
removeFile(file);
}
}
};
clearLogDir(mLogDir, aDate);
// чистим подпапки
foreach(auto dir, mLogDir.entryInfoList(QDir::Dirs | QDir::NoDot | QDir::NoDotDot))
{
clearLogDir(dir.filePath(), aDate);
}
auto clearSubdir = [&](QFileInfo & aFileInfo)
{
QDir dir(aFileInfo.absoluteFilePath());
foreach (auto file, dir.entryInfoList(QDir::Files))
{
removeFile(file);
}
};
QList<QDir> dirsToRemove;
dirsToRemove << mLogDir << QDir(mKernelPath + "/receipts");
foreach (auto dir, dirsToRemove)
{
foreach (auto file, dir.entryInfoList(QStringList(aDate.toString("yyyy.MM.dd*")), QDir::Dirs))
{
clearSubdir(file);
toLog(LogLevel::Debug, QString("Remove dir %1").arg(file.absoluteFilePath()));
mLogDir.rmdir(file.absoluteFilePath());
}
}
}
//---------------------------------------------------------------------------
void LogArchiver::checkArchiveSize()
{
toLog(LogLevel::Normal, QString("Check logs size limit. Max size is %1 Mb").arg(mMaxSize));
QStringList archiveWildcards;
archiveWildcards << "*.zip" << "*.7z";
QList<QFileInfo> files = mLogDir.entryInfoList(archiveWildcards, QDir::Files, QDir::Name);
auto fileSizeSumm = [](const QList<QFileInfo> & files) -> qint64
{
qint64 summ = 0;
foreach (auto file, files)
{
summ += file.size();
}
return summ;
};
while (!files.isEmpty() && fileSizeSumm(files) > mMaxSize * CLogArchiver::BytesInMB && !mCanceled)
{
removeFile(files.takeFirst());
}
toLog(LogLevel::Normal, QString("Logs archive size is %1 Mb").arg(fileSizeSumm(files) / double(CLogArchiver::BytesInMB), 0, 'f', 2));
}
//---------------------------------------------------------------------------
bool LogArchiver::removeFile(const QFileInfo & aFile)
{
bool result = QFile::remove(aFile.absoluteFilePath());
toLog(result ? LogLevel::Normal : LogLevel::Error, QString("Remove [%1] %2").arg(aFile.absoluteFilePath()).arg(result ? "OK" : "Error"));
return result;
}
//---------------------------------------------------------------------------

+ 44
- 36
3.0/src/apps/PaymentProcessor/src/SchedulerTasks/LogRotate.cpp View File

@@ -1,36 +1,44 @@
/* @file Реализация задачи архивации журнальных файлов. */

// Модули
#include <System/IApplication.h>
#include <Common/Application.h>

// Проект
#include "Services/TerminalService.h"
#include "LogRotate.h"

//---------------------------------------------------------------------------
LogRotate::LogRotate(const QString & aName, const QString & aLogName, const QString & aParams)
: ITask(aName, aLogName, aParams)
{
}

//---------------------------------------------------------------------------
void LogRotate::execute()
{
IApplication * app = dynamic_cast<IApplication *>(BasicApplication::getInstance());

dynamic_cast<TerminalService *>(app->getCore()->getTerminalService())->getClient()->execute("close_logs");

ILog::logRotateAll();

emit finished(mName, true);
}

//---------------------------------------------------------------------------
bool LogRotate::subscribeOnComplete(QObject * aReceiver, const char * aSlot)
{
return connect(this, SIGNAL(finished(const QString &, bool)), aReceiver, aSlot);
}

//---------------------------------------------------------------------------

/* @file Реализация задачи архивации журнальных файлов. */
// Модули
#include <System/IApplication.h>
#include <Common/Application.h>
// Проект
#include "Services/TerminalService.h"
#include "LogRotate.h"
//---------------------------------------------------------------------------
LogRotate::LogRotate(const QString & aName, const QString & aLogName, const QString & aParams)
: ITask(aName, aLogName, aParams)
{
}
//---------------------------------------------------------------------------
void LogRotate::execute()
{
IApplication * app = dynamic_cast<IApplication *>(BasicApplication::getInstance());
if (app)
{
auto terminalService = dynamic_cast<TerminalService *>(app->getCore()->getTerminalService());
if (terminalService)
{
terminalService->getClient()->execute("close_logs");
}
}
ILog::logRotateAll();
emit finished(mName, true);
}
//---------------------------------------------------------------------------
bool LogRotate::subscribeOnComplete(QObject * aReceiver, const char * aSlot)
{
return connect(this, SIGNAL(finished(const QString &, bool)), aReceiver, aSlot);
}
//---------------------------------------------------------------------------

+ 639
- 638
3.0/src/apps/PaymentProcessor/src/Services/DeviceService.cpp
File diff suppressed because it is too large
View File


+ 208
- 208
3.0/src/apps/PaymentProcessor/src/Services/DeviceService.h View File

@@ -1,208 +1,208 @@
/* @file Реализация сервиса для работы с устройствами. */
#pragma once
// Qt
#include <Common/QtHeadersBegin.h>
#include <QtCore/QStringList>
#include <QtCore/QFutureWatcher>
#include <QtCore/QMutex>
#include <QtCore/QSet>
#include <Common/QtHeadersEnd.h>
// Modules
#include <Common/ILog.h>
// SDK
#include <SDK/Drivers/IDevice.h>
#include <SDK/Plugins/IPLuginLoader.h>
// PP Core
#include <SDK/PaymentProcessor/Core/IDeviceService.h>
#include <SDK/Plugins/IPluginLoader.h>
#include <SDK/Plugins/PluginParameters.h>
#include <SDK/PaymentProcessor/Core/IService.h>
#include <SDK/PaymentProcessor/Core/Event.h>
// Project
#include "IntegratedDrivers.h"
class IApplication;
class IHardwareDatabaseUtils;
class DeviceManager;
//TODO #29565 - метод перезаписи статуса модема, пока не отрефакторили соединение и модем в единое целое
#pragma deprecated(overwriteDeviceStatus)
/// Варианты момента создания устройства
namespace EDeviceCreationOrder
{
enum Enum
{
OnDemand,
AtStart
};
}
//------------------------------------------------------------------------------
/// Реализация сервиса для работы с устройствами.
class DeviceService :
public SDK::PaymentProcessor::IDeviceService,
public SDK::PaymentProcessor::IService
{
Q_OBJECT
public:
/// структура - статус устройства
class Status : public SDK::PaymentProcessor::IDeviceStatus
{
public:
Status();
Status(const Status & aStatus);
explicit Status(SDK::Driver::EWarningLevel::Enum aLevel, const QString & aDescription, int aStatus);
public:
/// Уровень тревожности
virtual SDK::Driver::EWarningLevel::Enum level() const;
/// Описание статуса
virtual const QString & description() const;
/// Проверить содержимое статуса на удовлетворение определенному уровню
bool isMatched(SDK::Driver::EWarningLevel::Enum aLevel) const;
public:
SDK::Driver::EWarningLevel::Enum mLevel;
QString mDescription;
int mStatus;
};
public:
/// Получение экземпляра DeviceService.
static DeviceService * instance(IApplication * aApplication);
DeviceService(IApplication * aApplication);
virtual ~DeviceService();
/// Инициализация сервиса.
virtual bool initialize();
/// IService: Закончена инициализация всех сервисов.
virtual void finishInitialize();
/// Возвращает false, если сервис не может быть остановлен в текущий момент.
virtual bool canShutdown();
/// Завершение работы сервиса.
virtual bool shutdown();
/// Возвращает имя сервиса.
virtual QString getName() const;
/// Поулчение списка зависимостей.
virtual const QSet<QString> & getRequiredServices() const;
/// Получить параметры сервиса.
virtual QVariantMap getParameters() const;
/// Сброс служебной информации.
virtual void resetParameters(const QSet<QString> & aParameters);
// IDeviceService
/// Неблокирующий поиск всех устройств.
virtual void detect(const QString & aDeviceType);
/// Прервать поиск устройств.
virtual void stopDetection();
/// Получить полный список конфигураций.
virtual QStringList getConfigurations(bool aAllowOldConfigs = true) const;
/// Сохранить cписок конфигураций.
virtual bool saveConfigurations(const QStringList & aConfigList);
/// Добавить список параметров, необходимых для инициализации устройств.
virtual void setInitParameters(const QString & aDeviceType, const QVariantMap & aParameters);
/// Подключение/захват устройства. aDeviceNumber - номер среди одинаковых устройств.
virtual SDK::Driver::IDevice * acquireDevice(const QString & aInstancePath);
/// Создание устройства.
virtual QString createDevice(const QString & aDriverPath, const QVariantMap & aConfig);
/// Отключение/освобождение указанного устройства.
virtual void releaseDevice(SDK::Driver::IDevice * aDevice);
/// Обновить прошивку устройства.
virtual UpdateFirmwareResult updateFirmware(const QByteArray & aFirmware, const QString & aDeviceGUID);
/// Получение списка параметров драйвера.
virtual SDK::Plugin::TParameterList getDriverParameters(const QString & aDriverPath) const;
/// Получить конфигурацию утройства и всех, связынных с ним.
virtual QVariantMap getDeviceConfiguration(const QString & aConfigName);
/// Устанавливает конфигурацию устройству.
virtual void setDeviceConfiguration(const QString & aConfigName, const QVariantMap & aConfig);
/// Получение списка драверов (поддерживаемых устройств).
virtual SDK::PaymentProcessor::TModelList getModelList(const QString & aFilter) const;
/// Получение списка драйверов.
virtual QStringList getDriverList() const;
/// Возвращает список имен созданных устройств.
virtual QStringList getAcquiredDevicesList() const;
/// Получить имя конфига по устроойству.
virtual QString getDeviceConfigName(SDK::Driver::IDevice * aDevice);
/// Получить статус устройства по имени конфигурации.
virtual QSharedPointer<SDK::PaymentProcessor::IDeviceStatus> getDeviceStatus(const QString & aConfigName);
/// Освобождает все устройства.
virtual void releaseAll();
/// Перезаписать статус устройства (#29565)
virtual void overwriteDeviceStatus(SDK::Driver::IDevice * aDevice, SDK::Driver::EWarningLevel::Enum aLevel, const QString & aDescription, int aStatus);
private:
void doDetect(const QString & aDeviceType);
bool initializeDevice(const QString & aConfigName, SDK::Driver::IDevice * aDevice);
void statusChanged(SDK::Driver::IDevice * aDevice, Status & aStatus);
private slots:
void onDeviceDetected(const QString & aConfigName, SDK::Driver::IDevice * aDevice);
void onDetectionFinished();
void onDeviceStatus(SDK::Driver::EWarningLevel::Enum aLevel, const QString & aDescription, int aStatus);
private:
DeviceManager * mDeviceManager;
/// Общий список параметров, необходимых для инициализации устройств.
QMap<QString, QVariantMap> mInitParameters;
/// Здесь хранится результат запуска detectа.
QFutureWatcher<void> mDetectionResult;
mutable QMutex mAccessMutex;
/// Список всех использованных устройств.
typedef QMap<QString, SDK::Driver::IDevice *> TAcquiredDevices;
TAcquiredDevices mAcquiredDevices;
/// Кэш для статусов устройств.
QMap<QString, Status> mDeviceStatusCache;
/// Параметр момента создания устройств
QMap<QString, int> mDeviceCreationOrder;
IApplication * mApplication;
ILog * mLog;
IHardwareDatabaseUtils * mDatabaseUtils;
IntegratedDrivers mIntegratedDrivers;
};
//------------------------------------------------------------------------------
/* @file Реализация сервиса для работы с устройствами. */
#pragma once
// Qt
#include <Common/QtHeadersBegin.h>
#include <QtCore/QStringList>
#include <QtCore/QFutureWatcher>
#include <QtCore/QMutex>
#include <QtCore/QSet>
#include <Common/QtHeadersEnd.h>
// Modules
#include <Common/ILog.h>
// SDK
#include <SDK/Drivers/IDevice.h>
#include <SDK/Plugins/IPLuginLoader.h>
// PP Core
#include <SDK/PaymentProcessor/Core/IDeviceService.h>
#include <SDK/Plugins/IPluginLoader.h>
#include <SDK/Plugins/PluginParameters.h>
#include <SDK/PaymentProcessor/Core/IService.h>
#include <SDK/PaymentProcessor/Core/Event.h>
// Project
#include "IntegratedDrivers.h"
class IApplication;
class IHardwareDatabaseUtils;
class DeviceManager;
//TODO #29565 - метод перезаписи статуса модема, пока не отрефакторили соединение и модем в единое целое
#pragma deprecated(overwriteDeviceStatus)
/// Варианты момента создания устройства
namespace EDeviceCreationOrder
{
enum Enum
{
OnDemand,
AtStart
};
}
//------------------------------------------------------------------------------
/// Реализация сервиса для работы с устройствами.
class DeviceService :
public SDK::PaymentProcessor::IDeviceService,
public SDK::PaymentProcessor::IService
{
Q_OBJECT
public:
/// структура - статус устройства
class Status : public SDK::PaymentProcessor::IDeviceStatus
{
public:
Status();
Status(const Status & aStatus);
explicit Status(SDK::Driver::EWarningLevel::Enum aLevel, const QString & aDescription, int aStatus);
public:
/// Уровень тревожности
virtual SDK::Driver::EWarningLevel::Enum level() const;
/// Описание статуса
virtual const QString & description() const;
/// Проверить содержимое статуса на удовлетворение определенному уровню
bool isMatched(SDK::Driver::EWarningLevel::Enum aLevel) const;
public:
SDK::Driver::EWarningLevel::Enum mLevel;
QString mDescription;
int mStatus;
};
public:
/// Получение экземпляра DeviceService.
static DeviceService * instance(IApplication * aApplication);
DeviceService(IApplication * aApplication);
virtual ~DeviceService();
/// Инициализация сервиса.
virtual bool initialize();
/// IService: Закончена инициализация всех сервисов.
virtual void finishInitialize();
/// Возвращает false, если сервис не может быть остановлен в текущий момент.
virtual bool canShutdown();
/// Завершение работы сервиса.
virtual bool shutdown();
/// Возвращает имя сервиса.
virtual QString getName() const;
/// Получение списка зависимостей.
virtual const QSet<QString> & getRequiredServices() const;
/// Получить параметры сервиса.
virtual QVariantMap getParameters() const;
/// Сброс служебной информации.
virtual void resetParameters(const QSet<QString> & aParameters);
// IDeviceService
/// Неблокирующий поиск всех устройств.
virtual void detect(const QString & aDeviceType);
/// Прервать поиск устройств.
virtual void stopDetection();
/// Получить полный список конфигураций.
virtual QStringList getConfigurations(bool aAllowOldConfigs = true) const;
/// Сохранить cписок конфигураций.
virtual bool saveConfigurations(const QStringList & aConfigList);
/// Добавить список параметров, необходимых для инициализации устройств.
virtual void setInitParameters(const QString & aDeviceType, const QVariantMap & aParameters);
/// Подключение/захват устройства. aDeviceNumber - номер среди одинаковых устройств.
virtual SDK::Driver::IDevice * acquireDevice(const QString & aInstancePath);
/// Создание устройства.
virtual QString createDevice(const QString & aDriverPath, const QVariantMap & aConfig);
/// Отключение/освобождение указанного устройства.
virtual void releaseDevice(SDK::Driver::IDevice * aDevice);
/// Обновить прошивку устройства.
virtual UpdateFirmwareResult updateFirmware(const QByteArray & aFirmware, const QString & aDeviceGUID);
/// Получение списка параметров драйвера.
virtual SDK::Plugin::TParameterList getDriverParameters(const QString & aDriverPath) const;
/// Получить конфигурацию утройства и всех, связанных с ним.
virtual QVariantMap getDeviceConfiguration(const QString & aConfigName);
/// Устанавливает конфигурацию устройству.
virtual void setDeviceConfiguration(const QString & aConfigName, const QVariantMap & aConfig);
/// Получение списка драверов (поддерживаемых устройств).
virtual SDK::PaymentProcessor::TModelList getModelList(const QString & aFilter) const;
/// Получение списка драйверов.
virtual QStringList getDriverList() const;
/// Возвращает список имен созданных устройств.
virtual QStringList getAcquiredDevicesList() const;
/// Получить имя конфига по устроойству.
virtual QString getDeviceConfigName(SDK::Driver::IDevice * aDevice);
/// Получить статус устройства по имени конфигурации.
virtual QSharedPointer<SDK::PaymentProcessor::IDeviceStatus> getDeviceStatus(const QString & aConfigName);
/// Освобождает все устройства.
virtual void releaseAll();
/// Перезаписать статус устройства (#29565)
virtual void overwriteDeviceStatus(SDK::Driver::IDevice * aDevice, SDK::Driver::EWarningLevel::Enum aLevel, const QString & aDescription, int aStatus);
private:
void doDetect(const QString & aDeviceType);
bool initializeDevice(const QString & aConfigName, SDK::Driver::IDevice * aDevice);
void statusChanged(SDK::Driver::IDevice * aDevice, Status & aStatus);
private slots:
void onDeviceDetected(const QString & aConfigName, SDK::Driver::IDevice * aDevice);
void onDetectionFinished();
void onDeviceStatus(SDK::Driver::EWarningLevel::Enum aLevel, const QString & aDescription, int aStatus);
private:
DeviceManager * mDeviceManager;
/// Общий список параметров, необходимых для инициализации устройств.
QMap<QString, QVariantMap> mInitParameters;
/// Здесь хранится результат запуска detectа.
QFutureWatcher<void> mDetectionResult;
mutable QMutex mAccessMutex;
/// Список всех использованных устройств.
typedef QMap<QString, SDK::Driver::IDevice *> TAcquiredDevices;
TAcquiredDevices mAcquiredDevices;
/// Кэш для статусов устройств.
QMap<QString, Status> mDeviceStatusCache;
/// Параметр момента создания устройств
QMap<QString, int> mDeviceCreationOrder;
IApplication * mApplication;
ILog * mLog;
IHardwareDatabaseUtils * mDatabaseUtils;
IntegratedDrivers mIntegratedDrivers;
};
//------------------------------------------------------------------------------

+ 364
- 363
3.0/src/apps/PaymentProcessor/src/Services/FirmwareUploadScenario.cpp View File

@@ -1,363 +1,364 @@
/* @file Плагин сценария меню платежной книжки */

// Qt
#include <Common/QtHeadersBegin.h>
#include <QtCore/QCryptographicHash>
#include <QtCore/QDir>
#include <Common/QtHeadersEnd.h>

// PaymentProcessor SDK
#include <SDK/PaymentProcessor/Core/ICore.h>
#include <SDK/PaymentProcessor/Components.h>
#include <SDK/PaymentProcessor/Core/IGUIService.h>

// Driver SDK
#include <SDK/Drivers/IDevice.h>
#include <SDK/Drivers/HardwareConstants.h>

// Modules
#include "UpdateEngine/ReportBuilder.h"

// Project
#include "System/IApplication.h"
#include "TerminalService.h"
#include "GUIService.h"
#include "DeviceService.h"
#include "EventService.h"
#include "FirmwareUploadScenario.h"

namespace PPSDK = SDK::PaymentProcessor;

//--------------------------------------------------------------------------
namespace CFirmwareUploadScenario
{
const QString Name = "FirmwareUpload";

const int UploadRetryTimeout = 10 * 1000;
const int DeviceInitializedTimeout = 10 * 60 * 1000;
}

//---------------------------------------------------------------------------
FirmwareUploadScenario::FirmwareUploadScenario(IApplication * aApplication) :
Scenario(CFirmwareUploadScenario::Name, ILog::getInstance(CFirmwareUploadScenario::Name)),
mApplication(aApplication),
mRetryCount(2),
mDevice(nullptr)
{
mReportBuilder = new ReportBuilder(mApplication->getWorkingDirectory());
}

//---------------------------------------------------------------------------
FirmwareUploadScenario::~FirmwareUploadScenario()
{
delete mReportBuilder;
}

//---------------------------------------------------------------------------
bool FirmwareUploadScenario::initialize(const QList<GUI::SScriptObject> & /*aScriptObjects*/)
{
return true;
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::start(const QVariantMap & aContext)
{
Q_UNUSED(aContext);

mTimeoutTimer.stop();

lockGUI();

mCommand = RemoteService::instance(mApplication)->findUpdateCommand(PPSDK::IRemoteService::FirmwareUpload);

if (!mCommand.isValid())
{
toLog(LogLevel::Error, "Not found active FirmwareUpload command.");

GUIService::instance(mApplication)->disable(false);

QVariantMap parameters;
parameters.insert("result", "abort");
emit finished(parameters);

return;
}

toLog(LogLevel::Normal, QString("Command %1 loaded.").arg(mCommand.ID));

mReportBuilder->open(QString::number(mCommand.ID), mCommand.configUrl.toString(), mCommand.parameters.at(2));
mReportBuilder->setStatus(PPSDK::IRemoteService::Executing);

QFile firmwareFile(mApplication->getWorkingDirectory() + "/update/" + mCommand.parameters.at(1) + "/firmware.bin");
if (firmwareFile.open(QIODevice::ReadOnly))
{
mFirmware = firmwareFile.readAll();
firmwareFile.close();

toLog(LogLevel::Normal, QString("Firmware readed from file. size=%1.").arg(mFirmware.size()));
}
else
{
mRetryCount = 0;
abortScenario(QString("Error open file %1.").arg(firmwareFile.fileName()));
return;
}

if (QCryptographicHash::hash(mFirmware, QCryptographicHash::Md5).toHex().toLower() != mCommand.parameters.at(2).toLower())
{
mRetryCount = 0;
abortScenario("Firmware MD5 verify failed.");
return;
}

toLog(LogLevel::Normal, QString("Firmware MD5 verify OK. (%1).").arg(mCommand.parameters.at(2)));

QMetaObject::invokeMethod(this, "acquireDevice", Qt::QueuedConnection);
return;
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::stop()
{
if (mReportBuilder)
{
mReportBuilder->close();
}
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::pause()
{
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::resume(const QVariantMap & /*aContext*/)
{
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::signalTriggered(const QString & /*aSignal*/, const QVariantMap & /*aArguments*/)
{
}

//---------------------------------------------------------------------------
QString FirmwareUploadScenario::getState() const
{
return QString("main");
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::onTimeout()
{
}

//--------------------------------------------------------------------------
bool FirmwareUploadScenario::canStop()
{
return false;
}

//--------------------------------------------------------------------------
void FirmwareUploadScenario::lockGUI()
{
auto guiService = GUIService::instance(mApplication);

// Показываем экран блокировки и определяем, что делать дальше.
guiService->show("SplashScreen", QVariantMap());

QVariantMap parameters;
parameters.insert("firmware_upload", true);

guiService->notify("SplashScreen", parameters);
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::abortScenario(const QString & aErrorMessage)
{
toLog(LogLevel::Error, aErrorMessage);

if (--mRetryCount > 0)
{
toLog(LogLevel::Normal, QString("Retry upload throw %1 sec").arg(CFirmwareUploadScenario::UploadRetryTimeout / 1000));

if (mDevice)
{
QTimer::singleShot(CFirmwareUploadScenario::UploadRetryTimeout, this, SLOT(onDeviceInitialized()));
}
else
{
QTimer::singleShot(CFirmwareUploadScenario::UploadRetryTimeout, this, SLOT(acquireDevice()));
}

return;
}

killTimer(mDeviceInitializedTimer);

if (mDevice)
{
disconnect(dynamic_cast<QObject *>(mDevice), SDK::Driver::IDevice::InitializedSignal, this, SLOT(onDeviceInitialized()));
disconnect(dynamic_cast<QObject *>(mDevice), SDK::Driver::IDevice::UpdatedSignal, this, SLOT(onUpdated(bool)));

DeviceService::instance(mApplication)->releaseDevice(mDevice);
mDevice = nullptr;
}

mReportBuilder->setStatusDescription(aErrorMessage);
mReportBuilder->setStatus(PPSDK::IRemoteService::Error);

cleanFirmwareArtifacts();

EventService::instance(mApplication)->sendEvent(PPSDK::Event(PPSDK::EEventType::Restart));
QVariantMap parameters;
parameters.insert("result", "abort");
emit finished(parameters);
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::acquireDevice()
{
SDK::Driver::IDevice * device = nullptr;
QString deviceConfig;

foreach (auto config, DeviceService::instance(mApplication)->getConfigurations())
{
if (config.contains(mCommand.parameters.at(1)))
{
deviceConfig = config;
device = DeviceService::instance(mApplication)->acquireDevice(config);
break;
}
}

if (device == nullptr)
{
abortScenario(QString("Not found device with GUID:%1.").arg(mCommand.parameters.at(1)));
return;
}

toLog(LogLevel::Normal, QString("Device '%1' acquire OK.").arg(device->getName()));

if (!connect(dynamic_cast<QObject *>(device), SDK::Driver::IDevice::UpdatedSignal, this, SLOT(onUpdated(bool))))
{
abortScenario("Fail connect to device UpdatedSignal.");
return;
}

toLog(LogLevel::Normal, "Device UpdatedSignal connected.");

// Проверяем в каком состоянии находится устройство
auto status = DeviceService::instance(mApplication)->getDeviceStatus(deviceConfig);
if (status && status->isMatched(SDK::Driver::EWarningLevel::Warning))
{
toLog(LogLevel::Normal, QString("Device '%1' have status: %2.").arg(device->getName()).arg(status->description()));

mDevice = device;

QMetaObject::invokeMethod(this, "onDeviceInitialized", Qt::QueuedConnection);
}
else
{

if (!connect(dynamic_cast<QObject *>(device), SDK::Driver::IDevice::InitializedSignal, this, SLOT(onDeviceInitialized())))
{
abortScenario("Fail connect to device Initialized signal.");
return;
}

toLog(LogLevel::Normal, "Device Initialized signal connected.");

mDevice = device;

auto configuration = device->getDeviceConfiguration();
int waitInitializedTimeout = configuration.contains(CHardwareSDK::WaitUpdatingTimeout) ?
configuration.value(CHardwareSDK::WaitUpdatingTimeout).toInt() : CFirmwareUploadScenario::DeviceInitializedTimeout;

// Здесь ждём инициализации устройства -> onDeviceInitialized()
// Если не инициализировались в течении DeviceInitializedTimeout, то обрываем сценарий
mDeviceInitializedTimer = startTimer(waitInitializedTimeout);

toLog(LogLevel::Normal, "Wait for device initialize...");
}
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::timerEvent(QTimerEvent * aEvent)
{
if (aEvent->timerId() == mDeviceInitializedTimer)
{
killTimer(mDeviceInitializedTimer);

abortScenario("Device initialization timeout.");
}
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::onDeviceInitialized()
{
toLog(LogLevel::Normal, "Device initialized.");

killTimer(mDeviceInitializedTimer);
disconnect(dynamic_cast<QObject *>(mDevice), SDK::Driver::IDevice::InitializedSignal, this, SLOT(onDeviceInitialized()));

if (!mDevice)
{
abortScenario("onDeviceInitialized but mDevice isNULL.");
return;
}

if (!mDevice->canUpdateFirmware())
{
abortScenario("Device can't update.");
return;
}

toLog(LogLevel::Normal, "START upload firmware.");

mDevice->updateFirmware(mFirmware);
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::onUpdated(bool aSuccess)
{
if (aSuccess)
{
toLog(LogLevel::Normal, "Firmware upload OK.");

mReportBuilder->setStatusDescription("OK");
mReportBuilder->setStatus(PPSDK::IRemoteService::OK);
}
else
{
toLog(LogLevel::Error, "Firmware upload failed. See the log for details device errors.");

mReportBuilder->setStatusDescription("Fail");
mReportBuilder->setStatus(PPSDK::IRemoteService::Error);
}

cleanFirmwareArtifacts();

EventService::instance(mApplication)->sendEvent(PPSDK::Event(PPSDK::EEventType::Restart));
QVariantMap parameters;
parameters.insert("result", aSuccess ? "ok" : "error");
emit finished(parameters);
}

//---------------------------------------------------------------------------
void FirmwareUploadScenario::cleanFirmwareArtifacts()
{
killTimer(mDeviceInitializedTimer);

if (mCommand.isValid())
{
QDir updateDir(mApplication->getWorkingDirectory() + "/update/" + mCommand.parameters.at(1));

updateDir.remove("firmware.bin");
updateDir.cdUp();
updateDir.rmdir(mCommand.parameters.at(1));
}
}

//---------------------------------------------------------------------------
/* @file Плагин сценария меню платежной книжки */
// Qt
#include <Common/QtHeadersBegin.h>
#include <QtCore/QCryptographicHash>
#include <QtCore/QDir>
#include <Common/QtHeadersEnd.h>
// PaymentProcessor SDK
#include <SDK/PaymentProcessor/Core/ICore.h>
#include <SDK/PaymentProcessor/Components.h>
#include <SDK/PaymentProcessor/Core/IGUIService.h>
// Driver SDK
#include <SDK/Drivers/IDevice.h>
#include <SDK/Drivers/HardwareConstants.h>
// Modules
#include "UpdateEngine/ReportBuilder.h"
// Project
#include "System/IApplication.h"
#include "TerminalService.h"
#include "GUIService.h"
#include "DeviceService.h"
#include "EventService.h"
#include "FirmwareUploadScenario.h"
namespace PPSDK = SDK::PaymentProcessor;
//--------------------------------------------------------------------------
namespace CFirmwareUploadScenario
{
const QString Name = "FirmwareUpload";
const int UploadRetryTimeout = 10 * 1000;
const int DeviceInitializedTimeout = 10 * 60 * 1000;
}
//---------------------------------------------------------------------------
FirmwareUploadScenario::FirmwareUploadScenario(IApplication * aApplication) :
Scenario(CFirmwareUploadScenario::Name, ILog::getInstance(CFirmwareUploadScenario::Name)),
mApplication(aApplication),
mRetryCount(2),
mDevice(nullptr),
mDeviceInitializedTimer(0)
{
mReportBuilder = new ReportBuilder(mApplication->getWorkingDirectory());
}
//---------------------------------------------------------------------------
FirmwareUploadScenario::~FirmwareUploadScenario()
{
delete mReportBuilder;
}
//---------------------------------------------------------------------------
bool FirmwareUploadScenario::initialize(const QList<GUI::SScriptObject> & /*aScriptObjects*/)
{
return true;
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::start(const QVariantMap & aContext)
{
Q_UNUSED(aContext);
mTimeoutTimer.stop();
lockGUI();
mCommand = RemoteService::instance(mApplication)->findUpdateCommand(PPSDK::IRemoteService::FirmwareUpload);
if (!mCommand.isValid())
{
toLog(LogLevel::Error, "Not found active FirmwareUpload command.");
GUIService::instance(mApplication)->disable(false);
QVariantMap parameters;
parameters.insert("result", "abort");
emit finished(parameters);
return;
}
toLog(LogLevel::Normal, QString("Command %1 loaded.").arg(mCommand.ID));
mReportBuilder->open(QString::number(mCommand.ID), mCommand.configUrl.toString(), mCommand.parameters.at(2));
mReportBuilder->setStatus(PPSDK::IRemoteService::Executing);
QFile firmwareFile(mApplication->getWorkingDirectory() + "/update/" + mCommand.parameters.at(1) + "/firmware.bin");
if (firmwareFile.open(QIODevice::ReadOnly))
{
mFirmware = firmwareFile.readAll();
firmwareFile.close();
toLog(LogLevel::Normal, QString("Firmware readed from file. size=%1.").arg(mFirmware.size()));
}
else
{
mRetryCount = 0;
abortScenario(QString("Error open file %1.").arg(firmwareFile.fileName()));
return;
}
if (QCryptographicHash::hash(mFirmware, QCryptographicHash::Md5).toHex().toLower() != mCommand.parameters.at(2).toLower())
{
mRetryCount = 0;
abortScenario("Firmware MD5 verify failed.");
return;
}
toLog(LogLevel::Normal, QString("Firmware MD5 verify OK. (%1).").arg(mCommand.parameters.at(2)));
QMetaObject::invokeMethod(this, "acquireDevice", Qt::QueuedConnection);
return;
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::stop()
{
if (mReportBuilder)
{
mReportBuilder->close();
}
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::pause()
{
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::resume(const QVariantMap & /*aContext*/)
{
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::signalTriggered(const QString & /*aSignal*/, const QVariantMap & /*aArguments*/)
{
}
//---------------------------------------------------------------------------
QString FirmwareUploadScenario::getState() const
{
return QString("main");
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::onTimeout()
{
}
//--------------------------------------------------------------------------
bool FirmwareUploadScenario::canStop()
{
return false;
}
//--------------------------------------------------------------------------
void FirmwareUploadScenario::lockGUI()
{
auto guiService = GUIService::instance(mApplication);
// Показываем экран блокировки и определяем, что делать дальше.
guiService->show("SplashScreen", QVariantMap());
QVariantMap parameters;
parameters.insert("firmware_upload", true);
guiService->notify("SplashScreen", parameters);
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::abortScenario(const QString & aErrorMessage)
{
toLog(LogLevel::Error, aErrorMessage);
if (--mRetryCount > 0)
{
toLog(LogLevel::Normal, QString("Retry upload throw %1 sec").arg(CFirmwareUploadScenario::UploadRetryTimeout / 1000));
if (mDevice)
{
QTimer::singleShot(CFirmwareUploadScenario::UploadRetryTimeout, this, SLOT(onDeviceInitialized()));
}
else
{
QTimer::singleShot(CFirmwareUploadScenario::UploadRetryTimeout, this, SLOT(acquireDevice()));
}
return;
}
killTimer(mDeviceInitializedTimer);
if (mDevice)
{
disconnect(dynamic_cast<QObject *>(mDevice), SDK::Driver::IDevice::InitializedSignal, this, SLOT(onDeviceInitialized()));
disconnect(dynamic_cast<QObject *>(mDevice), SDK::Driver::IDevice::UpdatedSignal, this, SLOT(onUpdated(bool)));
DeviceService::instance(mApplication)->releaseDevice(mDevice);
mDevice = nullptr;
}
mReportBuilder->setStatusDescription(aErrorMessage);
mReportBuilder->setStatus(PPSDK::IRemoteService::Error);
cleanFirmwareArtifacts();
EventService::instance(mApplication)->sendEvent(PPSDK::Event(PPSDK::EEventType::Restart));
QVariantMap parameters;
parameters.insert("result", "abort");
emit finished(parameters);
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::acquireDevice()
{
SDK::Driver::IDevice * device = nullptr;
QString deviceConfig;
foreach (auto config, DeviceService::instance(mApplication)->getConfigurations())
{
if (config.contains(mCommand.parameters.at(1)))
{
deviceConfig = config;
device = DeviceService::instance(mApplication)->acquireDevice(config);
break;
}
}
if (device == nullptr)
{
abortScenario(QString("Not found device with GUID:%1.").arg(mCommand.parameters.at(1)));
return;
}
toLog(LogLevel::Normal, QString("Device '%1' acquire OK.").arg(device->getName()));
if (!connect(dynamic_cast<QObject *>(device), SDK::Driver::IDevice::UpdatedSignal, this, SLOT(onUpdated(bool))))
{
abortScenario("Fail connect to device UpdatedSignal.");
return;
}
toLog(LogLevel::Normal, "Device UpdatedSignal connected.");
// Проверяем в каком состоянии находится устройство
auto status = DeviceService::instance(mApplication)->getDeviceStatus(deviceConfig);
if (status && status->isMatched(SDK::Driver::EWarningLevel::Warning))
{
toLog(LogLevel::Normal, QString("Device '%1' have status: %2.").arg(device->getName()).arg(status->description()));
mDevice = device;
QMetaObject::invokeMethod(this, "onDeviceInitialized", Qt::QueuedConnection);
}
else
{
if (!connect(dynamic_cast<QObject *>(device), SDK::Driver::IDevice::InitializedSignal, this, SLOT(onDeviceInitialized())))
{
abortScenario("Fail connect to device Initialized signal.");
return;
}
toLog(LogLevel::Normal, "Device Initialized signal connected.");
mDevice = device;
auto configuration = device->getDeviceConfiguration();
int waitInitializedTimeout = configuration.contains(CHardwareSDK::WaitUpdatingTimeout) ?
configuration.value(CHardwareSDK::WaitUpdatingTimeout).toInt() : CFirmwareUploadScenario::DeviceInitializedTimeout;
// Здесь ждём инициализации устройства -> onDeviceInitialized()
// Если не инициализировались в течении DeviceInitializedTimeout, то обрываем сценарий
mDeviceInitializedTimer = startTimer(waitInitializedTimeout);
toLog(LogLevel::Normal, "Wait for device initialize...");
}
}
//---------------------------------------------------------------------------
void FirmwareUploadScenario::timerEvent(QTimerEvent * aEvent)
{
if (aEvent->timerId() == mDeviceInitializedTimer)
{
killTimer(mDeviceInitializedTimer);
abortScenario("Device initialization timeout.");
}
} <