Implement the wasm build task
This commit is contained in:
parent
82a154b1e2
commit
d4308a740d
|
@ -11,6 +11,7 @@
|
||||||
/Ooui.Wasm/sample*
|
/Ooui.Wasm/sample*
|
||||||
/Ooui.Wasm/lib*
|
/Ooui.Wasm/lib*
|
||||||
/Ooui.Wasm/*.w*
|
/Ooui.Wasm/*.w*
|
||||||
|
/Ooui.Wasm.Test
|
||||||
|
|
||||||
# Social media files
|
# Social media files
|
||||||
/Media
|
/Media
|
||||||
|
|
|
@ -1,30 +1,213 @@
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Diagnostics;
|
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Xml;
|
using System.IO.Compression;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Net;
|
||||||
|
|
||||||
using Microsoft.Build.Framework;
|
using Microsoft.Build.Framework;
|
||||||
using Microsoft.Build.Utilities;
|
using Microsoft.Build.Utilities;
|
||||||
|
using System.Text;
|
||||||
|
using Mono.Cecil;
|
||||||
|
|
||||||
namespace Ooui.Wasm.Build.Tasks
|
namespace Ooui.Wasm.Build.Tasks
|
||||||
{
|
{
|
||||||
public class BuildDistTask : MarshalByRefObject, ITask
|
public class BuildDistTask : Task
|
||||||
{
|
{
|
||||||
|
const string SdkUrl = "https://jenkins.mono-project.com/job/test-mono-mainline-webassembly/62/label=highsierra/Azure/processDownloadRequest/62/highsierra/sdks/wasm/mono-wasm-ddf4e7be31b.zip";
|
||||||
|
|
||||||
[Required]
|
[Required]
|
||||||
public string Assembly { get; set; }
|
public string Assembly { get; set; }
|
||||||
public string ReferencePath { get; set; }
|
public string ReferencePath { get; set; }
|
||||||
|
|
||||||
public bool Execute ()
|
public override bool Execute ()
|
||||||
{
|
{
|
||||||
var fullAsmPath = Path.GetFullPath (Assembly);
|
try {
|
||||||
Console.WriteLine ("YO " + fullAsmPath);
|
InstallSdk ();
|
||||||
|
GetBcl ();
|
||||||
|
CreateDist ();
|
||||||
|
CopyRuntime ();
|
||||||
|
LinkAssemblies ();
|
||||||
|
ExtractClientJs ();
|
||||||
|
GenerateHtml ();
|
||||||
|
GenerateServer ();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
catch (Exception ex) {
|
||||||
public IBuildEngine BuildEngine { get; set; }
|
Log.LogErrorFromException (ex);
|
||||||
public ITaskHost HostObject { get; set; }
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
string sdkPath;
|
||||||
|
|
||||||
|
void InstallSdk ()
|
||||||
|
{
|
||||||
|
var sdkName = Path.GetFileNameWithoutExtension (new Uri (SdkUrl).AbsolutePath.Replace ('/', Path.DirectorySeparatorChar));
|
||||||
|
Log.LogMessage ("SDK: " + sdkName);
|
||||||
|
sdkPath = Path.Combine (Path.GetTempPath (), sdkName);
|
||||||
|
Log.LogMessage ("SDK Path: " + sdkPath);
|
||||||
|
if (Directory.Exists (sdkPath))
|
||||||
|
return;
|
||||||
|
|
||||||
|
var client = new WebClient ();
|
||||||
|
var zipPath = sdkPath + ".zip";
|
||||||
|
Log.LogMessage ($"Downloading {sdkName} to {zipPath}");
|
||||||
|
client.DownloadFile (SdkUrl, zipPath);
|
||||||
|
|
||||||
|
ZipFile.ExtractToDirectory (zipPath, sdkPath);
|
||||||
|
Log.LogMessage ($"Extracted {sdkName} to {sdkPath}");
|
||||||
|
}
|
||||||
|
|
||||||
|
string bclPath;
|
||||||
|
Dictionary<string, string> bclAssemblies;
|
||||||
|
|
||||||
|
void GetBcl ()
|
||||||
|
{
|
||||||
|
bclPath = Path.Combine (sdkPath, "bcl");
|
||||||
|
var reals = Directory.GetFiles (bclPath, "*.dll");
|
||||||
|
var facades = Directory.GetFiles (Path.Combine (bclPath, "Facades"), "*.dll");
|
||||||
|
var allFiles = reals.Concat (facades);
|
||||||
|
bclAssemblies = allFiles.ToDictionary (x => Path.GetFileName (x));
|
||||||
|
}
|
||||||
|
|
||||||
|
string distPath;
|
||||||
|
string managedPath;
|
||||||
|
|
||||||
|
void CreateDist ()
|
||||||
|
{
|
||||||
|
var fullAsmPath = Path.GetFullPath (Assembly);
|
||||||
|
var outputPath = Path.GetDirectoryName (fullAsmPath);
|
||||||
|
distPath = Path.Combine (outputPath, "dist");
|
||||||
|
managedPath = Path.Combine (distPath, "managed");
|
||||||
|
Directory.CreateDirectory (managedPath);
|
||||||
|
//foreach (var dll in Directory.GetFiles (managedPath, "*.dll")) {
|
||||||
|
// File.Delete (dll);
|
||||||
|
//}
|
||||||
|
}
|
||||||
|
|
||||||
|
void CopyRuntime ()
|
||||||
|
{
|
||||||
|
var rtPath = Path.Combine (sdkPath, "release");
|
||||||
|
var files = new[] { "mono.wasm", "mono.js" };
|
||||||
|
foreach (var f in files) {
|
||||||
|
var src = Path.Combine (rtPath, f);
|
||||||
|
var dest = Path.Combine (distPath, f);
|
||||||
|
Log.LogMessage ($"Runtime {src} -> {dest}");
|
||||||
|
File.Copy (src, dest, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
List<string> linkedAsmNames;
|
||||||
|
List<string> linkedAsmPaths;
|
||||||
|
|
||||||
|
void LinkAssemblies ()
|
||||||
|
{
|
||||||
|
var references = ReferencePath.Split (';').Select (x => x.Trim ()).Where (x => x.Length > 0).ToList ();
|
||||||
|
references.Add (Path.GetFullPath (Assembly));
|
||||||
|
|
||||||
|
linkedAsmPaths = new List<string> ();
|
||||||
|
foreach (var r in references) {
|
||||||
|
var name = Path.GetFileName (r);
|
||||||
|
if (bclAssemblies.ContainsKey (name)) {
|
||||||
|
linkedAsmPaths.Add (bclAssemblies[name]);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
linkedAsmPaths.Add (r);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
linkedAsmNames = new List<string> ();
|
||||||
|
foreach (var l in linkedAsmPaths) {
|
||||||
|
var name = Path.GetFileName (l);
|
||||||
|
linkedAsmNames.Add (name);
|
||||||
|
var dest = Path.Combine (managedPath, name);
|
||||||
|
if (bclAssemblies.ContainsKey (name) && File.Exists (dest))
|
||||||
|
continue;
|
||||||
|
File.Copy (l, dest, true);
|
||||||
|
Log.LogMessage ($"Managed {l} -> {dest}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void ExtractClientJs ()
|
||||||
|
{
|
||||||
|
var oouiPath = linkedAsmPaths.FirstOrDefault (x => Path.GetFileName (x).Equals ("Ooui.dll", StringComparison.InvariantCultureIgnoreCase));
|
||||||
|
if (oouiPath == null) {
|
||||||
|
Log.LogError ("Ooui.dll not included in the project");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var oouiAsm = AssemblyDefinition.ReadAssembly (oouiPath);
|
||||||
|
var clientJs = oouiAsm.MainModule.Resources.FirstOrDefault (x => x.Name.EndsWith ("Client.js", StringComparison.InvariantCultureIgnoreCase)) as EmbeddedResource;
|
||||||
|
if (clientJs == null) {
|
||||||
|
Log.LogError ("Ooui.dll missing client javascript");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var dest = Path.Combine (distPath, "ooui.js");
|
||||||
|
using (var srcs = clientJs.GetResourceStream ()) {
|
||||||
|
using (var dests = new FileStream (dest, FileMode.Create, FileAccess.Write)) {
|
||||||
|
srcs.CopyTo (dests);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Log.LogMessage ($"Client JS {dest}");
|
||||||
|
}
|
||||||
|
|
||||||
|
void GenerateHtml ()
|
||||||
|
{
|
||||||
|
var htmlPath = Path.Combine (distPath, "index.html");
|
||||||
|
using (var w = new StreamWriter (htmlPath, false, new UTF8Encoding (false))) {
|
||||||
|
w.Write (@"<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<title>Ooui Wasm</title>
|
||||||
|
<meta name=""viewport"" content=""width=device-width, initial-scale=1"" />
|
||||||
|
<link rel=""stylesheet"" href=""https://ajax.aspnetcdn.com/ajax/bootstrap/3.3.7/css/bootstrap.min.css"" />
|
||||||
|
<link rel=""stylesheet"" href=""https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css"">
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div id=""ooui-body"" class=""container-fluid"">
|
||||||
|
<p id=""loading""><i class=""fa fa-refresh fa-spin"" style=""font-size:14px;margin-right:0.5em;""></i> Loading...</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<script type=""text/javascript"" src=""ooui.js""></script>
|
||||||
|
<script type=""text/javascript"">
|
||||||
|
var mainAsmName = """);
|
||||||
|
w.Write (Path.GetFileNameWithoutExtension (Assembly));
|
||||||
|
w.Write (@""";
|
||||||
|
var assemblies = [");
|
||||||
|
var head = "";
|
||||||
|
foreach (var l in linkedAsmNames) {
|
||||||
|
w.Write (head);
|
||||||
|
w.Write ('\"');
|
||||||
|
w.Write (l);
|
||||||
|
w.Write ('\"');
|
||||||
|
head = ",";
|
||||||
|
}
|
||||||
|
w.WriteLine (@"];
|
||||||
|
oouiWasm (mainAsmName, """", ""Program"", ""Main"", assemblies);
|
||||||
|
</script>
|
||||||
|
<script async type=""text/javascript"" src=""mono.js""></script>
|
||||||
|
</body>
|
||||||
|
</html>");
|
||||||
|
}
|
||||||
|
Log.LogMessage ($"HTML {htmlPath}");
|
||||||
|
}
|
||||||
|
|
||||||
|
void GenerateServer ()
|
||||||
|
{
|
||||||
|
var server = @"import SimpleHTTPServer
|
||||||
|
import SocketServer
|
||||||
|
PORT = 8000
|
||||||
|
class Handler(SimpleHTTPServer.SimpleHTTPRequestHandler):
|
||||||
|
pass
|
||||||
|
Handler.extensions_map["".wasm""] = ""application/wasm""
|
||||||
|
httpd = SocketServer.TCPServer(("""", PORT), Handler)
|
||||||
|
print ""serving at port"", PORT
|
||||||
|
httpd.serve_forever()";
|
||||||
|
var serverPath = Path.Combine (distPath, "server.py");
|
||||||
|
using (var w = new StreamWriter (serverPath, false, new UTF8Encoding (false))) {
|
||||||
|
w.WriteLine (server);
|
||||||
|
}
|
||||||
|
Log.LogMessage ($"Server {serverPath}");
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
26
Ooui.sln
26
Ooui.sln
|
@ -2,22 +2,24 @@ Microsoft Visual Studio Solution File, Format Version 12.00
|
||||||
# Visual Studio 15
|
# Visual Studio 15
|
||||||
VisualStudioVersion = 15.0.27130.2010
|
VisualStudioVersion = 15.0.27130.2010
|
||||||
MinimumVisualStudioVersion = 15.0.26124.0
|
MinimumVisualStudioVersion = 15.0.26124.0
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ooui", "Ooui\Ooui.csproj", "{DFDFD036-BF48-4D3A-BF99-88CA1EA8E4B9}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Ooui", "Ooui\Ooui.csproj", "{DFDFD036-BF48-4D3A-BF99-88CA1EA8E4B9}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Samples", "Samples\Samples.csproj", "{CDF8BB01-40BB-402F-8446-47AA6F1628F3}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Samples", "Samples\Samples.csproj", "{CDF8BB01-40BB-402F-8446-47AA6F1628F3}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Tests", "Tests\Tests.csproj", "{78F6E9E7-4322-4F87-8CE9-1EEF1B16D268}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Tests", "Tests\Tests.csproj", "{78F6E9E7-4322-4F87-8CE9-1EEF1B16D268}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ooui.Forms", "Ooui.Forms\Ooui.Forms.csproj", "{DB819A2F-91E1-40FB-8D48-6544169966B8}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Ooui.Forms", "Ooui.Forms\Ooui.Forms.csproj", "{DB819A2F-91E1-40FB-8D48-6544169966B8}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ooui.AspNetCore", "Ooui.AspNetCore\Ooui.AspNetCore.csproj", "{2EDF0328-698B-458A-B10C-AB1B4786A6CA}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Ooui.AspNetCore", "Ooui.AspNetCore\Ooui.AspNetCore.csproj", "{2EDF0328-698B-458A-B10C-AB1B4786A6CA}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "PlatformSamples", "PlatformSamples", "{12ADF328-BBA8-48FC-9AF1-F11B7921D9EA}"
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "PlatformSamples", "PlatformSamples", "{12ADF328-BBA8-48FC-9AF1-F11B7921D9EA}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AspNetCoreMvc", "PlatformSamples\AspNetCoreMvc\AspNetCoreMvc.csproj", "{7C6D477C-3378-4A86-9C31-AAD51204120B}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AspNetCoreMvc", "PlatformSamples\AspNetCoreMvc\AspNetCoreMvc.csproj", "{7C6D477C-3378-4A86-9C31-AAD51204120B}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "OouiTemplates", "Templates\OouiTemplates\OouiTemplates.csproj", "{1DA10AAB-EB41-49CF-9441-B4D28D0A7F96}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "OouiTemplates", "Templates\OouiTemplates\OouiTemplates.csproj", "{1DA10AAB-EB41-49CF-9441-B4D28D0A7F96}"
|
||||||
EndProject
|
EndProject
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Ooui.Wasm.Build.Tasks", "Ooui.Wasm.Build.Tasks\Ooui.Wasm.Build.Tasks.csproj", "{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}"
|
||||||
|
EndProject
|
||||||
Global
|
Global
|
||||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||||
Debug|Any CPU = Debug|Any CPU
|
Debug|Any CPU = Debug|Any CPU
|
||||||
|
@ -112,6 +114,18 @@ Global
|
||||||
{1DA10AAB-EB41-49CF-9441-B4D28D0A7F96}.Release|x64.Build.0 = Release|Any CPU
|
{1DA10AAB-EB41-49CF-9441-B4D28D0A7F96}.Release|x64.Build.0 = Release|Any CPU
|
||||||
{1DA10AAB-EB41-49CF-9441-B4D28D0A7F96}.Release|x86.ActiveCfg = Release|Any CPU
|
{1DA10AAB-EB41-49CF-9441-B4D28D0A7F96}.Release|x86.ActiveCfg = Release|Any CPU
|
||||||
{1DA10AAB-EB41-49CF-9441-B4D28D0A7F96}.Release|x86.Build.0 = Release|Any CPU
|
{1DA10AAB-EB41-49CF-9441-B4D28D0A7F96}.Release|x86.Build.0 = Release|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Debug|x64.Build.0 = Debug|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Debug|x86.Build.0 = Debug|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Release|x64.ActiveCfg = Release|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Release|x64.Build.0 = Release|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Release|x86.ActiveCfg = Release|Any CPU
|
||||||
|
{6E9C9582-0DA8-4496-BAE0-23EFAF4A10C2}.Release|x86.Build.0 = Release|Any CPU
|
||||||
EndGlobalSection
|
EndGlobalSection
|
||||||
GlobalSection(SolutionProperties) = preSolution
|
GlobalSection(SolutionProperties) = preSolution
|
||||||
HideSolutionNode = FALSE
|
HideSolutionNode = FALSE
|
||||||
|
|
Loading…
Reference in New Issue