2017-11-19 06:19:49 +00:00
#tool nuget:?package=NUnit.ConsoleRunner
#addin nuget:?package=Cake.Git
2017-11-11 06:14:14 +00:00
//////////////////////////////////////////////////////////////////////
// ARGUMENTS
//////////////////////////////////////////////////////////////////////
var target = Argument("target", "Default");
2018-06-10 02:34:37 +00:00
var configuration = Argument("configuration", "Debug");
2017-11-11 06:14:14 +00:00
//////////////////////////////////////////////////////////////////////
// PREPARATION
//////////////////////////////////////////////////////////////////////
// Define directories.
var workingDir = MakeAbsolute(Directory("./"));
var artifactsDirName = "Artifacts";
var testResultsDirName = "TestResults";
var windowsBuildFullFramework = "./BuildOutput/FullFramework/Windows";
var monoBuildFullFramework = "./BuildOutput/FullFramework/Mono";
//////////////////////////////////////////////////////////////////////
// TASKS
//////////////////////////////////////////////////////////////////////
Task("Info")
.Does(() =>
{
Information(@"Jackett Cake build script starting...");
Information(@"Requires InnoSetup and C:\cygwin to be present for packaging (Pre-installed on AppVeyor)");
Information(@"Working directory is: " + workingDir);
});
Task("Clean")
.IsDependentOn("Info")
.Does(() =>
{
2018-06-10 02:34:37 +00:00
CleanDirectories("./src/**/obj");
CleanDirectories("./src/**/bin");
2017-11-11 06:14:14 +00:00
CleanDirectories("./BuildOutput");
CleanDirectories("./" + artifactsDirName);
CleanDirectories("./" + testResultsDirName);
2017-11-12 00:01:05 +00:00
Information("Clean completed");
2017-11-11 06:14:14 +00:00
});
Task("Restore-NuGet-Packages")
.IsDependentOn("Clean")
.Does(() =>
{
NuGetRestore("./src/Jackett.sln");
});
Task("Build")
2017-11-12 00:01:05 +00:00
.IsDependentOn("Restore-NuGet-Packages")
.Does(() =>
2017-11-11 06:14:14 +00:00
{
2018-06-24 01:32:22 +00:00
var buildSettings = new MSBuildSettings()
.SetConfiguration(configuration)
.UseToolVersion(MSBuildToolVersion.VS2017);
MSBuild("./src/Jackett.sln", buildSettings);
2017-11-11 06:14:14 +00:00
});
Task("Run-Unit-Tests")
2017-11-12 00:01:05 +00:00
.IsDependentOn("Build")
.Does(() =>
2017-11-11 06:14:14 +00:00
{
CreateDirectory("./" + testResultsDirName);
var resultsFile = $"./{testResultsDirName}/JackettTestResult.xml";
2017-11-12 00:01:05 +00:00
NUnit3("./src/**/bin/" + configuration + "/**/*.Test.dll", new NUnit3Settings
2017-11-11 06:14:14 +00:00
{
Results = new[] { new NUnit3Result { FileName = resultsFile } }
});
if(AppVeyor.IsRunningOnAppVeyor)
{
AppVeyor.UploadTestResults(resultsFile, AppVeyorTestResultsType.NUnit3);
}
});
Task("Copy-Files-Full-Framework")
2017-11-12 00:01:05 +00:00
.IsDependentOn("Run-Unit-Tests")
.Does(() =>
2017-11-11 06:14:14 +00:00
{
var windowsOutput = windowsBuildFullFramework + "/Jackett";
2017-11-12 00:01:05 +00:00
2017-11-11 06:14:14 +00:00
CopyDirectory("./src/Jackett.Console/bin/" + configuration, windowsOutput);
CopyFiles("./src/Jackett.Service/bin/" + configuration + "/JackettService.*", windowsOutput);
CopyFiles("./src/Jackett.Tray/bin/" + configuration + "/JackettTray.*", windowsOutput);
2018-06-24 01:32:22 +00:00
CopyFiles("./src/Jackett.Updater/bin/" + configuration + "/net452" + "/JackettUpdater.*", windowsOutput); //builds against multiple frameworks
2017-11-11 06:14:14 +00:00
CopyFiles("./Upstart.config", windowsOutput);
CopyFiles("./LICENSE", windowsOutput);
CopyFiles("./README.md", windowsOutput);
var monoOutput = monoBuildFullFramework + "/Jackett";
CopyDirectory(windowsBuildFullFramework, monoBuildFullFramework);
DeleteFiles(monoOutput + "/JackettService.*");
DeleteFiles(monoOutput + "/JackettTray.*");
2017-11-12 00:01:05 +00:00
Information("Full framework file copy completed");
2017-11-11 06:14:14 +00:00
});
Task("Check-Packaging-Platform")
2017-11-12 00:01:05 +00:00
.IsDependentOn("Copy-Files-Full-Framework")
.Does(() =>
2017-11-11 06:14:14 +00:00
{
if (IsRunningOnWindows())
{
CreateDirectory("./" + artifactsDirName);
2017-11-12 00:01:05 +00:00
Information("Platform is Windows");
2017-11-11 06:14:14 +00:00
}
2017-11-12 00:01:05 +00:00
else
2017-11-11 06:14:14 +00:00
{
throw new Exception("Packaging is currently only implemented for a Windows environment");
}
});
Task("Package-Windows-Installer-Full-Framework")
2017-11-12 00:01:05 +00:00
.IsDependentOn("Check-Packaging-Platform")
.Does(() =>
2017-11-11 06:14:14 +00:00
{
2018-06-24 01:32:22 +00:00
string sourceFolder = MakeAbsolute(Directory(windowsBuildFullFramework + "/Jackett")).ToString();
2018-06-23 01:38:32 +00:00
InnoSetupSettings settings = new InnoSetupSettings();
settings.OutputDirectory = workingDir + "/" + artifactsDirName;
settings.Defines = new Dictionary<string, string>
{
2018-06-24 01:32:22 +00:00
{ "MyFileForVersion", sourceFolder + "/Jackett.Common.dll" },
2018-06-23 01:38:32 +00:00
{ "MySourceFolder", sourceFolder },
{ "MyOutputFilename", "Jackett.Installer.Windows" },
};
InnoSetup("./Installer.iss", settings);
2017-11-11 06:14:14 +00:00
});
Task("Package-Files-Full-Framework-Windows")
2017-11-12 00:01:05 +00:00
.IsDependentOn("Check-Packaging-Platform")
.Does(() =>
2017-11-11 06:14:14 +00:00
{
Zip(windowsBuildFullFramework, $"./{artifactsDirName}/Jackett.Binaries.Windows.zip");
Information(@"Full Framework Windows Binaries Zipping Completed");
});
Task("Package-Files-Full-Framework-Mono")
2017-11-12 00:01:05 +00:00
.IsDependentOn("Check-Packaging-Platform")
.Does(() =>
2017-11-11 06:14:14 +00:00
{
2018-06-02 07:33:26 +00:00
Gzip(monoBuildFullFramework, $"./{artifactsDirName}", "Jackett", "Jackett.Binaries.Mono.tar.gz");
Information(@"Full Framework Mono Binaries Gzip Completed");
2017-11-11 06:14:14 +00:00
});
Task("Package-Full-Framework")
.IsDependentOn("Package-Windows-Installer-Full-Framework")
.IsDependentOn("Package-Files-Full-Framework-Windows")
.IsDependentOn("Package-Files-Full-Framework-Mono")
.Does(() =>
{
2018-06-24 01:32:22 +00:00
Information("Full Framework Packaging Completed");
2017-11-11 06:14:14 +00:00
});
2018-06-24 02:13:33 +00:00
Task("Kestrel-Full-Framework")
.IsDependentOn("Package-Full-Framework")
2018-06-02 07:33:26 +00:00
.Does(() =>
{
2018-06-24 02:13:33 +00:00
CleanDirectories("./src/**/obj");
CleanDirectories("./src/**/bin");
2018-06-02 07:33:26 +00:00
2018-06-24 02:13:33 +00:00
//Patch csproj to net461 until off Owin (net452 can't handle a nestandard library)
var trayCsproj = File("./src/Jackett.Tray/Jackett.Tray.csproj");
XmlPoke(trayCsproj, "*[name()='Project']/*[name()='PropertyGroup']/*[name()='TargetFrameworkVersion']", "v4.6.1");
var serviceCsproj = File("./src/Jackett.Service/Jackett.Service.csproj");
XmlPoke(serviceCsproj, "*[name()='Project']/*[name()='PropertyGroup']/*[name()='TargetFrameworkVersion']", "v4.6.1");
NuGetRestore("./src/Jackett.sln");
var buildSettings = new MSBuildSettings()
.SetConfiguration(configuration)
.UseToolVersion(MSBuildToolVersion.VS2017);
MSBuild("./src/Jackett.sln", buildSettings);
2018-06-14 09:18:17 +00:00
});
2018-06-02 07:33:26 +00:00
2018-06-14 09:18:17 +00:00
Task("Experimental-Kestrel-Windows-Full-Framework")
2018-06-24 02:13:33 +00:00
.IsDependentOn("Kestrel-Full-Framework")
2018-06-14 09:18:17 +00:00
.Does(() =>
{
2018-06-24 02:13:33 +00:00
string serverProjectPath = "./src/Jackett.Server/Jackett.Server.csproj";
string buildOutputPath = "./BuildOutput/Experimental/net461/win7-x86/Jackett";
2018-06-14 09:18:17 +00:00
2018-06-24 02:13:33 +00:00
DotNetCorePublish(serverProjectPath, "net461", "win7-x86");
CopyFiles("./src/Jackett.Service/bin/" + configuration + "/JackettService.*", buildOutputPath);
CopyFiles("./src/Jackett.Tray/bin/" + configuration + "/JackettTray.*", buildOutputPath);
CopyFiles("./src/Jackett.Updater/bin/" + configuration + "/net461" + "/JackettUpdater.*", buildOutputPath); //builds against multiple frameworks
Zip("./BuildOutput/Experimental/net461/win7-x86", $"./{artifactsDirName}/Experimental.Jackett.Binaries.Windows.zip");
//InnoSetup
string sourceFolder = MakeAbsolute(Directory(buildOutputPath)).ToString();
2018-06-02 07:33:26 +00:00
2018-06-24 02:13:33 +00:00
InnoSetupSettings settings = new InnoSetupSettings();
settings.OutputDirectory = workingDir + "/" + artifactsDirName;
settings.Defines = new Dictionary<string, string>
{
{ "MyFileForVersion", sourceFolder + "/Jackett.Common.dll" },
{ "MySourceFolder", sourceFolder },
{ "MyOutputFilename", "Experimental.Jackett.Installer.Windows" },
};
InnoSetup("./Installer.iss", settings);
2018-06-14 09:18:17 +00:00
});
2018-06-24 02:13:33 +00:00
Task("Experimental-Kestrel-Mono-Full-Framework")
.IsDependentOn("Kestrel-Full-Framework")
2018-06-14 09:18:17 +00:00
.Does(() =>
{
string serverProjectPath = "./src/Jackett.Server/Jackett.Server.csproj";
2018-06-24 02:13:33 +00:00
string buildOutputPath = "./BuildOutput/Experimental/net461/linux-x64/Jackett";
2018-06-14 09:18:17 +00:00
DotNetCorePublish(serverProjectPath, "net461", "linux-x64");
2018-06-24 02:13:33 +00:00
CopyFiles("./src/Jackett.Updater/bin/" + configuration + "/net461" + "/JackettUpdater.*", buildOutputPath); //builds against multiple frameworks
2018-06-14 09:18:17 +00:00
//There is an issue with Mono 5.8 (fixed in Mono 5.12) where its expecting to use its own patched version of System.Net.Http.dll, instead of the version supplied in folder
//https://github.com/dotnet/corefx/issues/19914
//https://bugzilla.xamarin.com/show_bug.cgi?id=60315
//The workaround is to delete System.Net.Http.dll and patch the .exe.config file
2018-06-24 02:13:33 +00:00
DeleteFile(buildOutputPath + "/System.Net.Http.dll");
2018-06-14 09:18:17 +00:00
2018-06-24 02:13:33 +00:00
var configFile = File(buildOutputPath + "/JackettConsole.exe.config");
2018-06-14 09:18:17 +00:00
XmlPoke(configFile, "configuration/runtime/*[name()='assemblyBinding']/*[name()='dependentAssembly']/*[name()='assemblyIdentity'][@name='System.Net.Http']/../*[name()='bindingRedirect']/@newVersion", "4.0.0.0");
Gzip("./BuildOutput/Experimental/net461/linux-x64", $"./{artifactsDirName}", "Jackett", "Experimental.Jackett.Binaries.Mono.tar.gz");
});
2018-06-24 02:13:33 +00:00
Task("Experimental-DotNetCore")
.IsDependentOn("Kestrel-Full-Framework")
.Does(() =>
{
string serverProjectPath = "./src/Jackett.Server/Jackett.Server.csproj";
DotNetCorePublish(serverProjectPath, "netcoreapp2.1", "win-x86");
DotNetCorePublish(serverProjectPath, "netcoreapp2.1", "linux-x64");
DotNetCorePublish(serverProjectPath, "netcoreapp2.1", "osx-x64");
Zip("./BuildOutput/Experimental/netcoreapp2.1/win-x86", $"./{artifactsDirName}/Experimental.netcoreapp.win-x86.zip");
Zip("./BuildOutput/Experimental/netcoreapp2.1/osx-x64", $"./{artifactsDirName}/Experimental.netcoreapp.osx-x64.zip");
Gzip("./BuildOutput/Experimental/netcoreapp2.1/linux-x64", $"./{artifactsDirName}", "Jackett", "Experimental.netcoreapp.linux-x64.tar.gz");
});
2018-06-14 09:18:17 +00:00
Task("Experimental")
.IsDependentOn("Experimental-Kestrel-Windows-Full-Framework")
2018-06-24 02:13:33 +00:00
.IsDependentOn("Experimental-Kestrel-Mono-Full-Framework")
2018-07-02 12:37:48 +00:00
//.IsDependentOn("Experimental-DotNetCore")
2018-06-14 09:18:17 +00:00
.Does(() =>
{
2018-06-24 02:13:33 +00:00
//Unpatch csproj because it's annoying in source control (remove once off Owin)
var trayCsproj = File("./src/Jackett.Tray/Jackett.Tray.csproj");
XmlPoke(trayCsproj, "*[name()='Project']/*[name()='PropertyGroup']/*[name()='TargetFrameworkVersion']", "v4.5.2");
var serviceCsproj = File("./src/Jackett.Service/Jackett.Service.csproj");
XmlPoke(serviceCsproj, "*[name()='Project']/*[name()='PropertyGroup']/*[name()='TargetFrameworkVersion']", "v4.5.2");
2018-06-14 09:18:17 +00:00
Information("Experimental builds completed");
2018-06-02 07:33:26 +00:00
});
2017-11-11 06:14:14 +00:00
Task("Appveyor-Push-Artifacts")
2017-11-12 00:01:05 +00:00
.IsDependentOn("Package-Full-Framework")
2018-06-10 02:34:37 +00:00
.IsDependentOn("Experimental")
2017-11-12 00:01:05 +00:00
.Does(() =>
2017-11-11 06:14:14 +00:00
{
if (AppVeyor.IsRunningOnAppVeyor)
2017-11-12 00:01:05 +00:00
{
foreach (var file in GetFiles(workingDir + $"/{artifactsDirName}/*"))
2017-11-11 06:14:14 +00:00
{
2017-11-12 00:01:05 +00:00
AppVeyor.UploadArtifact(file.FullPath);
2017-11-11 06:14:14 +00:00
}
2017-11-12 00:01:05 +00:00
}
2017-11-11 06:14:14 +00:00
else
{
Information(@"Skipping as not running in AppVeyor Environment");
}
});
2018-03-10 08:28:59 +00:00
Task("Release-Notes")
2017-11-19 06:19:49 +00:00
.IsDependentOn("Appveyor-Push-Artifacts")
.Does(() =>
{
2017-11-19 07:37:47 +00:00
string latestTag = GitDescribe(".", false, GitDescribeStrategy.Tags, 0);
Information($"Latest tag is: {latestTag}" + Environment.NewLine);
List<GitCommit> relevantCommits = new List<GitCommit>();
2017-11-19 06:19:49 +00:00
2017-11-19 07:37:47 +00:00
var commitCollection = GitLog("./", 50);
2017-11-19 06:19:49 +00:00
2017-11-19 07:37:47 +00:00
foreach(GitCommit commit in commitCollection)
{
var commitTag = GitDescribe(".", commit.Sha, false, GitDescribeStrategy.Tags, 0);
2017-11-19 06:19:49 +00:00
2017-11-19 07:37:47 +00:00
if (commitTag == latestTag)
2017-11-19 06:19:49 +00:00
{
relevantCommits.Add(commit);
}
2017-11-19 07:37:47 +00:00
else
2017-11-19 06:19:49 +00:00
{
2017-11-19 07:37:47 +00:00
break;
}
}
2017-11-19 06:19:49 +00:00
2017-11-19 07:37:47 +00:00
relevantCommits = relevantCommits.AsEnumerable().Reverse().Skip(1).ToList();
2017-11-19 06:19:49 +00:00
2017-11-19 07:37:47 +00:00
if (relevantCommits.Count() > 0)
{
List<string> notesList = new List<string>();
foreach(GitCommit commit in relevantCommits)
2017-11-19 06:19:49 +00:00
{
2017-11-19 07:37:47 +00:00
notesList.Add($"{commit.MessageShort} (Thank you @{commit.Author.Name})");
2017-11-19 06:19:49 +00:00
}
2017-11-19 07:37:47 +00:00
string buildNote = String.Join(Environment.NewLine, notesList);
Information(buildNote);
2018-03-10 08:28:59 +00:00
System.IO.File.WriteAllLines(workingDir + "\\BuildOutput\\ReleaseNotes.txt", notesList.ToArray());
2017-11-19 06:19:49 +00:00
}
2017-11-19 07:37:47 +00:00
else
{
Information($"No commit messages found to create release notes");
}
2017-11-19 06:19:49 +00:00
});
2017-11-11 06:14:14 +00:00
private void RunCygwinCommand(string utility, string utilityArguments)
{
var cygwinDir = @"C:\cygwin\bin\";
var utilityProcess = cygwinDir + utility + ".exe";
Information("CygWin Utility: " + utility);
Information("CygWin Directory: " + cygwinDir);
Information("Utility Location: " + utilityProcess);
Information("Utility Arguments: " + utilityArguments);
IEnumerable<string> redirectedStandardOutput;
IEnumerable<string> redirectedErrorOutput;
var exitCodeWithArgument =
StartProcess(
utilityProcess,
new ProcessSettings {
Arguments = utilityArguments,
WorkingDirectory = cygwinDir,
RedirectStandardOutput = true
},
out redirectedStandardOutput,
out redirectedErrorOutput
);
Information(utility + " output:" + Environment.NewLine + string.Join(Environment.NewLine, redirectedStandardOutput.ToArray()));
// Throw exception if anything was written to the standard error.
if (redirectedErrorOutput != null && redirectedErrorOutput.Any())
{
throw new Exception(
string.Format(
utility + " Errors ocurred: {0}",
string.Join(", ", redirectedErrorOutput)));
}
Information(utility + " Exit code: {0}", exitCodeWithArgument);
}
private string RelativeWinPathToCygPath(string relativePath)
{
var cygdriveBase = "/cygdrive/" + workingDir.ToString().Replace(":", "").Replace("\\", "/");
2018-06-02 07:33:26 +00:00
var cygPath = cygdriveBase + relativePath.TrimStart('.');
2017-11-11 06:14:14 +00:00
return cygPath;
}
2018-06-02 07:33:26 +00:00
private void Gzip(string sourceFolder, string outputDirectory, string tarCdirectoryOption, string outputFileName)
{
var cygSourcePath = RelativeWinPathToCygPath(sourceFolder);
var tarFileName = outputFileName.Remove(outputFileName.Length - 3, 3);
var tarArguments = @"-cvf " + cygSourcePath + "/" + tarFileName + " -C " + cygSourcePath + $" {tarCdirectoryOption} --mode ='755'";
var gzipArguments = @"-k " + cygSourcePath + "/" + tarFileName;
RunCygwinCommand("Tar", tarArguments);
RunCygwinCommand("Gzip", gzipArguments);
MoveFile($"{sourceFolder}/{tarFileName}.gz", $"{outputDirectory}/{tarFileName}.gz");
}
2018-06-10 02:34:37 +00:00
private void DotNetCorePublish(string projectPath, string framework, string runtime)
2018-06-02 07:33:26 +00:00
{
var settings = new DotNetCorePublishSettings
{
Framework = framework,
Runtime = runtime,
OutputDirectory = $"./BuildOutput/Experimental/{framework}/{runtime}/Jackett"
};
2018-06-10 02:34:37 +00:00
DotNetCorePublish(projectPath, settings);
2018-06-02 07:33:26 +00:00
}
2017-11-11 06:14:14 +00:00
//////////////////////////////////////////////////////////////////////
// TASK TARGETS
//////////////////////////////////////////////////////////////////////
Task("Default")
2018-03-10 08:28:59 +00:00
.IsDependentOn("Release-Notes")
2017-11-12 00:01:05 +00:00
.Does(() =>
{
Information("Default Task Completed");
});
2017-11-11 06:14:14 +00:00
//////////////////////////////////////////////////////////////////////
// EXECUTION
//////////////////////////////////////////////////////////////////////
RunTarget(target);