Skip to content
Snippets Groups Projects
Commit add398fe authored by Bensong Liu's avatar Bensong Liu
Browse files

single-flow working

parent 8e7b1ff0
No related branches found
No related tags found
No related merge requests found
#ifndef CIS_WORKFLOW_GEN_ACTIVITY_HPP #ifndef CIS_WORKFLOW_GEN_ACTIVITY_HPP
#define CIS_WORKFLOW_GEN_ACTIVITY_HPP #define CIS_WORKFLOW_GEN_ACTIVITY_HPP
#include <iterator>
#include <string> #include <string>
#include <map> #include <unordered_map>
#include <list>
#include <queue>
#include <algorithm>
#include "uuid.hpp" #include "uuid.hpp"
#include "xaml-template.hpp" #include "xaml-template.hpp"
#include <rlib/string.hpp> #include <rlib/string.hpp>
#include <rlib/require/cxx14>
#include <rlib/scope_guard.hpp>
namespace CIS { namespace CIS {
using std::string; using std::string;
using namespace rlib::literals;
class Flow; class Flow;
class Activity { class Activity {
...@@ -17,35 +25,86 @@ namespace CIS { ...@@ -17,35 +25,86 @@ namespace CIS {
Activity(string displayName, string className, string entityName = "") Activity(string displayName, string className, string entityName = "")
: displayName(displayName), className(className), entityName(entityName), taskId(GenUUID()) {} : displayName(displayName), className(className), entityName(entityName), taskId(GenUUID()) {}
Flow &operator>>(const Flow &seqNext) { Flow operator>>(const Flow &seqNext) const;
return Flow(*this) >> seqNext; Flow operator|(const Flow &seqNext) const;
void addInputSetting(string k, string v) {
inputSettings[k] = v;
} }
private: private:
string displayName, className, entityName; string displayName, className, entityName;
string taskId; string taskId;
std::map<string, string> std::unordered_map<string, string> inputSettings;
}; };
class Flow { class Flow {
public: public:
Flow(const Activity &activity) { Flow(const Activity &activity) {
xamlCode = ACTIVITY_XAML_TEMPLATE; xamlCode = templates::ACTIVITY_XAML_TEMPLATE;
xamlCode.replace("__TEMPLATE_ARG_ClassName", activity.className); xamlCode.replace("__TEMPLATE_ARG_ClassName", activity.className);
xamlCode.replace("__TEMPLATE_ARG_DisplayName", activity.displayName); xamlCode.replace("__TEMPLATE_ARG_DisplayName", activity.displayName);
auto entityXaml = activity.entityName == "" ? "" : rlib::string(ENTITY_DEF_TEMPLATE).replace("__TEMPLATE_ARG_EntityName", activity.entityName); xamlCode.replace("__TEMPLATE_ARG_TaskId", activity.taskId);
auto entityXaml = activity.entityName == "" ? "" : rlib::string(templates::ENTITY_DEF_TEMPLATE).replace("__TEMPLATE_ARG_EntityName", activity.entityName);
xamlCode.replace("__TEMPLATE_ARG_EntityDefPlaceholder", entityXaml); xamlCode.replace("__TEMPLATE_ARG_EntityDefPlaceholder", entityXaml);
std::list<string> inputSettingStrings;
std::transform(activity.inputSettings.begin(), activity.inputSettings.end(), std::back_inserter(inputSettingStrings), [](auto &&kv) {
return "{\"{}\", \"{}\"}"_rs.format(kv.first, kv.second);
});
auto inputSettingsString = ",\n "_rs.join(inputSettingStrings);
xamlCode.replace("__TEMPLATE_ARG_DictLines", inputSettingsString);
} }
Flow(rlib::string xamlCode) : xamlCode(xamlCode) {}
Flow(const Flow &another) : queued(another.queued), xamlCode(another.xamlCode), prevOperationIsSequential(another.prevOperationIsSequential) {}
Flow &operator>>(const Flow &seqNext) { // Actually modify xamlCode on "OperationChange".
// for example, A >> B >> C >> D | E. ABCD should be merged into one sequential operation.
Flow operator>>(const Flow &seqNext) const {
return binaryOperation(seqNext, true);
}
Flow operator|(const Flow &seqNext) const {
return binaryOperation(seqNext, false);
}
rlib::string generateXaml() const {
Flow finalized(*this);
if(!finalized.queued.empty())
finalized.reduceQueued();
return finalized.xamlCode;
} }
private:
bool prevOperationIsSequential = false;
rlib::string xamlCode; rlib::string xamlCode;
std::queue<rlib::string> queued;
Flow binaryOperation(const Flow &seqNext, bool thisOperationIsSequential) const {
Flow result = *this;
if(thisOperationIsSequential != prevOperationIsSequential && !queued.empty()) {
result.reduceQueued();
}
result.prevOperationIsSequential = thisOperationIsSequential;
result.queued.push(seqNext.xamlCode);
return result;
}
void reduceQueued() {
rlib::string resultXaml = prevOperationIsSequential ? templates::SEQ_BEGIN : templates::PAR_BEGIN;
resultXaml += xamlCode;
while(!queued.empty())
resultXaml += queued.front(), queued.pop();
resultXaml += prevOperationIsSequential ? templates::SEQ_END : templates::PAR_END;
xamlCode = std::move(resultXaml);
}
}; };
inline Flow Activity::operator>>(const Flow &seqNext) const {
return Flow(*this) >> seqNext;
}
inline Flow Activity::operator|(const Flow &seqNext) const {
return Flow(*this) >> seqNext;
}
struct Workflow { struct Workflow {
std::list<string> assemblyReferences; std::list<string> assemblyReferences;
......
#include <rlib/stdio.hpp>
#include "activity.hpp"
using namespace CIS;
...@@ -4,7 +4,7 @@ ...@@ -4,7 +4,7 @@
#include <random> #include <random>
#include <string> #include <string>
inline static string GenUUID() { inline static std::string GenUUID() {
static std::random_device dev; static std::random_device dev;
static std::mt19937 rng(dev()); static std::mt19937 rng(dev());
......
...@@ -2,10 +2,15 @@ ...@@ -2,10 +2,15 @@
#define XAML_TEMPLATE_HPP #define XAML_TEMPLATE_HPP
#include <string> #include <string>
namespace CIS::impl { #include <rlib/require/cxx14>
constexpr auto ACTIVITY_XAML_TEMPLATE = R"XAMLTL( namespace CIS {
<mwcwa:ControlledActivity ClassName="__TEMPLATE_ARG_ClassName" DisplayName="__TEMPLATE_ARG_DisplayName" TaskId="__TEMPLATE_ARG_TaskId" __TEMPLATE_ARG_EntityDefPlaceholder> namespace templates {
// Rule: Every end-of-line should contains a \n
constexpr auto ACTIVITY_XAML_TEMPLATE =
R"XAMLTL( <mwcwa:ControlledActivity ClassName="__TEMPLATE_ARG_ClassName" DisplayName="__TEMPLATE_ARG_DisplayName" TaskId="__TEMPLATE_ARG_TaskId" __TEMPLATE_ARG_EntityDefPlaceholder>
<mwcwa:ControlledActivity.InputSettings> <mwcwa:ControlledActivity.InputSettings>
<InArgument x:TypeArguments="scg:Dictionary(x:String, x:String)"> <InArgument x:TypeArguments="scg:Dictionary(x:String, x:String)">
<mca:CSharpValue x:TypeArguments="scg:Dictionary(x:String, x:String)" xml:space="preserve"> <mca:CSharpValue x:TypeArguments="scg:Dictionary(x:String, x:String)" xml:space="preserve">
...@@ -17,11 +22,19 @@ constexpr auto ACTIVITY_XAML_TEMPLATE = R"XAMLTL( ...@@ -17,11 +22,19 @@ constexpr auto ACTIVITY_XAML_TEMPLATE = R"XAMLTL(
</InArgument> </InArgument>
</mwcwa:ControlledActivity.InputSettings> </mwcwa:ControlledActivity.InputSettings>
</mwcwa:ControlledActivity> </mwcwa:ControlledActivity>
)XAMLTL" )XAMLTL";
constexpr auto ENTITY_DEF_TEMPLATE = R"(coordination:DependencyBinder.EntityName="__TEMPLATE_ARG_EntityName")";
constexpr auto ENTITY_DEF_TEMPLATE = R"XAMLTL(coordination:DependencyBinder.EntityName="__TEMPLATE_ARG_EntityName")XAMLTL"; constexpr auto SEQ_BEGIN = R"( <mwcwa:ControlledSequence IsHiddenFromOperator="False">)" "\n";
constexpr auto SEQ_END = R"( </mwcwa:ControlledSequence>)" "\n";
constexpr auto PAR_BEGIN = R"( <mwcwa:ControlledParallel IsHiddenFromOperator="False">)" "\n";
constexpr auto PAR_END = R"( </mwcwa:ControlledParallel>)" "\n";
}
} }
#endif #endif
#include "activity.hpp"
#include "quick-include.hpp"
// Define some handy c# types. int main() {
auto dict = 'System.Collections.Generic.Dictionary<string, string>'; Activity SCS ("SCS", "FleetAGC.Activities.WriteTraceinfo", "PreRteg.InitiateBareMetalComplete");
SCS.addInputSetting("Message", "Doing SCS");
Activity SearchFarms ("Search Farms", "FleetAGC.Activities.WriteTraceinfo");
SearchFarms.addInputSetting("Message", "fuck");
SearchFarms.addInputSetting("AnotherMessage", "shit");
// Define activities. rlib::println(((SCS >> SearchFarms) | SCS).generateXaml());
Activity SCS (ClassName='...', EntityName='...'); }
// SCS.AddRawArgument(Type=dict, CSharpCode='new Dictionary() {{"Message", "Doing SCS"}}');
SCS.AddInputSetting("Message", "Doing SCS"); /*
Activity SearchAnalytics (......); Activity SearchAnalytics (......);
SearchAnalytics.AddArgument(......); SearchAnalytics.AddArgument(......);
......; ......;
...@@ -19,3 +25,4 @@ auto block4 = IC3Tooling -> (MonitoringSetup | (MicroServices -> DevelopmentVali ...@@ -19,3 +25,4 @@ auto block4 = IC3Tooling -> (MonitoringSetup | (MicroServices -> DevelopmentVali
(block1 | 3SConfigAndInterop | block3 | block4).GenerateXaml("/home/recolic/code/Azure/myWorkflow.xaml"); (block1 | 3SConfigAndInterop | block3 | block4).GenerateXaml("/home/recolic/code/Azure/myWorkflow.xaml");
*/
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment