/// <summary> /// Generates early-bound object wrapper /// </summary> /// <param name="sender"> </param> /// <param name="e"> </param> private void OnGenerateWrapper(object sender, EventArgs e) { try { //Get current Project: Project[] projects = VSUtils.GetProjects(GetNodeSite()); if (projects == null || projects.Length == 0) { return; } //This is an assumtion that's working so far. //TODO: verify if this is the right way to determine the startup project //in the solution: Project curProject = projects[0]; string curProjSuffix = VSUtils.MapProjectGuidToSuffix(new Guid(curProject.Kind)); if (curProjSuffix == string.Empty) { //neither a VB nor a CS project throw new Exception(WMISys.GetString("WMISE_Invalid_Project_Type_For_CodeGen")); } ProjectItems projItems = curProject.ProjectItems; if (projItems == null) { throw new Exception(WMISys.GetString("WMISE_Could_Not_Add_File_to_Project")); } Guid curProjectType = new Guid(curProject.Kind); string wrapperFileName = className + "." + curProjSuffix; if (!mgmtObj.GetStronglyTypedClassCode(VSUtils.MapProjectGuidToCodeLanguage(curProjectType), Path.GetTempPath() + "\\" + wrapperFileName)) { throw new Exception(WMISys.GetString("WMISE_Code_Generation_Failed")); } ProjectItem newItem = projItems.AddFromFileCopy(Path.GetTempPath() + "\\" + wrapperFileName); if (newItem == null) { throw new Exception(WMISys.GetString("WMISE_Could_Not_Add_File_to_Project")); } File.Delete(Path.GetTempPath() + "\\" + wrapperFileName); } catch (Exception exc) { MessageBox.Show(WMISys.GetString("WMISE_Exception", exc.Message, exc.StackTrace)); } }
/// <summary> /// This will generate an early-bound wrapper for WMI class, /// add it as a source file to the current project; instantiate /// the newly-generated type and return it as a drag component. /// </summary> /// <param name="designerHost"> </param> public override IComponent[] CreateDragComponents(IDesignerHost designerHost) { try { Project[] projects = VSUtils.GetProjects(GetNodeSite()); if (projects == null) { return(null); } //This is an assumtion that's working so far. //TODO: verify this is the right way to determine the startup project //in the solution: Project curProject = projects[0]; ProjectItems projItems = curProject.ProjectItems; if (projItems == null) { return(null); } string curProjSuffix = VSUtils.MapProjectGuidToSuffix(new Guid(curProject.Kind)); if (curProjSuffix == string.Empty) { //neither a VB nor a CS project throw new Exception(WMISys.GetString("WMISE_Invalid_Project_Type_For_CodeGen")); } Guid curProjectType = new Guid(curProject.Kind); string wrapperFileName = className + "." + curProjSuffix; CodeTypeDeclaration newType = null; if (!mgmtClassObj.GetStronglyTypedClassCode(true, true, out newType)) { throw new Exception(WMISys.GetString("WMISE_Code_Generation_Failed")); } ICodeGenerator cg = VSUtils.MapProjectGuidToCodeGenerator(curProjectType); //construct generated code Namespace name (in the form "System.Management.root.cimv2") string[] nsParts = nsName.ToLower().Split(new Char[] { '\\' }); string codeNSName = "System.Management"; for (int i = 0; i < nsParts.Length; i++) { codeNSName += nsParts[i] + "."; } codeNSName = codeNSName.Substring(0, codeNSName.Length - 1); System.CodeDom.CodeNamespace cn = new System.CodeDom.CodeNamespace(codeNSName); // Add imports to the code cn.Imports.Add(new CodeNamespaceImport("System")); cn.Imports.Add(new CodeNamespaceImport("System.ComponentModel")); cn.Imports.Add(new CodeNamespaceImport("System.Management")); cn.Imports.Add(new CodeNamespaceImport("System.Collections")); // Add class to the namespace cn.Types.Add(newType); //Now create the output file TextWriter tw = new StreamWriter(new FileStream(Path.GetTempPath() + "\\" + wrapperFileName, FileMode.Create)); // And write it to the file cg.GenerateCodeFromNamespace(cn, tw, new CodeGeneratorOptions()); ProjectItem newItem = projItems.AddFromFileCopy(Path.GetTempPath() + "\\" + wrapperFileName); if (newItem == null) { throw new Exception(WMISys.GetString("WMISE_Could_Not_Add_File_to_Project")); } File.Delete(Path.GetTempPath() + "\\" + wrapperFileName); Object comp = Activator.CreateInstance(designerHost.GetType(codeNSName + "." + newType.Name)); if (comp == null) { throw new Exception(WMISys.GetString("WMISE_Could_Not_Instantiate_Management_Class")); } return(new IComponent[] { (IComponent)comp }); //The commented-out block below implements the solution with VS custom code generator: /* * //create a new file containing the path to the instance object * string tempFileName = Path.GetTempPath() + this.className + ".wmi"; * StreamWriter sw = File.AppendText(tempFileName); * if (sw == null) * { * return null; * } * * sw.WriteLine(WmiHelper.MakeClassPath(this.serverName, * this.nsName, * this.className)); * * sw.Flush(); * sw.Close(); * ProjectItem newItem = projItems.AddFromFileCopy(tempFileName); * if (newItem == null) * { * return null; * } * File.Delete(tempFileName); * VSUtils.SetGenerator(newItem, "WMICodeGenerator"); * return null; //is this OK??? */ } catch (Exception exc) { MessageBox.Show(WMISys.GetString("WMISE_Exception", exc.Message, exc.StackTrace)); return(null); } }