CodeDom add reference to existing file - c#

In visual studio, I can click on "Reference" > "Add reference" and browse to an existing .dll file from my computer. I can then use the referenced dll as follows:
dllNameSpace.dllClassName myReference = new dllNameSpace.dllClassName();
myReference.someVoid();
I know how to add a referenced assembly using codedom (will show this below), but the actual dll file is not being added to the project as it is when done through Visual Studio. Again, I need to be able to call some function in the dll file I'd like to reference.
What I'm doing now:
// Configure a CompilerParameters that links the system.dll and produces the specified executable file.
string[] referenceAssemblies = {
"System.dll",
"System.Drawing.dll",
"System.Windows.Forms.dll",
"System.Data.dll",
"System.Xml.dll",
"System.Management.dll",
Environment.GetFolderPath(Environment.SpecialFolder.Desktop) + #"\myDllFile.dll"
};
CompilerParameters cp = new CompilerParameters(referenceAssemblies, exeFile, false);
I'm assuming that I will need to do something different in order to have CodeDom add the dll to the output executable file. What more needs to be done here?
Thanks for the help everyone!

Following code may help you in loading the assembly and invoke method.
Assembly asmbly = Assembly.LoadFile("assembly.test.dll");
var myclass = asmbly.GetType("MyClass"); // use FullName i.e. Namespace.Classname
var myobj = Activator.CreateInstance(myclass);
myclass.GetMethod("MyMethod").Invoke(myobj,new object[]{"param1","param2"});

Related

C# Read text file from resources rather than locally [duplicate]

I have a web application project. I generated the DLL and import it in another project. I implemented VirtualPathProvider.
I followed this web site: http://support.microsoft.com/kb/910441/en-us?spid=8940&sid=global, and everything works until I add another site master.
I added site_export.master and changed its Build Action to Embedded Resource.
I changed my page to use the new site master.
GetManifestResourceStream() returns null when I load site_export.master.
I call GetManifestResourceNames() to check if site_export.master exists in the DLL and it does. It's in the list. All of the name spaces match. I didn't list the name space out here.
Why can't GetManifestResourceStream() load my new site_export.master? It loads site.master just fine. I know my DLL is loaded because I can see other files in the DLL.
Remember the following issues...
Step 1. Build action set to embedded resource see
C#’s GetManifestResourceStream Gotcha
Step 2. Use namespace.resourcename see GetManifestResourceStream() returns null ?
Actually, this method returns null if a private resource in another assembly is accessed and the caller does not have ReflectionPermission with the ReflectionPermissionFlag.MemberAccess flag.
Side-hint. To make sure you're in the right assembly and with right name: dump and evaluate all the resources available in your target assembly
string[] names = assembly.GetManifestResourceNames();
(in my case, I misused a namespace from another assembly)
I did this to make it work:
Step 1: Select the resource (CRDF.xsl in my case) and right click > Properties.
Set Build Action to "EmbeddedResource" and Logical Name to name of your choice, e.g. CRDFXSL.
Step 2 : Change your Source code like this:
Assembly _assembly;
_assembly = Assembly.GetExecutingAssembly();
xslStream = _assembly.GetManifestResourceStream("CRDFXSL");
_xmlReader = XmlReader.Create(xslStream);
Thus everything went smoooooooth..
Hint and Caution:
If the "Assembly name" and "Default namespace" does not match in the project file then also GetManifestResourceStream would return null. GetManifestResourceNames still returns the names of assemblies but during loading the manifest would not work.
Try this:
Dim ctx As Windows.ApplicationModel.Resources.Core.ResourceContext = New Windows.ApplicationModel.Resources.Core.ResourceContext()
ctx.Languages = {Globalization.CultureInfo.CurrentUICulture.Name}
Dim rmap As Windows.ApplicationModel.Resources.Core.ResourceMap = Windows.ApplicationModel.Resources.Core.ResourceManager.Current.MainResourceMap
Dim res = rmap.GetValue("Assets/sample.png", ctx)
Dim resFile = Await res.GetValueAsFileAsync
The Windows.ApplicationModel.Resources.Core.ResourceManager.Current.MainResourceMap list all resources.

How to edit a resource assembly in C# .net application

Now, I am working on edit existing string/icon resource assembly which is code in C# in VS. I have search some method to edit the binary file directly, particularly, I use mono.cecil (http://www.mono-project.com/docs/tools+libraries/libraries/Mono.Cecil/), almost all the localized resource files work fine. But only the English original resource file does not work. So I think I should give up this way, I hope to edit the file manually, either open source or original .net API is ok. Anyone have this kind experience to edit the resource file, please let me know:
BTW, the English project contains core logic code and references other dlls (OtherDLL.dll), this may cause exceptions when using mono.cecil, the code and exception is below.
AssemblyDefinition assemblyDefinition = AssemblyDefinition.ReadAssembly(resourceFileName);
// Some code
assemblyDefinition.Write(newFileName); // This will cause exception: "Failed to resolve assembly: 'OtherDLL, Version=10.1.1.1, Culture=neutral, PublicKeyToken=null'
The english dll is TestDll.dll under deployment directory, and other localized resource dlls are TestDll.resources.dll under localized directory, like /de/TestDll.resources.dll and /zh-CN/TestDll.resources.dll.
Now I need the method to achieve the target(edit and save resource part), so please help me to find a way to achieve the goal. Any comments will be appreciated.
Thanks in advance.
The problem is that you need to set the search directories for the assembly references in the metadata tables to be rewritten correctly:
var assemblyFile = #"c:\myassembly.dll";
var resolver = new DefaultAssemblyResolver();
// add directory of the source assembly for references
resolver.AddSearchDirectory(Path.GetDirectoryName(assemblyFile));
// add .NET runtime directories
var runtimeDir = RuntimeEnvironment.GetRuntimeDirectory();
foreach (var dir in Directory.GetDirectories(RuntimeEnvironment.GetRuntimeDirectory(), "*", SearchOption.AllDirectories))
{
resolver.AddSearchDirectory(dir);
}
var mod = AssemblyDefinition.ReadAssembly(assemblyFile, new ReaderParameters { AssemblyResolver = resolver }).MainModule;
mod.Write(assemblyFile + ".patched");
When you want to change resources with Mono.Cecil:
var strings = mod.Resources.SingleOrDefault(a => a.Name == "English.resources");
mod.Resources.Remove(strings);
using var ms = new MemoryStream();
using var rw = new ResourceWriter(ms);
rw.AddResource("GreetingText", "Hello World");
rw.Generate();
ms.Position = 0;
mod.Resources.Add(new EmbeddedResource("English.resources", ManifestResourceAttributes.Public, ms));
mod.Write(assemblyFile + ".patched");
Regards

System.Printing not found( C# )?

I am trying to run the following example from MSDN:
using System.Printing;
public class PrintTest {
public static void Main(string[] args)
{
// Create the printer server and print queue objects
LocalPrintServer localPrintServer = new LocalPrintServer();
PrintQueue defaultPrintQueue = LocalPrintServer.GetDefaultPrintQueue();
// Call AddJob
PrintSystemJobInfo myPrintJob = defaultPrintQueue.AddJob();
// Write a Byte buffer to the JobStream and close the stream
Stream myStream = myPrintJob.JobStream;
Byte[] myByteBuffer = UnicodeEncoding.Unicode.GetBytes("This is a test string for the print job stream.");
myStream.Write(myByteBuffer, 0, myByteBuffer.Length);
myStream.Close();
}
}
but the compiler is complaining
The type or namespace Printing does not exist in the namespace
System(are you missing an assembly reference) ?
How do I solve this issue ?
EDIT: How do I add a reference for command line compiled application ( Not Visual Studio)
From the command line something like csc /reference:lib\System.Printing.dll
Original Answer
Project > Add Reference, then under 'Assemblies > Framework'.
Choose System.Printing.
You can find out which Assembly you need to add a reference to by Googling the namespace followed by the word 'assembly'. In your case:
System.Printing assembly
The second result is from MSDN and indicates which assembly System.Printing can be found in.
From Command prompt
Create a public reference
/reference:[alias=]filename
/reference:filename
Where
Arguments
filename
The name of a file that contains an assembly manifest. To import more than one file, include a separate /reference option for each file.
alias
A valid C# identifier that will represent a root namespace that will contain all namespaces in the assembly.
Microsoft documentation page for cmd
From Visual Studio Community 2013 (Free version)
Right click References folder in your solution and browse for it there.
You are missing an assembly reference. Add a reference to System.Printing.dll.
You need to add the System.Printing assembly to your project.
You can find this by right clicking on your project and clicking "Add Reference". (You can search for it in the Assemblies > Framework tab)
Additionally, you must add using System.IO; in order to use Stream.
In your Solution Explorer right click on References click on Add Reference click on the .NET tab and scroll to System.Drawing. It should work.
Original answer found here:
https://social.msdn.microsoft.com/Forums/vstudio/en-US/0648fdc4-f67b-476e-b434-998efec14b89/class-systemprintingprintcapabilities-not-found?forum=wpf
However, you'll need to add the Assembly called ReachFramework

Visual studio locking DLL because of embedding views using "embedded resource"

PROJECT A contains a View , let's call it View1.ascx marked as "Embedded Resource" in the properties window
both PROJECT A and PROJECT B and C load that view1 from the PROJECTA.DLL using a custom resource provider
This way I can reuse my views across projects.
Sadly, this causes visual studio to be unable to build PROJECT B , OR C the first time around, after each change to the PROJECTA.dll
"Error 12 Could not copy "C:\GIT\PROJECTA\PROJECTA\bin\PROJECTA.dll" to "bin\PROJECTA.dll". Exceeded retry count of 10. Failed."
Is there any way to make this work? or should I somehow move all "re-used" views to a seperate assembly? The views use classes from PROJECT A so that's why I kept them inside PROJECT A
To make everything clear: Building it a second time around usually works, and the code and views are all working, it's just a really big waste of time to have to wait 10 seconds for the first build attempt to fail.
Apparantly my assemblyresourceprovider used a AssemblyResourceVirtualFile:VirtualFile oebject that was loading my dll from Assembly.LoadFile instead of using the recommended way of loading dlls in memory as described here: http://fzysqr.com/2010/04/26/asp-net-mvc2-plugin-architecture-tutorial/
I left the old line of code in comment for you guys to see where the problem was
public override System.IO.Stream Open()
{
string[] parts = path.Split('/');
string assemblyName = parts[2];
string resourceName = parts[3];
assemblyName = Path.Combine(HttpRuntime.BinDirectory, assemblyName);
byte[] assemblyBytes = File.ReadAllBytes(assemblyName);
System.Reflection.Assembly assembly = Assembly.Load(assemblyBytes);
/*System.Reflection.Assembly assembly = System.Reflection.Assembly.LoadFile(assemblyName);*/
if (assembly != null)
{
Stream resourceStream = assembly.GetManifestResourceStream(resourceName);
return resourceStream;
}
return null;
}

Load an assembly from an embedded resource

I would like to load a dll file (Test.dll) as an assembly. I am able to do this using both direct Visual Studio references (ie. loading the dll as a reference to my C# application) as well as loading the dll using the Assembly.LoadFile(filename) method. Now, I would like to add my dll file as an embedded resource to my Visual Studio application, and load the dll file as an assembly. I know how to load this resource as a byte array, is there some correlation between the byte array and the assembly that I could use? Furthermore, I need to be able to call a method located within the dll file. See the code below - it will further explain what I am doing.
Assembly SampleAssembly = Assembly.LoadFrom("WindowsFormsApplication2.ThisisaTESTDLL.dll");
Type myType = SampleAssembly.GetTypes()[0];
MethodInfo Method = myType.GetMethod("myVoid");
object myInstance = Activator.CreateInstance(myType,null);
Method.Invoke(myInstance,new object[] { "param1", "param1"});
If I am missing anything here, please respectfully let me know and I will edit the original post.
Assembly.GetExecutingAssembly().GetManifestResourceStream(...)
That should get you a Stream object. You can read a byte array from that.
You can load that using Assembly.Load
I embedded AxInterop.WMPLib.dll and Interop.WMPLib.dll into my exe and got them loaded by using the following code. The code is placed just at the beginning of static void Main() in Program.cs file. Target framework is .NET 3.5 in my case. This code helped me bundle the dlls into the exe itself without having to deploy them through installers. I have hardcoded my names. In the code below "res" is the name of my resource "res.resx" that contains the two embedded dlls.
AppDomain.CurrentDomain.AssemblyResolve += new ResolveEventHandler(
(s, a) =>
{
if (a.Name.Substring(0, a.Name.IndexOf(",")) == "AxInterop.WMPLib")
{
return Assembly.Load(res.AxInterop_WMPLib);
}
if (a.Name.Substring(0, a.Name.IndexOf(",")) == "Interop.WMPLib")
{
return Assembly.Load(res.Interop_WMPLib);
}
return null;
});

Categories

Resources