| ¶Ô±ÈÐÂÎļþ |
| | |
| | | #pragma once |
| | | #include <string> |
| | | #include <vector> |
| | | #include <algorithm> |
| | | #include <cstdint> |
| | | #include <optional> |
| | | #include <chrono> |
| | | #include <functional> |
| | | #include "ProcessJob.h" |
| | | |
| | | |
| | | // ââ æ å/项ç®å
约å®ç屿§åï¼A:40ï¼ââ |
| | | // 说æï¼ä¸ä»¥ç©ºæ ¼å¼å¤´/ç»å°¾ï¼å符èå´ 0x20-0x7Eï¼ä¸ä¸è½å
å« > : ? * ~ |
| | | inline constexpr const char* CJ_ATTR_CJID = "CJID"; // A:n |
| | | inline constexpr const char* CJ_ATTR_PRIORITY = "Priority"; // U1 |
| | | inline constexpr const char* CJ_ATTR_PRJOBLIST = "PRJOBLIST"; // L:n of A:n (PJID[]) |
| | | |
| | | namespace SERVO { |
| | | /// CJ ç¶æï¼è´´è¿ E40 è¯ä¹ï¼ |
| | | enum class CJState : uint8_t { |
| | | NoState = 0, |
| | | Queued, |
| | | Executing, |
| | | Paused, |
| | | Completed, |
| | | Aborted, |
| | | Failed |
| | | }; |
| | | |
| | | /// å建/ä¿®æ¹ç»æä¸çé误项 |
| | | struct CJError { |
| | | uint16_t code; // èªå®ä¹é误ç ï¼ä¾ï¼2001=PJ_NOT_FOUND, 2002=NOT_JOINABLEï¼ |
| | | std::string text; // 建议å
å«å®ä½ä¿¡æ¯ï¼ATTRID/PJIDï¼ |
| | | }; |
| | | |
| | | /// CControlJobï¼Control Job 管çç±» |
| | | class CControlJob { |
| | | public: |
| | | CControlJob(); |
| | | explicit CControlJob(std::string cjId); |
| | | explicit CControlJob(CControlJob& src); |
| | | |
| | | // ââ åºæ¬å±æ§ ââ // |
| | | const std::string& id() const noexcept { return m_cjId; } |
| | | CJState state() const noexcept { return m_state; } |
| | | uint8_t priority() const noexcept { return m_priority; } |
| | | void setPriority(uint8_t p) noexcept { m_priority = p; } |
| | | std::string getStateText(); |
| | | |
| | | // ââ PJ å表维æ¤ï¼å»éï¼ââ // |
| | | bool addPJ(const std::string& pjId); // å·²åå¨åä¸é夿·»å |
| | | bool addPJs(const std::vector<std::string>& ids); // è¿åæ¯å¦ææ°å¢ |
| | | bool removePJ(const std::string& pjId); // åå¨åç§»é¤ |
| | | bool containsPJ(const std::string& pjId) const; |
| | | const std::vector<std::string>& pjIds() const noexcept { return m_pjIds; } |
| | | bool setPJs(const std::vector<CProcessJob*>& pjs); |
| | | void clearPJs() { m_pjIds.clear(); } |
| | | const std::vector<CProcessJob*>& getPjs() { return m_pjs; }; |
| | | |
| | | // ââ æ ¡éª ââ // |
| | | struct ValidationIssue { uint32_t code; std::string text; }; |
| | | |
| | | // æ ¡éª CJ æ¯å¦å¯å建/æ´æ°ï¼ä¾å¦ï¼PJ æ¯å¦åå¨ãæ¯å¦å¯å å
¥ï¼ |
| | | // getPjExistsFn(pjId)->boolï¼PJ æ¯å¦åå¨ |
| | | // canJoinFn(pjId)->bool ï¼PJ å½åæ¯å¦å
许å å
¥ CJï¼å¦ PJ ç¶æä¸º Queued çï¼ |
| | | bool validateForCreate( |
| | | const std::function<bool(uint32_t& code, std::string& msg)>& canCreateCjFn, |
| | | const std::function<bool(const std::string&)>& getPjExistsFn, |
| | | const std::function<bool(const std::string&)>& canJoinFn |
| | | ); |
| | | const std::vector<CControlJob::ValidationIssue>& CControlJob::issues(); |
| | | |
| | | // ââ S14F9 â S14F10 çâåºç¨ç»æâ模å ââ // |
| | | struct CreateRequest { |
| | | std::optional<uint8_t> priority; // è¥æåè¦ç |
| | | std::vector<std::string> requestedPjIds;// æ³è¦ç»å®ç PJ å表 |
| | | }; |
| | | struct CreateResult { |
| | | std::vector<std::string> acceptedPjIds; // æåç»å®ç PJï¼ç¨äºåæ¾ PRJOBLISTï¼ |
| | | std::vector<CJError> errors; // 失败项ï¼å« PJID 说æï¼ |
| | | uint8_t objack{ 0 }; // 0=å
¨æå, 1=é¨åæå, 2=å
¨å¤±è´¥ |
| | | }; |
| | | |
| | | // åºç¨å建/æ´æ°è¯·æ±ï¼åªç»å®å
许ç PJï¼å¹¶çæ OBJACK/é误æ¸
å |
| | | // getPjExistsFn / canJoinFn åä¸ |
| | | CreateResult applyCreate( |
| | | const CreateRequest& req, |
| | | const std::function<bool(const std::string&)>& getPjExistsFn, |
| | | const std::function<bool(const std::string&)>& canJoinFn |
| | | ); |
| | | |
| | | // ââ ç¶ææº ââ // |
| | | bool queue(); // NoState -> Queued |
| | | bool start(); // Queued -> Executing |
| | | bool pause(); // Executing -> Paused |
| | | bool resume(); // Paused -> Executing |
| | | bool complete(); // Executing/Paused -> Completed |
| | | bool abort(); // éç»æ -> Aborted |
| | | bool fail(std::string reason); // ä»»æ -> Failed |
| | | |
| | | const std::string& failReason() const noexcept { return m_failReason; } |
| | | |
| | | // ââ æ¶é´æ³ ââ // |
| | | std::optional<std::chrono::system_clock::time_point> tQueued() const { return m_tQueued; } |
| | | std::optional<std::chrono::system_clock::time_point> tStart() const { return m_tStart; } |
| | | std::optional<std::chrono::system_clock::time_point> tEnd() const { return m_tEnd; } |
| | | |
| | | // ââ æ±æ»ç¶æè¾
å©ï¼å¯éï¼ââ // |
| | | // æ ¹æ®å¤é¨æä¾çâPJ æ¯å¦å·²å®æâ夿ï¼å°è¯æ CJ èå置为 Completedã |
| | | // isPjCompletedFn(pjId)->bool |
| | | bool tryAggregateComplete(const std::function<bool(const std::string&)>& isPjCompletedFn); |
| | | |
| | | // å·¥å
·ï¼ç»ä¸å符串éå¶ |
| | | static void clampString(std::string& s, size_t maxLen); |
| | | static bool asciiPrintable(const std::string& s); |
| | | |
| | | static constexpr uint32_t CJ_MAGIC = 0x434A5031; // "CJP1" |
| | | static constexpr uint16_t CJ_VERSION = 0x0001; |
| | | |
| | | void serialize(std::ostream& os) const; |
| | | static bool deserialize(std::istream& is, CControlJob& out, std::string* err = nullptr); |
| | | |
| | | private: |
| | | void markQueued(); |
| | | void markStart(); |
| | | void markEnd(); |
| | | |
| | | protected: |
| | | // ââ æ è¯ & é
ç½® ââ // |
| | | std::string m_cjId; |
| | | uint8_t m_priority{ 5 }; // 缺çä¼å
级ï¼èªå®ï¼ |
| | | |
| | | // ââ ç»æ ââ // |
| | | std::vector<std::string> m_pjIds; |
| | | std::vector<CProcessJob*> m_pjs; |
| | | |
| | | // ââ ç¶æ / ææ¬ ââ // |
| | | CJState m_state{ CJState::NoState }; |
| | | std::string m_failReason; |
| | | |
| | | // ââ æ¶é´æ³ ââ // |
| | | std::optional<std::chrono::system_clock::time_point> m_tQueued; |
| | | std::optional<std::chrono::system_clock::time_point> m_tStart; |
| | | std::optional<std::chrono::system_clock::time_point> m_tEnd; |
| | | |
| | | // ââ ç»ä¸çº¦æ ââ // |
| | | static constexpr size_t MAX_ID_LEN = 64; // CJID / PJID ç |
| | | |
| | | // é误å表 |
| | | std::vector<ValidationIssue> m_issues; |
| | | }; |
| | | } |
| | | |