I have been using the following Powershell to browse around some assemblies
$assembly = [Reflection.Assembly]::Load('myassembly')
$assembly.GetTypes()
Sometimes, I get the following exception:
Exception calling "GetTypes" with "0" argument(s): "Unable to load one or more of the requested types. Retrieve the LoaderExceptions property for more information."
At line:1 char:19
+ $assembly.GetTypes <<<< ()
+ CategoryInfo : NotSpecified: (:) [], MethodInvocationException
+ FullyQualifiedErrorId : DotNetMethodException
To get at the actual error, I use the following:
$x = $Error[0]
$x.Exception.GetBaseException().LoaderExceptions
Then all I had to do was to load the assemblies that were listed and my initial Load() now works.
Learning how to do things and fix stuff as I go because who really has time to sit in a classroom. Posting it all here because I can not remember it all.
Showing posts with label assembly. Show all posts
Showing posts with label assembly. Show all posts
Monday, December 1, 2014
Monday, May 26, 2014
Calling private member using reflection in Powershell
Often I have to put together some Powershell scripts for troubleshooting. These scripts are based on some c# code. Recently, I had to mimic the behaviour of a call to a private member overload of GetTags in the Microsoft.Office.Server.SocialData.SocialTagManager class.
$site = Get-SPSite my-site-url
$context = Get-SPServiceContext($site)
$socialTagManager = New-Object -TypeName Microsoft.Office.server.SocialData.SocialTagManager -ArgumentList $context
# Get the type definition
$type = [type]'Microsoft.Office.Server.SocialData.SocialTagManager'
# List the GetTags members
($socialTagManager | Get-Member GetTags).Definition.Replace("), ", ")`n")
This results in (just the public members):
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(Microsoft.Office.Server.UserProfiles.UserProfile user)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(Microsoft.Office.Server.UserProfiles.UserProfile user, int maximumItemsToReturn)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(Microsoft.Office.Server.UserProfiles.UserProfile user, int maximumItemsToReturn, int startIndex)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(System.Uri url)
Now use Reflection
# Which methods to list
$bindingFlags = [Reflection.BindingFlags] "Default,NonPublic,Instance"
# List the methods
$type.GetMethods($bindingFlags) | Where-Object {$_.Name -eq 'GetTags'} | ForEach-Object {$_.GetParameters() | Select-Object Member -First 1}
This results in (both public and private members);
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(System.DateTime, System.DateTime)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(System.DateTime, System.DateTime, Int32)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(System.DateTime, System.DateTime, Int32, Int32)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(System.Uri, Microsoft.Office.Server.UserProfiles.UserProfile, System.Nullable`1[System.DateTime], System.Nullable`1[System.DateTime])
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(System.Uri, Int32)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(System.Uri, Int32, Microsoft.Office.Server.SocialData.SocialItemPrivacy)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(Microsoft.SharePoint.Taxonomy.Term[], Int32, Microsoft.Office.Server.SocialData.SocialItemPrivacy)
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(Microsoft.Office.Server.UserProfiles.UserProfile, Int32, Int32, Boolean, System.Nullable`1[System.DateTime], System.Nullable`1[System.DateTime])
Microsoft.Office.Server.SocialData.SocialTag[] GetTags(Microsoft.Office.Server.UserProfiles.UserProfile, Int32, Int32, Boolean, System.Nullable`1[System.DateTime], System.Nullable`1[System.DateTime], System.Nullable`1[System.Guid])
Now to call a private member. Let's call: Microsoft.Office.Server.SocialData.SocialTag[] GetTags(System.DateTime, System.DateTime, Int32, Int32)
$startTime = [DateTime]'2014-05-01 00:00:00'
$endTime = [DateTime]'2014-05-31 00:00:00'
$maximumItemsToReturn = 1000
$startIndex = 0
$typeList = @([type]'DateTime', [type]'DateTime', [type]'Int32', [type]'Int32')
$method = $socialTagManager.GetType().GetMethod('GetTags', $bindingFlags, $null, $typeList, $null)
$terms = $method.Invoke($socialTagManager, [Object[]] @($startTime, $endTime, $maximumItemsToReturn, $startIndex))
$terms | Format-Table @{l='Term';e={$_.Term.Name}}, Title -AutoSize
For more details on calls to other types of methods, please reference: https://www.netspi.com/blog/entryid/200/using-powershell-and-reflection-api-to-invoke-methods-from-net-assemblies
Friday, April 5, 2013
Managing assemblies with Powershell
A simple way to access assemblies and see what's in them. Still a work in progress. I hope to add more tricks to this post soon.
Load in the assembly
$assembly = [Reflection.Assembly]::LoadFile($assemblyPath)
or
$assembly = [Reflection.Assembly]::Load($assemblyName)
Get details on a type defined in the assembly
$type = $assembly.DefinedTypes | Where-Object {$_.Name -eq $typeName}
$type.DeclaredConstructors | ForEach-Object {$_.ToString()}
$type.DeclaredMethods | ForEach-Object {$_.ToString()}
To load the assembly for use
Add-Type -Path $assemblyPath #if assembly in file
or
Add-Type -AssemblyName $assemblyName #if assembly in GAC
For some reason $assemblyName must be the full name contrary to the documentation in Add-Type
Get all assemblies in current AppDomain
[AppDomain]::CurrentDomain.GetAssemblies() | Select-Object FullName | Sort-Object FullName
References:
System.Reflection.Assembly class
Add-Type cmdlet
AppDomain class
Load in the assembly
$assembly = [Reflection.Assembly]::LoadFile($assemblyPath)
or
$assembly = [Reflection.Assembly]::Load($assemblyName)
Get details on a type defined in the assembly
$type = $assembly.DefinedTypes | Where-Object {$_.Name -eq $typeName}
$type.DeclaredConstructors | ForEach-Object {$_.ToString()}
$type.DeclaredMethods | ForEach-Object {$_.ToString()}
To load the assembly for use
Add-Type -Path $assemblyPath #if assembly in file
or
Add-Type -AssemblyName $assemblyName #if assembly in GAC
For some reason $assemblyName must be the full name contrary to the documentation in Add-Type
Get all assemblies in current AppDomain
[AppDomain]::CurrentDomain.GetAssemblies() | Select-Object FullName | Sort-Object FullName
References:
System.Reflection.Assembly class
Add-Type cmdlet
AppDomain class
Subscribe to:
Posts (Atom)