/// <summary> /// Serialize the applet to a file /// </summary> private void SerializeApplet(AppletPackage pkg, string target, String csproj = null) { Emit.Message("INFO", "Slipsteam {0} -> {1}", pkg.Meta.Id, target); // Add the file using (var fs = File.Create(Path.Combine(target, pkg.Meta.Id) + ".pak")) pkg.Save(fs); // Save the CSPROJ info if (!String.IsNullOrEmpty(csproj)) { XmlDocument doc = new XmlDocument(); doc.Load(csproj); // Get Android Assets - Do they exist for this object? var assetPath = Path.Combine(target.Replace(Path.GetDirectoryName(csproj), "").Substring(1), pkg.Meta.Id + ".pak"); var node = doc.SelectSingleNode($"//*[local-name() = 'AndroidAsset'][@Include = '{assetPath}']"); if (node == null) { var itemElement = doc.CreateElement("ItemGroup", "http://schemas.microsoft.com/developer/msbuild/2003") .AppendChild(doc.CreateElement("AndroidAsset", "http://schemas.microsoft.com/developer/msbuild/2003")) .Attributes.Append(doc.CreateAttribute("Include")); itemElement.Value = assetPath; doc.DocumentElement.AppendChild(itemElement.OwnerElement.ParentNode); doc.Save(csproj); } } }
/// <summary> /// Creates an applet. /// </summary> /// <returns>Returns the created applet manifest info.</returns> public AppletManifestInfo CreateApplet(AppletPackage appletPackage) { using (MemoryStream ms = new MemoryStream()) { appletPackage.Save(ms); ms.Flush(); return(this.Client.Post <byte[], AppletManifestInfo>("Applet", "application/octet-stream", ms.ToArray())); } }
/// <summary> /// Updates an applet. /// </summary> /// <param name="appletId">The id of the applet to be updated.</param> /// <param name="appletPackage">The applet containing the updated information.</param> /// <returns>Returns the updated applet.</returns> public AppletManifestInfo UpdateApplet(Guid appletId, AppletPackage appletPackage) { using (var ms = new MemoryStream()) { appletPackage.Save(ms); ms.Flush(); return(this.Client.Put <byte[], AppletManifestInfo>($"Applet/{appletId}", "application/octet-stream", ms.ToArray())); } }
/// <summary> /// Install the package /// </summary> public AppletInfo Put(AppletPackage package) { // Locate the specified package try { using (var ms = new MemoryStream()) { package.Save(ms); return(this.m_client.Put <MemoryStream, AppletInfo>("pak", new MemoryStream(ms.ToArray()))); } } catch (RestClientException e) { this.m_traceSource.TraceEvent(TraceEventType.Error, e.HResult, "Error pushing package {0}: {1}", package.Meta, e); throw; } }
/// <summary> /// Sign an existing package /// </summary> private static int Sign(ConsoleParameters parameters) { try { AppletPackage pkg = null; using (FileStream fs = File.OpenRead(parameters.Source)) pkg = AppletPackage.Load(fs); Console.WriteLine("Will sign package {0}", pkg.Meta); pkg = CreateSignedPackage(pkg.Unpack(), parameters); using (FileStream fs = File.Create(parameters.Output ?? Path.ChangeExtension(parameters.Source, ".signed.pak"))) pkg.Save(fs); return(0); } catch (Exception e) { Console.Error.WriteLine("Cannot sign package: {0}", e); return(-0232); } }
/// <summary> /// Sign an existing package /// </summary> public int Sign() { try { AppletPackage pkg = null; using (FileStream fs = File.OpenRead(this.m_parms.Source)) pkg = AppletPackage.Load(fs); Emit.Message("INFO", "Will sign package {0}", pkg.Meta); pkg = this.CreateSignedPackage(pkg.Unpack()); using (FileStream fs = File.Create(this.m_parms.Output ?? Path.ChangeExtension(this.m_parms.Source, ".signed.pak"))) pkg.Save(fs); return(0); } catch (Exception e) { Emit.Message("ERROR", "Cannot sign package: {0}", e); return(-0232); } }
/// <summary> /// Installs a package into the package repository /// </summary> public AppletInfo Put(AppletPackage package) { if (this.m_packageInfos == null) { throw new InvalidOperationException("Package repository is not initialized"); } else if (String.IsNullOrEmpty(package.Meta?.Id)) { throw new ArgumentNullException("Package must have ID"); } else if (String.IsNullOrEmpty(package.Meta?.Version)) { throw new ArgumentNullException("Package must have version"); } try { var targetPath = Path.Combine(this.GetRepositoryPath(), $"{package.Meta.Id}-{package.Meta.Version}.pak"); if (!Directory.Exists(Path.GetDirectoryName(targetPath))) { Directory.CreateDirectory(Path.GetDirectoryName(targetPath)); } using (var fs = System.IO.File.Create(targetPath)) package.Save(fs); // Add the file to the repository lock (this.m_lockObject) if (!this.m_packageInfos.ContainsKey(targetPath)) { this.m_packageInfos.Add(targetPath, package.Meta); } return(package.Meta); } catch (System.Exception e) { throw new System.Exception($"Could not install package {package.Meta.Id} v {package.Meta.Version}", e); } }
/// <summary> /// Compile /// </summary> static int Compile(ConsoleParameters parameters) { int retVal = 0; // First is there a Manifest.xml? if (!Path.IsPathRooted(parameters.Source)) { parameters.Source = Path.Combine(Environment.CurrentDirectory, parameters.Source); } // Applet collection AppletCollection ac = new AppletCollection(); XmlSerializer xsz = new XmlSerializer(typeof(AppletManifest)); XmlSerializer xpz = new XmlSerializer(typeof(AppletPackage)); if (parameters.References != null) { foreach (var itm in parameters.References) { if (File.Exists(itm)) { using (var fs = File.OpenRead(itm)) { if (Path.GetExtension(itm) == ".pak") { using (var gzs = new GZipStream(fs, CompressionMode.Decompress)) { var pack = xpz.Deserialize(gzs) as AppletPackage; var mfst = pack.Unpack(); mfst.Initialize(); ac.Add(mfst); Console.WriteLine("Added reference to {0}; v={1}", mfst.Info.Id, mfst.Info.Version); } } else { var mfst = xsz.Deserialize(fs) as AppletManifest; mfst.Initialize(); ac.Add(mfst); Console.WriteLine("Added reference to {0}; v={1}", mfst.Info.Id, mfst.Info.Version); } } } } } Console.WriteLine("Processing {0}...", parameters.Source); String manifestFile = Path.Combine(parameters.Source, "manifest.xml"); if (!File.Exists(manifestFile)) { Console.WriteLine("Directory must have manifest.xml"); } else { Console.WriteLine("\t Reading Manifest...", parameters.Source); using (var fs = File.OpenRead(manifestFile)) { AppletManifest mfst = xsz.Deserialize(fs) as AppletManifest; mfst.Assets.AddRange(ProcessDirectory(parameters.Source, parameters.Source, parameters)); foreach (var i in mfst.Assets) { i.Name = i.Name.Substring(1); } if (mfst.Info.Version.Contains("*")) { mfst.Info.Version = mfst.Info.Version.Replace("*", (((DateTime.Now.Subtract(new DateTime(DateTime.Now.Year, 1, 1)).Ticks >> 24) % 10000)).ToString("0000")); } if (!Directory.Exists(Path.GetDirectoryName(parameters.Output)) && !String.IsNullOrEmpty(Path.GetDirectoryName(parameters.Output))) { Directory.CreateDirectory(Path.GetDirectoryName(parameters.Output)); } AppletPackage pkg = null; // Is there a signature? if (!String.IsNullOrEmpty(parameters.SignKey)) { pkg = CreateSignedPackage(mfst, parameters); if (pkg == null) { return(-102); } } else { Console.WriteLine("WARNING:>>> THIS PACKAGE IS NOT SIGNED - MOST OPEN IZ TOOLS WILL NOT LOAD IT"); mfst.Info.PublicKeyToken = null; pkg = mfst.CreatePackage(parameters.Compression); //pkg.Meta.PublicKeyToken = null; } pkg.Meta.Hash = SHA256.Create().ComputeHash(pkg.Manifest); using (var ofs = File.Create(Path.ChangeExtension(parameters.Output ?? "out.pak", ".pak"))) { pkg.Save(ofs); } // Render the build directory if (!String.IsNullOrEmpty(parameters.Deploy)) { var bindir = Path.Combine(Path.GetDirectoryName(parameters.Output), "bin"); if (String.IsNullOrEmpty(parameters.Deploy)) { if (Directory.Exists(bindir) && parameters.Clean) { Directory.Delete(bindir, true); } bindir = Path.Combine(bindir, mfst.Info.Id); Directory.CreateDirectory(bindir); } else { bindir = parameters.Deploy; } mfst.Initialize(); ac.Add(mfst); foreach (var lang in mfst.Strings) { string wd = Path.Combine(bindir, lang.Language); if (String.IsNullOrEmpty(parameters.Lang)) { Directory.CreateDirectory(wd); } else if (parameters.Lang == lang.Language) { wd = bindir; } else { continue; } foreach (var m in ac) { foreach (var itm in m.Assets) { try { String fn = Path.Combine(wd, m.Info.Id, itm.Name.Replace("/", "\\")); Console.WriteLine("\tRendering {0}...", fn); if (!Directory.Exists(Path.GetDirectoryName(fn))) { Directory.CreateDirectory(Path.GetDirectoryName(fn)); } File.WriteAllBytes(fn, ac.RenderAssetContent(itm, lang.Language)); } catch (Exception e) { Console.WriteLine("E: {0}: {1} {2}", itm, e.GetType().Name, e); retVal = -1000; } } } } } } } return(retVal); }
/// <summary> /// Performs an installation /// </summary> public bool Install(AppletPackage package, bool isUpgrade, AppletSolution owner) { this.m_tracer.TraceInfo("Installing {0}", package.Meta); var appletScope = owner?.Meta.Id ?? String.Empty; // TODO: Verify package hash / signature if (!this.VerifyPackage(package)) { throw new SecurityException("Applet failed validation"); } else if (!this.m_appletCollection[appletScope].VerifyDependencies(package.Meta)) { this.m_tracer.TraceWarning($"Applet {package.Meta} depends on : [{String.Join(", ", package.Meta.Dependencies.Select(o => o.ToString()))}] which are missing or incompatible"); } // Save the applet var appletDir = this.m_configuration.AppletDirectory; if (!Path.IsPathRooted(appletDir)) { appletDir = Path.Combine(Path.GetDirectoryName(Assembly.GetEntryAssembly().Location), this.m_configuration.AppletDirectory); } if (owner != null) { appletDir = Path.Combine(appletDir, owner.Meta.Id); } if (!Directory.Exists(appletDir)) { Directory.CreateDirectory(appletDir); } // Install var pakFile = Path.Combine(appletDir, package.Meta.Id + ".pak"); if (this.m_appletCollection[appletScope].Any(o => o.Info.Id == package.Meta.Id) && File.Exists(pakFile) && !isUpgrade) { throw new InvalidOperationException($"Cannot replace {package.Meta} unless upgrade is specifically specified"); } using (var fs = File.Create(pakFile)) { package.Save(fs); } lock (this.m_fileDictionary) if (!this.m_fileDictionary.ContainsKey($"{appletScope}{package.Meta.Id}")) { this.m_fileDictionary.Add($"{appletScope}{package.Meta.Id}", pakFile); } var pkg = package.Unpack(); // remove the package from the collection if this is an upgrade if (isUpgrade) { this.m_appletCollection[appletScope].Remove(pkg); } this.m_appletCollection[appletScope].Add(pkg); // We want to install the templates & protocols into the DB this.m_tracer.TraceInfo("Installing templates..."); // Install templates var idp = ApplicationServiceContext.Current.GetService <ITemplateDefinitionRepositoryService>(); if (idp != null) { foreach (var itm in pkg.Templates) { if (idp.GetTemplateDefinition(itm.Mnemonic) == null) { this.m_tracer.TraceInfo("Installing {0}...", itm.Mnemonic); idp.Insert(new TemplateDefinition() { Oid = itm.Oid, Mnemonic = itm.Mnemonic, Description = itm.Description, Name = itm.Mnemonic }); } } } AppletCollection.ClearCaches(); return(true); }