parent
5ef1a58359
commit
6fdc410a41
@ -0,0 +1,57 @@
|
|||||||
|
## How to use reflection to explore an assembly?
|
||||||
|
or
|
||||||
|
## How to use reflection to dynamically add a plugin to an application?
|
||||||
|
|
||||||
|
This sample is made of three projects. Be careful with the role and moreover, the links between each other.
|
||||||
|
|
||||||
|
#### 1) ex_036_001_Mammifère.csproj
|
||||||
|
This assembly contains a **_Mammifère_** class with a simple **_Name_** property and compiles to a dll in the **_ex_036_001_Reflection\bin_** directory.
|
||||||
|
#### 2) ex_036_001_ChatChienOiseau.csproj
|
||||||
|
This assembly contains three classes:
|
||||||
|
- 2 of them are inheriting from **_Mammifère_** (**_Chat_** and **_Chien_**),
|
||||||
|
- the other one is not inheriting from **_Mammifère_** (**_Oiseau_**).
|
||||||
|
|
||||||
|
Important: this assembly references the first one, and compiles to a dll into the **_ex_036_001_Reflection\plugin_** directory.
|
||||||
|
#### 3) Applications\ex_036_001_Reflection.csproj
|
||||||
|
This assembly compiles to an exe in the **_ex_036_001_Reflection\bin_** directory. It references the first assembly, but **_does not reference_** the second assembly.
|
||||||
|
- First, it parses the plugin folder and gets all files :
|
||||||
|
```` C#
|
||||||
|
DirectoryInfo folder = new DirectoryInfo(Directory.GetCurrentDirectory().ToString()+"..\\..\\..\\plugin\\");F
|
||||||
|
ileInfo[] files = folder.GetFiles();
|
||||||
|
````
|
||||||
|
- Next, it filters these files and launches an assembly analysis on .dll files only
|
||||||
|
```` C#
|
||||||
|
foreach (FileInfo file in files.Where(f => f.Extension.Equals(".dll")))
|
||||||
|
{
|
||||||
|
AnalyseDLL(file.FullName);
|
||||||
|
}
|
||||||
|
````
|
||||||
|
- In this **_AnalyseDLL(string filePath)_** method, first, it loads the assembly:
|
||||||
|
```` C#
|
||||||
|
Assembly a = Assembly.LoadFile(filePath);
|
||||||
|
````
|
||||||
|
- then, it gets all the exported types of this assembly (all public types):
|
||||||
|
```` C#
|
||||||
|
Type[] types = a.GetExportedTypes();
|
||||||
|
````
|
||||||
|
- for each type **_t_** in **_types_**, it then writes its name in the Console, and tests if it's a subclass of **_Animal.Mammifère_**
|
||||||
|
```` C#
|
||||||
|
Write(t.Name);
|
||||||
|
|
||||||
|
if(t.GetTypeInfo().IsSubclassOf(typeof(Animal.Mammifère)))
|
||||||
|
{
|
||||||
|
//
|
||||||
|
}
|
||||||
|
````
|
||||||
|
|
||||||
|
|
||||||
|
Remember that this Console App does not reference the assembly where the classes **_Chat_**, **_Chien_** and **_Oiseau_** are defined.
|
||||||
|
It only references the first assembly with the **_Animal.Mammifère_** class, so
|
||||||
|
this is the only class it knows at compile-time. It _discovers_ the others by reflection.
|
||||||
|
|
||||||
|
Now you can explore the types (if they are primitive, interfaces, abstract, delegate, generics ...) and their members (methods, properties...).
|
||||||
|
Have fun!
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
_Marc Chevaldonné, 27th of may 2019_
|
Loading…
Reference in new issue