/// <summary> /// Carga los datos de un paso /// </summary> private JobStepModel LoadStep(MLNode rootML, JobProjectModel project, JobStepModel parent) { JobStepModel step = new JobStepModel(project, parent); // Asigna las propiedades básicas step.Name = rootML.Nodes[TagName].Value.TrimIgnoreNull(); step.Description = rootML.Nodes[TagDescription].Value.TrimIgnoreNull(); step.ScriptFileName = rootML.Attributes[TagScript].Value.TrimIgnoreNull(); step.Target = rootML.Attributes[TagTarget].Value.TrimIgnoreNull(); step.ProcessorKey = rootML.Attributes[TagProcessor].Value.TrimIgnoreNull(); step.StartWithPreviousError = rootML.Attributes[TagStartWithPreviousError].Value.GetBool(false); step.Enabled = rootML.Attributes[TagEnabled].Value.GetBool(true); step.Parallel = rootML.Attributes[TagParallel].Value.GetBool(false); // Carga los pasos step.Steps.AddRange(LoadSteps(rootML, project, step)); // Carga el contexto foreach (MLNode nodeML in rootML.Nodes) { if (nodeML.Name == JobContextRepository.TagContext) { step.Context = new JobContextRepository().LoadContext(rootML, nodeML.Attributes[TagProcessor].Value.TrimIgnoreNull()); } } // Carga los parámetros step.Context.Parameters.AddRange(new JobParameterRepository().LoadParameters(rootML)); // Devuelve los datos del paso return(step); }
internal DbScriptManager(JobStepModel step, DbAggregatorManager dataProviderManager, NormalizedDictionary <object> parameters, LogManager logger) { Step = step; DataProviderManager = dataProviderManager; Parameters = parameters; Logger = logger; }
/// <summary> /// Obtiene las conexiones asociadas a un trabajo: primero las de los pasos padre porque las de los hijos son más restrictivas /// </summary> private NormalizedDictionary <Models.CloudConnection> GetConnections(JobStepModel job) { NormalizedDictionary <Models.CloudConnection> connections = new NormalizedDictionary <Models.CloudConnection>(); // Añade las conexiones de los pasos padre if (job.Parent != null) { connections.AddRange(GetConnections(job.Parent)); } // Añade las conexiones del paso connections.AddRange(GetConnections(job.Context)); // Devuelve la colección de conexiones return(connections); }
/// <summary> /// Obtiene los parámetros de un paso: primero obtiene los parámetros de sus ancestros porque se supone que cuánto más /// abajo, más específico /// </summary> private NormalizedDictionary <object> GetParameters(JobStepModel step) { NormalizedDictionary <object> parameters = new NormalizedDictionary <object>(); // Obtiene la colección de parámetros del padre if (step.Parent != null) { parameters.AddRange(GetParameters(step.Parent)); } // y le añade los parámetros de este paso parameters.AddRange(GetParameters(step.Context.Parameters)); // Devuelve la colección de parámetros return(parameters); }
/// <summary> /// Obtiene los contextos que se asocian al trabajo /// </summary> private List <JobContextModel> GetContexts(JobProjectModel project, JobStepModel job) { List <JobContextModel> contexts = new List <JobContextModel>(); // Obtiene los contextos asociados foreach (JobContextModel context in project.Contexts) { if (context.ProcessorKey.Equals(JobProjectModel.GlobalContext, StringComparison.CurrentCultureIgnoreCase) || context.ProcessorKey.Equals(job.ProcessorKey, StringComparison.CurrentCultureIgnoreCase)) { contexts.Add(context); } } // Devuelve la colección de contextos return(contexts); }
/// <summary> /// Procesa un trabajo /// </summary> public async Task <bool> ProcessAsync(List <JobContextModel> contexts, JobStepModel step, CancellationToken cancellationToken) { NormalizedDictionary <object> parameters = GetParameters(contexts, step); bool processed = false; // Procesa el paso try { processed = await ProcessStepAsync(contexts, step, parameters, cancellationToken); } catch (Exception exception) { Errors.Add($"Error when execute step '{step.Name}'. {exception}"); } // Devuelve el valor que indica si se ha procesado correctamente return(processed); }
public void SetUp() { jobMessageStatus = new RecordJobMessageProcessingStatus { JobId = 1, MessageName = "Message1", Id = Guid.NewGuid(), Succeeded = true, EndTime = DateTimeOffset.UtcNow, GeneratedMessages = new List <GeneratedMessage>() }; jobStep = new JobStepModel { JobId = 21, StartTime = DateTimeOffset.UtcNow.AddSeconds(-10), MessageName = "Message1", MessageId = jobMessageStatus.Id, Id = 2, Status = JobStepStatus.Queued, }; mocker = AutoMock.GetLoose(); var mockDataContext = mocker.Mock <IJobsDataContext>(); mockDataContext.Setup(x => x.GetJobIdFromDcJobId(It.IsAny <long>())) .Returns(Task.FromResult <long>(99)); mockDataContext.Setup(x => x.GetJobByDcJobId(It.IsAny <long>())) .Returns(Task.FromResult <JobModel>(new JobModel { Id = jobStep.JobId, DcJobId = jobMessageStatus.JobId })); jobSteps = new List <JobStepModel> { jobStep }; mockDataContext .Setup(dc => dc.GetJobSteps(It.IsAny <List <Guid> >())) .Returns(Task.FromResult <List <JobStepModel> >(jobSteps)); mockDataContext.Setup(dc => dc.GetJobIdFromDcJobId(It.IsAny <long>())) .Returns(Task.FromResult <long>(1)); object job = new JobModel { Id = jobStep.JobId, DcJobId = jobMessageStatus.JobId }; mocker.Mock <IMemoryCache>() .Setup(cache => cache.TryGetValue(It.IsAny <string>(), out job)) .Returns(true); }
/// <summary> /// Ejecuta un <see cref="JobModel"/> /// </summary> private async Task ExecuteJobAsync(JobProjectModel project, JobStepModel job, CancellationToken cancellationToken) { using (BlockLogModel block = Logger.Default.CreateBlock(LogModel.LogType.Debug, $"Start execute '{job.Name}'")) { IJobProcesor processor = GetProcessor(job); // Comprueba los datos antes de continuar if (processor == null) { block.Error($"Can't execute '{job.Name}' because can't find a procssor for '{job.ProcessorKey}'"); } else { try { List <JobContextModel> contexts = GetContexts(project, job); // Cambia el nombre de archivo job.ScriptFileName = project.GetFullFileName(job.ScriptFileName, contexts); // Procesa el archivo if (string.IsNullOrWhiteSpace(job.ScriptFileName) || !System.IO.File.Exists(job.ScriptFileName)) { block.Error($"Cant find the file '{job.ScriptFileName}'"); Errors.Add($"Cant find the file '{job.ScriptFileName}'"); } else { bool processed = await processor.ProcessAsync(contexts, job, cancellationToken); // Añade los errores de procesamiento if (!processed) { block.Error($"Error when execute '{job.Name}'{Environment.NewLine}{GetError(processor.Errors)}"); Errors.Add($"Error when execute '{job.Name}'"); Errors.AddRange(processor.Errors); } } } catch (Exception exception) { block.Error($"Error when execute '{job.Name}'", exception); } } } }
/// <summary> /// Obtiene el nodo de un <see cref="JobStepModel"/> /// </summary> private MLNode GetStepNode(JobStepModel step) { MLNode rootML = new MLNode(TagStep); // Añade los datos básicos rootML.Nodes.Add(TagName, step.Name); rootML.Nodes.Add(TagDescription, step.Description); rootML.Attributes.Add(TagScript, step.ScriptFileName); rootML.Attributes.Add(TagTarget, step.Target); rootML.Attributes.Add(TagProcessor, step.ProcessorKey); rootML.Attributes.Add(TagStartWithPreviousError, step.StartWithPreviousError); rootML.Attributes.Add(TagEnabled, step.Enabled); rootML.Attributes.Add(TagParallel, step.Parallel); // Añade los nodos de los pasos hijo rootML.Nodes.AddRange(GetStepNodes(step.Steps)); // Añade los nodos del contexto rootML.Nodes.Add(new JobContextRepository().GetContextNode(JobContextRepository.TagContext, string.Empty, step.Context)); // Añade los parámetros rootML.Nodes.AddRange(new JobParameterRepository().GetParametersNodes(step.Context.Parameters)); // Devuelve el nodo return(rootML); }
public void SetUp() { jobMessageStatus = new RecordJobMessageProcessingStatus { JobId = 1, MessageName = "Message1", Id = Guid.NewGuid(), Succeeded = true, EndTime = DateTimeOffset.UtcNow, GeneratedMessages = new List <GeneratedMessage>() }; jobStep = new JobStepModel { JobId = 21, StartTime = DateTimeOffset.UtcNow.AddSeconds(-10), MessageName = "Message1", MessageId = jobMessageStatus.Id, Id = 2, Status = JobStepStatus.Queued, }; jobSteps = new List <JobStepModel>(); mocker = AutoMock.GetLoose(); mocker.Mock <IJobStorageService>() .Setup(x => x.StoreNewJob(It.IsAny <JobModel>(), It.IsAny <CancellationToken>())) .Returns(Task.FromResult(true)); object job = new JobModel { Id = jobStep.JobId, DcJobId = jobMessageStatus.JobId }; mocker.Mock <IMemoryCache>() .Setup(cache => cache.TryGetValue(It.IsAny <string>(), out job)) .Returns(true); mocker.Mock <IJobStorageService>() .Setup(x => x.GetInProgressMessages(It.IsAny <long>(), It.IsAny <CancellationToken>())) .ReturnsAsync(new List <InProgressMessage>()); }
/// <summary> /// Carga una serie de pasos /// </summary> private List <JobStepModel> LoadSteps(MLNode rootML, JobProjectModel project, JobStepModel parent) { List <JobStepModel> steps = new List <JobStepModel>(); // Carga los pasos foreach (MLNode nodeML in rootML.Nodes) { if (nodeML.Name == TagStep) { steps.Add(LoadStep(nodeML, project, parent)); } } // Devuelve la colección de pasos return(steps); }
/// <summary> /// Ejecuta un paso /// </summary> protected override async Task <bool> ProcessStepAsync(List <JobContextModel> contexts, JobStepModel step, NormalizedDictionary <object> parameters, CancellationToken cancellationToken) { bool processed = false; // Procesa el paso using (BlockLogModel block = Logger.Default.CreateBlock(LogModel.LogType.Debug, $"Start execute step {step.Name}")) { if (string.IsNullOrEmpty(step.ScriptFileName) || !System.IO.File.Exists(step.ScriptFileName)) { block.Error($"Cant find the file {step.ScriptFileName}"); } else { List <Models.Sentences.BaseSentence> program = new Repository.JobRestRepository().Load(step.ScriptFileName); // Ejecuta el paso processed = await new Manager.ScriptInterpreter(this, step).ProcessAsync(block, program, parameters, cancellationToken); } } // Devuelve el valor que indica si se ha procesado correctamente return(processed); }
/// <summary> /// Ejecuta un paso /// </summary> protected override async Task <bool> ProcessStepAsync(List <JobContextModel> contexts, JobStepModel step, NormalizedDictionary <object> parameters, CancellationToken cancellationToken) { bool processed = false; DbAggregatorManager dataProviderManager = GetProviderManager(contexts, step); // Procesa el paso using (BlockLogModel block = Logger.Default.CreateBlock(LogModel.LogType.Debug, $"Start execute step {step.Name}")) { if (string.IsNullOrEmpty(step.ScriptFileName) || !System.IO.File.Exists(step.ScriptFileName)) { block.Error($"Cant find the file {step.ScriptFileName}"); } else { DbScriptManager scriptManager = new DbScriptManager(step, dataProviderManager, parameters, Logger); // Ejecuta el paso if (System.IO.Path.GetExtension(step.ScriptFileName).EqualsIgnoreCase(".sql")) { processed = await scriptManager.ProcessBySqlScriptAsync(step.Target, step.ScriptFileName, cancellationToken); } else { processed = await scriptManager.ProcessByFileAsync(step.ScriptFileName, cancellationToken); } } } // Devuelve el valor que indica si se ha procesado correctamente return(processed); }
/// <summary> /// Obtiene las conexiones del contexto y del trabajo /// </summary> private NormalizedDictionary <Models.CloudConnection> GetConnections(List <JobContextModel> contexts, JobStepModel job) { NormalizedDictionary <Models.CloudConnection> connections = new NormalizedDictionary <Models.CloudConnection>(); // Obtiene los proveedores de los contextos globales foreach (JobContextModel context in contexts) { if (!string.IsNullOrWhiteSpace(context.ProcessorKey) && context.ProcessorKey.Equals(Key, StringComparison.CurrentCultureIgnoreCase)) { connections.AddRange(GetConnections(context)); } } // Obtiene los proveedores del contexto del trabajo connections.AddRange(GetConnections(job)); // Devuelve las conexiones return(connections); }
internal ScriptInterpreter(JobCloudManager manager, JobStepModel step, NormalizedDictionary <CloudConnection> connections) { Manager = manager; Step = step; Connections = connections; }
/// <summary> /// Obtiene e inicializa el controlador de proveedores de datos /// </summary> private DbAggregatorManager GetProviderManager(List <JobContextModel> contexts, JobStepModel job) { DbAggregatorManager providersManager = new DbAggregatorManager(); NormalizedDictionary <DataBaseConnectionModel> connections = GetConnections(contexts, job); // Asign las conexiones al proveedor foreach ((string key, DataBaseConnectionModel connection) in connections.Enumerate()) { DbAggregator.Models.ConnectionModel dbConnection = new DbAggregator.Models.ConnectionModel(key, connection.Type.ToString()); // Añade los parámetros dbConnection.Parameters.AddRange(connection.Parameters); // Añade la conexión providersManager.AddConnection(dbConnection); } // Devuelve el agregado return(providersManager); }
/// <summary> /// Ejecuta un paso /// </summary> protected abstract Task <bool> ProcessStepAsync(List <JobContextModel> contexts, JobStepModel step, NormalizedDictionary <object> parameters, CancellationToken cancellationToken);
/// <summary> /// Obtiene los parámetros del paso /// </summary> private NormalizedDictionary <object> GetParameters(List <JobContextModel> contexts, JobStepModel step) { NormalizedDictionary <object> parameters = new NormalizedDictionary <object>(); // Añade los parámetros de los contextos foreach (JobContextModel context in contexts) { parameters.AddRange(GetParameters(context.Parameters)); } // Añade al diccionario los parámetros del script (desde el padre hacia abajo: los más internos son los que prevalecen // porque son más específicos que los externos) parameters.AddRange(GetParameters(step)); // Devuelve el diccionario de parámetros return(parameters); }
internal ScriptInterpreter(JobPowershellManager manager, JobStepModel step) { Manager = manager; Step = step; }
/// <summary> /// Obtiene el procesador asociado a un trabajo /// </summary> private IJobProcesor GetProcessor(JobStepModel job) { return(Processors[job.ProcessorKey]); }
internal PowerShellController(ScriptInterpreter interpreter, JobStepModel step) { Interpreter = interpreter; Step = step; }
internal ScriptInterpreter(JobRestManager manager, JobStepModel step) { Manager = manager; Step = step; }