ln.build/ln.build/CIJob.cs

192 lines
6.2 KiB
C#
Raw Normal View History

2020-11-27 22:12:01 +01:00
using System;
using System.Collections.Generic;
using System.IO;
using ln.build.commands;
2020-12-03 00:05:51 +01:00
using ln.build.pipeline;
2020-11-29 22:02:16 +01:00
using ln.build.repositories;
using ln.build.secrets;
2020-12-09 10:05:52 +01:00
using ln.build.semver;
2020-11-27 22:12:01 +01:00
using ln.json;
using ln.logging;
using ln.threading;
namespace ln.build
{
2020-12-09 10:05:52 +01:00
public delegate void CIJobCompleted(CIJob cIJob);
2020-11-27 22:12:01 +01:00
public class CIJob : PoolJob
{
2020-12-09 10:05:52 +01:00
public event CIJobCompleted OnJobCompleted;
2020-11-27 22:12:01 +01:00
public string JobID { get; } = Guid.NewGuid().ToString("N");
public CIService CIService { get; }
public Repository Repository { get; set; }
public SecretStorage SecretStorage { get; set; }
public string WorkingDirectory { get; set; }
2020-11-27 22:12:01 +01:00
public Logger Logger { get; private set; }
public CommandEnvironment Environment { get; }
2020-11-29 22:02:16 +01:00
2020-12-03 00:05:51 +01:00
public DefaultPipeLine PipeLine { get; set; }
2020-11-29 22:02:16 +01:00
public BuildState BuildState { get; private set; }
2020-11-27 22:12:01 +01:00
Dictionary<string,MemoryStream> logStreams = new Dictionary<string, MemoryStream>();
Dictionary<string,Logger> logStreamLoggers = new Dictionary<string, Logger>();
public CIJob(CIService ciService, Repository repository, SecretStorage secretStorage)
:this(ciService, repository)
{
SecretStorage = secretStorage;
2020-12-03 22:58:35 +01:00
Environment.SecretStorage = secretStorage;
}
public CIJob(CIService ciService, Repository repository)
2020-11-27 22:12:01 +01:00
{
CIService = ciService;
Repository = repository;
2020-11-27 22:12:01 +01:00
WorkingDirectory = Path.Combine(Path.GetTempPath(), JobID);
2020-12-03 00:05:51 +01:00
Directory.CreateDirectory(Path.Combine(ciService.ReportsDirectory, JobID));
Logger = new Logger(new FileLogger(Path.Combine(ciService.ReportsDirectory, JobID, "build.log")));
2020-11-27 22:12:01 +01:00
Logger.Backends.Add(Logger.ConsoleLogger);
2020-12-09 17:15:46 +01:00
Environment = new CommandEnvironment(){ CIJob = this, WorkingDirectory = WorkingDirectory };
2020-11-27 22:12:01 +01:00
}
public Stream GetLogStream(string name)
{
if (!logStreams.TryGetValue(name,out MemoryStream logStream))
{
logStream = new MemoryStream();
logStreams.Add(name, logStream);
}
return logStream;
}
public Logger GetLogger(string name)
{
if (!logStreamLoggers.TryGetValue(name, out Logger logStreamLogger))
{
logStreamLogger = new Logger(GetLogStream(name));
logStreamLogger.Backends.Add(Logger.ConsoleLogger);
logStreamLoggers.Add(name, logStreamLogger);
}
return logStreamLogger;
}
2020-11-29 22:02:16 +01:00
public string GetLoggedContent(string name)
{
logStreams[name].Position = 0;
using StreamReader sr = new StreamReader(logStreams[name]);
return sr.ReadToEnd();
}
public IEnumerable<string> GetLogStreamNames() => logStreams.Keys;
public string GetVariable(string varName) => Environment.Get(varName);
public string GetVariable(string varName,string defValue) => Environment.Get(varName, defValue);
public bool ContainsVariable(string varName) => Environment.Contains(varName);
public CIJob SetVariable(string varName,string varValue){ Environment.Set(varName,varValue); return this; }
2020-11-27 22:12:01 +01:00
public void UpdateBuildState(BuildState buildState)
2020-11-27 22:12:01 +01:00
{
2020-11-29 22:02:16 +01:00
BuildState = buildState;
Repository?.UpdateBuildState(this);
2020-11-27 22:12:01 +01:00
}
public override void RunJob()
{
2020-11-28 01:08:49 +01:00
if (CloneRepository())
{
2020-12-03 00:05:51 +01:00
try
{
LoadPipeLine();
PipeLine.Run();
UpdateBuildState(BuildState.SUCCESS);
} catch (Exception e)
2020-11-27 22:12:01 +01:00
{
2020-12-03 00:05:51 +01:00
Logger.Log(e);
UpdateBuildState(BuildState.FAILURE);
2020-11-27 22:12:01 +01:00
}
2020-11-28 01:08:49 +01:00
} else {
Logger.Log(LogLevel.ERROR, "CIJob failed at CloneRepository()");
2020-11-27 22:12:01 +01:00
}
2020-11-28 01:08:49 +01:00
2020-12-09 10:05:52 +01:00
OnJobCompleted?.Invoke(this);
2020-11-27 22:12:01 +01:00
Notify();
Cleanup();
}
2020-11-28 01:08:49 +01:00
public bool CloneRepository()
2020-11-27 22:12:01 +01:00
{
Repository?.CloneSources(this);
2020-12-03 00:05:51 +01:00
return true;
2020-11-27 22:12:01 +01:00
}
2020-12-03 00:05:51 +01:00
public void LoadPipeLine()
2020-11-27 22:12:01 +01:00
{
2020-12-03 00:05:51 +01:00
JSONObject jsonPipeLine = JSONParser.ParseFile(Path.Combine(WorkingDirectory, "build.ln")) as JSONObject;
if (jsonPipeLine != null)
2020-11-28 01:08:49 +01:00
{
2020-12-03 00:05:51 +01:00
DefaultPipeLine pipeLine = new DefaultPipeLine(CIService, Environment);
pipeLine.LoadJson(jsonPipeLine);
PipeLine = pipeLine;
2020-11-28 01:08:49 +01:00
}
2020-11-27 22:12:01 +01:00
}
public void Notify()
{
2020-11-29 22:02:16 +01:00
// foreach (string key in logStreams.Keys)
// {
// logStreams[key].Position = 0;
// string logContent;
// using (StreamReader sr = new StreamReader(logStreams[key]))
// logContent = sr.ReadToEnd();
// Logger.Log(LogLevel.INFO, "------------------- LogStream {0} ---------------------------\n{1}", key, logContent);
// }
2020-11-27 22:12:01 +01:00
}
public void Cleanup()
{
CIService.CreateReport(this);
2020-12-03 00:05:51 +01:00
if (Repository != null)
2020-12-03 00:05:51 +01:00
Directory.Delete(WorkingDirectory, true);
2020-11-27 22:12:01 +01:00
}
2020-12-09 10:05:52 +01:00
public void PublishRelease(SemVerLevels releaseLevel)
{
if (BuildState == BuildState.SUCCESS)
{
if (PipeLine.Versioning != null)
{
Versioning versioning = PipeLine.Versioning;
SemVersion version = versioning.GetCurrentVersion(this);
if (version.IsPreRelease)
{
SemVersion releaseVersion = new SemVersion(version);
releaseVersion.PreRelease = null;
versioning.SetVersion(this, releaseVersion);
} else if (version.IsRelease)
{
}
}
}
}
2020-11-27 22:12:01 +01:00
}
}