【发布时间】:2020-10-10 04:34:22
【问题描述】:
我有一堆由我编写的 C# 库,应该被 PowerShell 脚本用来在我们的环境中执行各种 devops 任务。 最奇怪的事情正在发生,我认为这与我的 PowerShell 脚本中库的外部加载有关。
工作示例
首先,我将演示通用代码和一个这样的类的工作原理,以便您了解我是如何使用它的: 我们首先为我的 API 加载外部库
$binpath = "$PSScriptRoot\bin"
#Reads credentials
Add-Type -Path "$binpath\CredentialHandling.dll"
#Is used for logging
Add-Type -Path "$binpath\OperationLogging.dll"
#Is used to handle the different dev environments (we have a lot of them!)
Add-Type -Path "$binpath\IdmEnvironmentHandling.dll"
#Is used to perform operations in LDAP
Add-Type -Path "$binpath\IdmLdapInteractions.dll"
#Is used to perform operations with a specific REST API service
#The base library that contains general methods and binds it all together
Add-Type -Path "$binpath\IdmApi.dll"
我设置了应该在 C# 代码中调用构造函数的对象,然后继续在其中一个连接器上执行方法
#The IdmApiOperator contains multiple connectors to different platforms to perform unified tasks
$idm = [IdmApi.IdmApiOperator]::new($environment)
$searchbase = 'ou=OrganizationalUnit,o=SYSTEM'
$ldapFilter = '(cn=CommonNameExample)'
#This will return some sort of ldap search response, which works
$search = $idm.LdapOperator.Search($searchbase, ldapFilter)
此代码上下文中的 Ldap 运算符使用标准 .NET 库 System.DirectoryServices.Protocols,它的工作方式非常棒,所有实际代码都在 C# 和 PowerShell 中运行。
IdmApiConnector 的成员(运算符的基类,有点像接口)
行不通的例子
我们首先为我的 API 加载外部库,这次包括一个用于 REST API 的库,对 RestOperator 类的调用将失败,我不明白为什么
$binpath = "$PSScriptRoot\bin"
#Reads credentials
Add-Type -Path "$binpath\CredentialHandling.dll"
#Is used for logging
Add-Type -Path "$binpath\OperationLogging.dll"
#Is used to handle the different dev environments (we have a lot of them!)
Add-Type -Path "$binpath\IdmEnvironmentHandling.dll"
#Is used to perform operations in LDAP
Add-Type -Path "$binpath\IdmLdapInteractions.dll"
#Is used to perform operations with a specific REST API service
Add-Type -Path "$binpath\IdmRestInteractions.dll"
#Used by IdmRestInteractions, put in here just to be safe
Add-Type -Path "$binpath\RestSharp.dll"
#The base library that contains general methods and binds it all together
Add-Type -Path "$binpath\IdmApi.dll"
$idm = [IdmApi.IdmApiOperator]::new($environment)
#Purely a test, this method will return an Oauth token for the specified connection, this method is a derivative of the actual method that will set a token property in the base class.
$token = $idm.RestOperator.GetToken()
#Will return null, not even an error is thrown
GetToken() 方法的代码,它返回一个 IdmToken,定义在 IdmRestInteractions.Objects 下的同一命名空间中:
public IdmToken GetToken()
{
string path = MethodPaths["OAuthUri"];
RestRequest request = new RestRequest()
{
Method = Method.POST,
Resource = path,
};
string authstring = GetOAuthString();
request.AddHeader("Authorization", authstring);
string body = ""//here it creates the body, removed in this version
request.AddParameter("application/x-www-form-urlencoded", body, ParameterType.RequestBody);
IRestResponse response = Client.Post(request); //Client here being an IRestClient object from the library RestSharp
return JsonConvert.DeserializeObject<IdmToken>(response.Content);
}
查看tomcat主机,该方法似乎没有通过什么的,因为服务器没有收到任何请求。 将方法的输出改成乱码会使其返回乱码,所以并不是没有触发该方法。 我还尝试将 Newtonsoft.Json 添加到我的 PowerShell 代码中,但这也没有改变任何东西。 当然,当我稍后在我的程序中使用该令牌时,它会给出一个 nullref 异常......
总结
- 我使用自己在 PowerShell 脚本中以 .dll 格式编写的库。
- 一个有效,一个无效,问题不在于库的使用或实现
- Rest Api 连接器使用外部库 RestSharp(这可能是原因?)
- 方法被触发,但不向服务执行 API 请求
- 最重要的是,代码确实可以在 C# 中本地运行,这不像我没有经过身份验证
【问题讨论】:
-
缺乏服务器端活动本身并不能证明没有调用客户端方法 - 如果其余客户端静默失败请求并且
response.Content为空,JsonConvert.DeserializeObject<IdmToken>()将返回 @ 987654332@. -
只是一个虚拟的猜测,你说你的 dll 使用 restsharp.dll 但在我的理解中,没有魔法可以告诉你的 dll 在哪里寻找 restsharp.dll 并简单地加载它不会做我认为的诀窍。在 PowerShell 的末尾不执行链接器的工作,它只是加载 dll,以便您可以访问那里的代码。
标签: c# powershell restsharp