// Merges the appdefs from the plan with the current ones (add new, replace existing). private void AdoptPlan(ILaunchPlan plan) { // add record for not yet existing apps foreach (var a in plan.getAppDefs()) { if (!appsState.ContainsKey(a.AppIdTuple)) { appsState[a.AppIdTuple] = new AppState() { Initialized = false, Running = false, Started = false, Disabled = a.Disabled }; } if (a.AppIdTuple.MachineId == machineId) { if (!localApps.ContainsKey(a.AppIdTuple)) { localApps[a.AppIdTuple] = new LocalApp() { AppDef = a, launcher = null, watchers = new List <IAppWatcher>() }; } else // app already exists, just update its appdef to be used on next launch { localApps[a.AppIdTuple].AppDef = a; } } } }
public void SetPlanRepo(IEnumerable <ILaunchPlan> planRepo) { if (planRepo == null) { this.planRepo = new List <ILaunchPlan>(); } else { this.planRepo = new List <ILaunchPlan>(planRepo); } // populate planRTInfo accordingly foreach (var p in planRepo) { planRTInfo[p.Name] = new PlanRuntimeInfo(p); AdoptPlan(p); } // update current plan // replace also current plan instances so we are using the new one // (possible the one created by remoting from a network message), // instead of the default one created from local application config if (this.currentPlan != null) { string currentPlanName = currentPlan.Name; this.currentPlan = null; foreach (var p in planRepo) { if (p.Name == currentPlanName) // is one of the new plans matching our current plan? { currentPlan = p; } } } }
List<ILaunchPlan> planRepo; // current plan repo #endregion Fields #region Constructors //void terminateFromConstructor() //{ // Load += (s, e) => Close(); //} /// <summary> /// Dirigent Agent GUI main form constructor /// </summary> /// <param name="ctrl">instance of object providing dirigent operations</param> /// <param name="planRepo">planRepo to be used until a new one is received from the master; null if none</param> /// <param name="machineId">machine id (part of application id in launch plans); informative only; used to be presented to the user</param> /// <param name="clientId">name of network client used to mark the network messages; informative only; used to recognize incoming errors caused by request from this agent</param> /// <param name="notifyIcon">instance of notify icon</param> /// <param name="allowLocalIfDisconnected">if true, apps and plans can be operated locally even if not connected to master</param> /// <param name="callbacks">bunch of callbacks</param> public frmMain( IDirigentControl ctrl, IEnumerable<ILaunchPlan> planRepo, string machineId, string clientId, NotifyIcon notifyIcon, bool allowLocalIfDisconnected, GuiAppCallbacks callbacks ) { this.ctrl = ctrl; this.machineId = machineId; this.clientId = clientId; this.callbacks = callbacks; this.notifyIcon = notifyIcon; this.allowLocalIfDisconnected = allowLocalIfDisconnected; InitializeComponent(); //setDoubleBuffered(gridApps, true); // not needed anymore, DataViewGrid does not flicker this.plan = null; if (planRepo != null) { this.planRepo = new List<ILaunchPlan>(planRepo); populatePlanLists(); } // start ticking tmrTick.Enabled = true; }
public bool Equals(ILaunchPlan other) { if (other == null) return false; if (this.Name == other.Name && this.appDefs.SequenceEqual( other.getAppDefs() ) ) return true; else return false; }
public LocalOperations( string machineId, ILauncherFactory launcherFactory, IAppInitializedDetectorFactory appAppInitializedDetectorFactory, string rootForRelativePaths) { this.launcherFactory = launcherFactory; this.appAppInitializedDetectorFactory = appAppInitializedDetectorFactory; this.rootForRelativePaths = rootForRelativePaths; appsState = new Dictionary <AppIdTuple, AppState>(); localApps = new Dictionary <AppIdTuple, LocalApp>(); currentPlan = null; planRepo = new List <ILaunchPlan>(); this.machineId = machineId; }
public LocalOperations( string machineId, ILauncherFactory launcherFactory, IAppInitializedDetectorFactory appAppInitializedDetectorFactory ) { this.launcherFactory = launcherFactory; this.appAppInitializedDetectorFactory = appAppInitializedDetectorFactory; appsState = new Dictionary<AppIdTuple,AppState>(); localApps = new Dictionary<AppIdTuple,LocalApp>(); currentPlan = null; planRepo = new List<ILaunchPlan>(); this.machineId = machineId; launchSequencer = new LaunchSequencer(); }
// Throws exception if plan not found; returns null if empty input arguments are provided. public static ILaunchPlan GetPlanByName(IEnumerable <ILaunchPlan> planRepo, string planName) { // start the initial launch plan if specified if (planRepo != null && planName != null && planName != "") { try { ILaunchPlan plan = planRepo.First((i) => i.Name == planName); return(plan); } catch { throw new UnknownPlanName(planName); } } return(null); }
public bool Equals(ILaunchPlan other) { if (other == null) { return(false); } if (this.Name == other.Name && this.appDefs.SequenceEqual(other.getAppDefs()) ) { return(true); } else { return(false); } }
/// <summary> /// Prepares for starting a new plan. /// </summary> /// <param name="plan"></param> public void SelectPlan(string planName) { // change the current plan to this one if (string.IsNullOrEmpty(planName)) { return; } if (!planRTInfo.ContainsKey(planName)) { log.ErrorFormat("Plan {0} not found.", planName); return; } var plan = planRTInfo[planName].Plan; AdoptPlan(plan); currentPlan = plan; }
public CurrentPlanMessage(ILaunchPlan plan) { this.plan = plan; }
/// <summary> /// Checks dependency conditions and launches apps in wawes /// Launches max. one app at a time, next one earliest after the previous one's separation interval. /// </summary> // FIXME: presunout do PlanRuntimeInfo void processPlan(double currentTime, ILaunchPlan plan) { // too frequent message filling up the log - commented out //log.Debug("processPlan"); if (plan == null) { return; } var rti = planRTInfo[plan.Name]; // if plan is stopped, don't start contained apps if (!rti.State.Running) { return; } // SPECIAL CASE for plans with all-volatile apps // Kill the plan as soon as all apps have terminated. // So the plan can be started again without being manually Killed first. // This is used for utility-plans launching some tools on the stations, // where the tools terminate automatically after they are done with their job. // Note: this won't kill any app as the Kill is initiated when no app is running any more. // (Usual non-volatile plans would not allow next start before prior KillPlan) { var currTime = DateTime.UtcNow; //bool allLaunched = true; //bool allNonVolatileRunning = true; bool anyNonVolatileApp = false; // is there at least one non-volatile? bool allAppsProcessed = true; bool anyStillRunning = false; foreach (var appDef in rti.Plan.getAppDefs()) { var apst = appsState[appDef.AppIdTuple]; bool isRemoteApp = appDef.AppIdTuple.MachineId != this.machineId; var statusInfoAge = currTime - apst.LastChange; bool offline = (isRemoteApp && statusInfoAge > TimeSpan.FromSeconds(3)); { } //if ( !offline & !(apst.PlanApplied && apst.Started && apst.Initialized)) //{ // allLaunched = false; //} if (!offline && !(apst.PlanApplied && (apst.Initialized || apst.StartFailed))) { allAppsProcessed = false; } if (!offline && apst.Running) { anyStillRunning = true; } if (!appDef.Volatile) { anyNonVolatileApp = true; //if (!apst.Running || offline) //{ // allNonVolatileRunning = false; //} } } if (allAppsProcessed && !anyNonVolatileApp && !anyStillRunning) // all apps volatile, all launched and none is running any longer { // Note: this won't kill any app as no apps are running any more. // It just make the plan startable again. KillPlan(plan.Name); } } // if no plan exists // or client re-connected and re-set the plan repo (then we loose the previous RTI) if (rti.launchDepChecker == null) { return; } // feed the sequencer with apps whose dependencies and constraints have already been satisfied if (rti.launchSequencer.IsEmpty()) { rti.launchSequencer.AddApps( rti.launchDepChecker.getAppsToLaunch() ); } // try to get an app to launch and launch it immediately AppDef appToLaunch = rti.launchSequencer.GetNext(currentTime); if (appToLaunch != null) { // remember that the app was already processed by the launch plan and should not be touched again // note: must be called before StartApp otherwise it would be enlessly re-tried by the launch plan if it throws exception during StartUp var la = localApps[appToLaunch.AppIdTuple]; var appState = appsState[la.AppDef.AppIdTuple]; appState.PlanApplied = true; LaunchApp(appToLaunch.AppIdTuple); } }
public LaunchSequencer launchSequencer; // non-null only when plan is running public PlanRuntimeInfo(ILaunchPlan plan) { this.Plan = plan; launchSequencer = new LaunchSequencer(); State = new PlanState(); }
public void LoadPlan(ILaunchPlan plan) { this.plan = plan; client.BroadcastMessage( new LoadPlanMessage( plan ) ); }
public void SelectPlan(ILaunchPlan plan) { impl.SelectPlan(plan); }
public SelectPlanMessage( ILaunchPlan plan ) { this.plan = plan; }
/// <summary> /// returns true if the message was fully handled and shall not be further processed /// </summary> /// <param name="clientName"></param> /// <param name="msg"></param> /// <returns></returns> private bool HandleMessage(Message msg) { Type t = msg.GetType(); if (t == typeof(SelectPlanMessage)) { var m = msg as SelectPlanMessage; lock (clients) { CurrentPlan = m.plan; } } else if (t == typeof(CurrentPlanMessage)) { var m = msg as CurrentPlanMessage; lock (clients) { CurrentPlan = m.plan; } } else if (t == typeof(PlanRepoMessage)) { var m = msg as PlanRepoMessage; lock (clients) { PlanRepo = new List<ILaunchPlan>(m.repo); } } return false; }
/// <summary> /// Prepares for starting a new plan. Merges the appdefs from the plan with the current ones (add new, replace existing). /// </summary> /// <param name="plan"></param> public void SelectPlan(ILaunchPlan plan) { //if (plan == null) //{ // throw new ArgumentNullException("plan"); //} // stop the current plan StopPlan(); // change the current plan to this one currentPlan = plan; if (plan == null) { return; } // add record for not yet existing apps foreach (var a in plan.getAppDefs()) { if (!appsState.ContainsKey(a.AppIdTuple)) { appsState[a.AppIdTuple] = new AppState() { Initialized = false, Running = false, Started = false }; } if (a.AppIdTuple.MachineId == machineId) { if (!localApps.ContainsKey(a.AppIdTuple)) { localApps[a.AppIdTuple] = new LocalApp() { AppDef = a, launcher = null, watchers = new List<IAppWatcher>() }; } else // app already exists, just update its appdef to be used on next launch { localApps[a.AppIdTuple].AppDef = a; } } } }
public void SelectPlan(ILaunchPlan plan) { client.BroadcastMessage( new SelectPlanMessage( plan ) ); }
public void LoadPlan(ILaunchPlan plan) { this.plan = plan; client.BroadcastMessage(new LoadPlanMessage(plan)); }