[8506] | 1 | using System;
|
---|
| 2 | using System.Collections.Generic;
|
---|
| 3 | using System.Linq;
|
---|
| 4 | using System.Text;
|
---|
| 5 | using HeuristicLab.Services.Optimization.ControllerService.Interfaces;
|
---|
| 6 | using HeuristicLab.Optimization;
|
---|
| 7 | using HeuristicLab.Algorithms.GeneticAlgorithm;
|
---|
| 8 | using HeuristicLab.Problems.TravelingSalesman;
|
---|
| 9 | using HeuristicLab;
|
---|
| 10 | using System.Reflection;
|
---|
| 11 | using HeuristicLab.Services.Optimization.ControllerService.Model;
|
---|
| 12 | using HeuristicLab.Core;
|
---|
| 13 | using System.Collections;
|
---|
| 14 | using HeuristicLab.Clients.Hive;
|
---|
| 15 | using System.Threading;
|
---|
[8545] | 16 | using HeuristicLab.Data;
|
---|
[8506] | 17 |
|
---|
| 18 | namespace HeuristicLab.Services.Optimization.ControllerService {
|
---|
| 19 | public class HiveScenarioManager : IScenarioManager {
|
---|
| 20 | public object MapControllerDataType(object model, Parameter param) {
|
---|
| 21 | switch (param.Type) {
|
---|
| 22 | case ParameterType.Boolean:
|
---|
| 23 | return (param.Value as Model.BoolValue).Value;
|
---|
| 24 | case ParameterType.Integer:
|
---|
| 25 | return Convert.ToInt32((param.Value as Model.DecimalValue).Value);
|
---|
| 26 | case ParameterType.Percent:
|
---|
| 27 | case ParameterType.Decimal:
|
---|
| 28 | return (param.Value as Model.DecimalValue).Value;
|
---|
| 29 | case ParameterType.DecimalMatrix:
|
---|
| 30 | return Utility.ToMultiD(((param.Value as Model.DecimalMatrix).Value));
|
---|
| 31 | case ParameterType.DecimalVector:
|
---|
| 32 | return (param.Value as Model.DecimalVector).Value;
|
---|
| 33 | case ParameterType.Type:
|
---|
| 34 | //TODO handle type correctly!
|
---|
| 35 | var typeValue = param.Value as Model.TypeValue;
|
---|
| 36 |
|
---|
| 37 | IProblem problem = model as IProblem;
|
---|
| 38 | IAlgorithm algoModel = model as IAlgorithm;
|
---|
| 39 | if (problem == null && algoModel != null) {
|
---|
| 40 | problem = algoModel.Problem;
|
---|
| 41 | }
|
---|
| 42 |
|
---|
| 43 | if (problem != null) {
|
---|
| 44 | var toselect = problem.Operators.OfType<IOperator>().FirstOrDefault(x => x.Name == typeValue.Value);
|
---|
| 45 | if (toselect != null) {
|
---|
| 46 | return toselect;
|
---|
| 47 | }
|
---|
| 48 | }
|
---|
| 49 |
|
---|
| 50 | string parameterPropertyName = typeValue.Name.EndsWith("Parameter") ? typeValue.Name : typeValue.Name + "Parameter";
|
---|
| 51 | var parameterProperty = model.GetType().GetProperty(parameterPropertyName);
|
---|
| 52 | if (parameterProperty != null) {
|
---|
| 53 | var parameterPropertyValue = parameterProperty.GetGetMethod().Invoke(model, null);
|
---|
| 54 | var vvProp = parameterPropertyValue.GetType().GetProperty("ValidValues");
|
---|
| 55 | if (vvProp != null) {
|
---|
| 56 | //http://stackoverflow.com/questions/245607/how-is-generic-covariance-contra-variance-implemented-in-c-sharp-4-0 because of covariance declared in IEnumerable
|
---|
| 57 | var options = vvProp.GetGetMethod().Invoke(parameterPropertyValue, null) as IEnumerable<IItem>;
|
---|
| 58 | if (options != null) {
|
---|
| 59 | var result = options.FirstOrDefault(x => x.ItemName == typeValue.Value);
|
---|
| 60 | if (result != null)
|
---|
| 61 | return result;
|
---|
| 62 | }
|
---|
| 63 | }
|
---|
| 64 | }
|
---|
| 65 |
|
---|
| 66 | Type type = null;
|
---|
| 67 | foreach (var asm in AppDomain.CurrentDomain.GetAssemblies()) {
|
---|
| 68 | type = asm.GetType(typeValue.Value);
|
---|
| 69 | if (type != null)
|
---|
| 70 | break;
|
---|
| 71 | }
|
---|
| 72 |
|
---|
| 73 | return Activator.CreateInstance(type);
|
---|
| 74 | }
|
---|
| 75 | return null;
|
---|
| 76 | }
|
---|
| 77 |
|
---|
| 78 | public object CreateHLObjectForType(object obj, Type type, Parameter prop) {
|
---|
| 79 | var value = MapControllerDataType(obj, prop);
|
---|
| 80 | if (prop.Type == ParameterType.Type)
|
---|
| 81 | return value;
|
---|
| 82 |
|
---|
| 83 | if (type == typeof(HeuristicLab.Encodings.PermutationEncoding.Permutation)) {
|
---|
| 84 | double[] input = value as double[];
|
---|
| 85 | int[] arr = new int[input.Length];
|
---|
| 86 | for (int i = 0; i < input.Length; i++) {
|
---|
| 87 | arr[i] = Convert.ToInt32(input[i]);
|
---|
| 88 | }
|
---|
| 89 | var valueObj = new HeuristicLab.Encodings.PermutationEncoding.Permutation(Encodings.PermutationEncoding.PermutationTypes.RelativeUndirected, arr);
|
---|
| 90 | return valueObj;
|
---|
| 91 | }
|
---|
| 92 | var propertyGetter = obj.GetType().GetProperty(prop.Value.Name).GetGetMethod();
|
---|
| 93 | return Activator.CreateInstance(propertyGetter.ReturnType, value);
|
---|
| 94 | }
|
---|
| 95 |
|
---|
| 96 | private void MapProperty(object model, Parameter prop) {
|
---|
| 97 | var propertyGetter = model.GetType().GetProperty(prop.Value.Name).GetGetMethod();
|
---|
| 98 | var propertySetter = model.GetType().GetProperty(prop.Value.Name).GetSetMethod();
|
---|
| 99 | var value = propertyGetter.Invoke(model, null);
|
---|
| 100 | var valueProperty = value != null ? value.GetType().GetProperty("Value") : null;
|
---|
| 101 | if (propertySetter != null) {
|
---|
| 102 | var instance = CreateHLObjectForType(model, propertyGetter.ReturnType, prop);
|
---|
| 103 | propertySetter.Invoke(model, new object[] { instance });
|
---|
| 104 | }
|
---|
| 105 | else if (valueProperty != null) {
|
---|
| 106 | valueProperty.GetSetMethod().Invoke(value, new object[] { MapControllerDataType(model, prop) });
|
---|
| 107 | }
|
---|
| 108 | else {
|
---|
| 109 | Console.WriteLine("Failed to handle property!");
|
---|
| 110 | }
|
---|
| 111 | }
|
---|
| 112 |
|
---|
[8545] | 113 | public void DispatchScenario(Model.User user, Model.OptimizationScenario scenario) {
|
---|
[8506] | 114 | Experiment experiment = new Experiment();
|
---|
| 115 | var problem = new TravelingSalesmanProblem();
|
---|
| 116 | foreach (var prop in scenario.InputParameters.Items) {
|
---|
| 117 | MapProperty(problem, prop);
|
---|
| 118 | }
|
---|
| 119 |
|
---|
| 120 | var algo = new GeneticAlgorithm();
|
---|
| 121 | algo.Problem = problem;
|
---|
| 122 | foreach (var prop in scenario.AlgorithmParameters.Items) {
|
---|
| 123 | MapProperty(algo, prop);
|
---|
| 124 | }
|
---|
| 125 |
|
---|
| 126 | experiment.Optimizers.Add(algo);
|
---|
[8545] | 127 | SendExperimentToHive(user, experiment);
|
---|
[8506] | 128 | }
|
---|
| 129 |
|
---|
[8545] | 130 | private void SendExperimentToHive(Model.User user, Experiment exp) {
|
---|
[8506] | 131 | var job = new RefreshableJob();
|
---|
| 132 | job.IsAllowedPrivileged = true;
|
---|
| 133 | job.Job.Name = "Web Scheduled Traveling Salesman Job";
|
---|
| 134 | job.Job.ResourceNames = "TESTGROUP";
|
---|
| 135 | job.RefreshAutomatically = false;
|
---|
| 136 | job.HiveTasks.Add(new OptimizerHiveTask(exp));
|
---|
[8545] | 137 | HiveServiceLocator.Instance.Username = user.Username;
|
---|
| 138 | HiveServiceLocator.Instance.Password = user.Password;
|
---|
[8506] | 139 | HiveServiceLocator.Instance.EndpointConfigurationName = "WSHttpBinding_IHiveService";
|
---|
| 140 |
|
---|
| 141 | HiveClient.StartJob((ex) => {
|
---|
| 142 | Console.WriteLine(ex.StackTrace);
|
---|
| 143 | }, job, new CancellationToken());
|
---|
| 144 |
|
---|
| 145 | job.StopResultPolling();
|
---|
| 146 | }
|
---|
[8545] | 147 |
|
---|
| 148 |
|
---|
| 149 | public IList<Model.Job> GetJobs(User user) {
|
---|
| 150 | HiveServiceLocator.Instance.Username = user.Username;
|
---|
| 151 | HiveServiceLocator.Instance.Password = user.Password;
|
---|
| 152 | HiveServiceLocator.Instance.EndpointConfigurationName = "WSHttpBinding_IHiveService";
|
---|
| 153 | var jobsLoaded = HiveServiceLocator.Instance.CallHiveService<IEnumerable<HeuristicLab.Clients.Hive.Job>>(s => s.GetJobs());
|
---|
| 154 | IList<Model.Job> jobs = new List<Model.Job>();
|
---|
| 155 |
|
---|
| 156 | foreach (var job in jobsLoaded) {
|
---|
| 157 | jobs.Add(ConvertJob(user, job));
|
---|
| 158 | }
|
---|
| 159 | return jobs;
|
---|
| 160 | }
|
---|
| 161 |
|
---|
| 162 | private Model.Job ConvertJob(User user, HeuristicLab.Clients.Hive.Job job)
|
---|
| 163 | {
|
---|
| 164 | var waitingJobs = job.JobCount - job.CalculatingCount - job.FinishedCount;
|
---|
| 165 | Model.JobState? state = null;
|
---|
| 166 | var jobTasks = HiveServiceLocator.Instance.CallHiveService<IEnumerable<HeuristicLab.Clients.Hive.LightweightTask>>(s => s.GetLightweightJobTasks(job.Id));
|
---|
| 167 |
|
---|
| 168 | foreach (var task in jobTasks) {
|
---|
| 169 | switch (task.State) {
|
---|
| 170 | case TaskState.Aborted:
|
---|
| 171 | state = JobState.Aborted;
|
---|
| 172 | break;
|
---|
| 173 | case TaskState.Failed:
|
---|
| 174 | state = JobState.Failed;
|
---|
| 175 | break;
|
---|
| 176 | }
|
---|
| 177 | }
|
---|
| 178 | if (!state.HasValue) {
|
---|
| 179 | if (job.CalculatingCount > 0)
|
---|
| 180 | state = JobState.Calculating;
|
---|
| 181 | else if (waitingJobs > 0)
|
---|
| 182 | state = JobState.Waiting;
|
---|
| 183 | else
|
---|
| 184 | state = JobState.Finished;
|
---|
| 185 | }
|
---|
| 186 | return new Model.Job() { Id = job.Id.ToString(), Name = job.Name, Resource = job.ResourceNames, State = state.Value };
|
---|
| 187 | }
|
---|
| 188 |
|
---|
| 189 |
|
---|
| 190 | public Model.Job GetJob(User user, string id) {
|
---|
| 191 | HiveServiceLocator.Instance.Username = user.Username;
|
---|
| 192 | HiveServiceLocator.Instance.Password = user.Password;
|
---|
| 193 | HiveServiceLocator.Instance.EndpointConfigurationName = "WSHttpBinding_IHiveService";
|
---|
| 194 | var guid = Guid.Parse(id);
|
---|
| 195 | return ConvertJob(user, HiveServiceLocator.Instance.CallHiveService<HeuristicLab.Clients.Hive.Job>(s => s.GetJob(guid)));
|
---|
| 196 | }
|
---|
| 197 |
|
---|
| 198 |
|
---|
| 199 | public void DeleteJob(User user, string id) {
|
---|
| 200 | HiveServiceLocator.Instance.Username = user.Username;
|
---|
| 201 | HiveServiceLocator.Instance.Password = user.Password;
|
---|
| 202 | HiveServiceLocator.Instance.EndpointConfigurationName = "WSHttpBinding_IHiveService";
|
---|
| 203 | var guid = Guid.Parse(id);
|
---|
| 204 | HiveServiceLocator.Instance.CallHiveService(s => s.DeleteJob(guid));
|
---|
| 205 | }
|
---|
| 206 |
|
---|
| 207 | public IList<Model.Run> GetJobResults(User user, string id) {
|
---|
| 208 | HiveServiceLocator.Instance.Username = user.Username;
|
---|
| 209 | HiveServiceLocator.Instance.Password = user.Password;
|
---|
| 210 | HiveServiceLocator.Instance.EndpointConfigurationName = "WSHttpBinding_IHiveService";
|
---|
| 211 | var guid = Guid.Parse(id);
|
---|
| 212 | var jobTasks = HiveServiceLocator.Instance.CallHiveService<IEnumerable<HeuristicLab.Clients.Hive.LightweightTask>>(s => s.GetLightweightJobTasks(guid));
|
---|
| 213 |
|
---|
| 214 | IList<Guid> taskIds = new List<Guid>();
|
---|
| 215 | foreach (var task in jobTasks) {
|
---|
| 216 | taskIds.Add(task.Id);
|
---|
| 217 | }
|
---|
| 218 | TaskDownloader downloader = new TaskDownloader(taskIds);
|
---|
| 219 | downloader.StartAsync();
|
---|
| 220 | while (!downloader.IsFinished) {
|
---|
| 221 | Thread.Sleep(500);
|
---|
| 222 |
|
---|
| 223 | if (downloader.IsFaulted) {
|
---|
| 224 | throw downloader.Exception;
|
---|
| 225 | }
|
---|
| 226 | }
|
---|
| 227 | IDictionary<Guid, HiveTask> hiveTasks = downloader.Results;
|
---|
| 228 | IList<Model.Run> runs = new List<Model.Run>();
|
---|
| 229 | foreach (var keyTask in hiveTasks.Keys) {
|
---|
| 230 | var oht = hiveTasks[keyTask] as OptimizerHiveTask;
|
---|
| 231 | if (oht != null) {
|
---|
| 232 | foreach (var run in oht.ItemTask.Item.Runs) {
|
---|
| 233 | Model.Run taskRun = new Model.Run();
|
---|
| 234 | taskRun.Id = taskRun.Name = run.Name;
|
---|
| 235 | IList<Parameter> resultValues = new List<Model.Parameter>();
|
---|
| 236 | foreach (var key in run.Results.Keys) {
|
---|
| 237 | var value = run.Results[key];
|
---|
| 238 | Parameter result = MapHiveDataType(key, value);
|
---|
| 239 | resultValues.Add(result);
|
---|
| 240 | }
|
---|
| 241 | taskRun.Results = resultValues;
|
---|
| 242 | runs.Add(taskRun);
|
---|
| 243 | }
|
---|
| 244 | }
|
---|
| 245 | }
|
---|
| 246 | return runs;
|
---|
| 247 | }
|
---|
| 248 | private Parameter MapHiveDataType(string name, IItem item) {
|
---|
| 249 | Parameter result = new Parameter();
|
---|
| 250 | result.Type = ParameterType.String;
|
---|
| 251 | if (item is IStringConvertibleValue) {
|
---|
| 252 | var value = (item as IStringConvertibleValue).GetValue();
|
---|
| 253 | result.Value = new HeuristicLab.Services.Optimization.ControllerService.Model.StringValue() { Name = name, Value = value };
|
---|
| 254 | }
|
---|
| 255 | else if (item is IStringConvertibleValueTuple) {
|
---|
| 256 | var value1 = (item as IStringConvertibleValueTuple).Item1.GetValue();
|
---|
| 257 | var value2 = (item as IStringConvertibleValueTuple).Item2.GetValue();
|
---|
| 258 | result.Value = new HeuristicLab.Services.Optimization.ControllerService.Model.StringValue() { Name = name, Value = "{" + value1 + ", " + value2 + "}" };
|
---|
| 259 | }
|
---|
| 260 | else if (item is IStringConvertibleArray) {
|
---|
| 261 | StringBuilder sb = new StringBuilder();
|
---|
| 262 | var array = item as IStringConvertibleArray;
|
---|
| 263 | if (array.Length == 0) {
|
---|
| 264 | sb.Append("[ ]");
|
---|
| 265 | } else {
|
---|
| 266 | sb.Append("[");
|
---|
| 267 | for (int i=0; i < array.Length - 1; i++) {
|
---|
| 268 | sb.Append(array.GetValue(i)).Append(", ");
|
---|
| 269 | }
|
---|
| 270 | sb.Append(array.GetValue(array.Length - 1));
|
---|
| 271 | sb.Append(" ]");
|
---|
| 272 | }
|
---|
| 273 | var value = sb.ToString();
|
---|
| 274 | result.Value = new HeuristicLab.Services.Optimization.ControllerService.Model.StringValue() { Name = name, Value = value };
|
---|
| 275 | }
|
---|
| 276 | else if (item is IStringConvertibleMatrix) {
|
---|
| 277 | StringBuilder sb = new StringBuilder();
|
---|
| 278 | var matrix = item as IStringConvertibleMatrix;
|
---|
| 279 | if (matrix.Rows == 0 || matrix.Columns == 0) {
|
---|
| 280 | sb.Append("[ ]");
|
---|
| 281 | }
|
---|
| 282 | else {
|
---|
| 283 | sb.Append("[ ");
|
---|
| 284 | for (int r = 0; r < matrix.Rows; r++) {
|
---|
| 285 | sb.Append("( ");
|
---|
| 286 | for (int c = 0; c < matrix.Columns - 1; c++) {
|
---|
| 287 | sb.Append(matrix.GetValue(r, c)).Append(", ");
|
---|
| 288 | }
|
---|
| 289 | sb.Append(matrix.GetValue(r, matrix.Columns - 1)).Append(r < matrix.Rows - 1 ? " ), " : " )");
|
---|
| 290 | }
|
---|
| 291 | sb.Append(" ]");
|
---|
| 292 | }
|
---|
| 293 | var value = sb.ToString();
|
---|
| 294 | result.Value = new HeuristicLab.Services.Optimization.ControllerService.Model.StringValue() { Name = name, Value = value };
|
---|
| 295 | }
|
---|
| 296 | else {
|
---|
| 297 | result.Value = new HeuristicLab.Services.Optimization.ControllerService.Model.StringValue() { Name = name, Value = "Cannot be displayed as string" };
|
---|
| 298 | }
|
---|
| 299 | return result;
|
---|
| 300 | }
|
---|
[8506] | 301 | }
|
---|
| 302 | }
|
---|