【问题标题】:PowerShell function return best practicesPowerShell 函数返回最佳实践
【发布时间】:2015-12-13 13:52:57
【问题描述】:

我有一个关于 PowerShell 中关于函数返回值的最佳实践的两部分问题。我有许多复杂的函数,至少需要返回成功或失败,加上一组日志项,有时只是失败日志,有时是成功和失败日志。有时函数也需要返回一个对象。我现在使用 $return 元组作为哈希表来执行此操作。所以我可能在函数的末尾有这样的东西

@{
   success = $success
   log = $log
}

使用可能看起来像这样

$functionReturn = Function
if $functionReturn.success {
 stuff
} else {
 Write-Log $functionReturn.log
}

我只是好奇这里是否有更好的模式可以使用,或者这种方法是否相当可靠。如果是,是否有任何命名约定等标准?作为一般规则,我尽量不重用“临时”变量,因此我不会一遍又一遍地使用 $functionReturn,而是适当地命名变量,因此真实世界的函数调用可能是$readXML = Read-XML $xmlPath。 非常感谢您对此处的最佳实践提出任何建议。

此外,我还看到了创建自定义对象来执行相同操作的参考,但从代码的角度来看,哈希表似乎更清晰(更简单)。是否有任何理由使用自定义对象而不是哈希表?例如,当返回一个大的日志数组加上一个大的 XML 对象时,哈希表是否有大小限制?或者哈希表可以返回的内容是否有限制?还是真的是六分之一,六分之一?

【问题讨论】:

  • 答案是为你的情况做任何真正有效的事情。话虽如此,使用对象是一种非常好的结构化方法。另外,请记住 return 关键字是多余的,因为返回了函数的 all 输出。至于命名约定,答案是任何描述性足够的东西,以便其他读者知道发生了什么。 $r 很糟糕,因为它没有任何意义。 $functionReturn$result 就足够了。
  • 马特,关于“使用有效的东西”的观点。也许我应该改写为“是否存在哈希表不起作用的情况”,主要是因为我确实喜欢一致性,所以假设存在哈希表会失败的地方,并假设自定义对象没有性能问题,我会选择到处使用自定义对象。然而,如果一个哈希表可以一直工作,并且使用它没有性能损失,我会在任何地方使用哈希表,因为设置更简单。但是,您说对象非常“结构化”。这与哈希表有什么不同?
  • 这主要是个人喜好或我认为的实际使用驱动。当我想使用 ContainsKey 之类的方法时,我会使用哈希表。 PowerShell 旨在处理更复杂的对象,因此我经常使用[pscustomobject]@{}。如果在这方面存在功能限制,我还没有遇到过。 (它们很容易存在。)
  • 如果您确实使用元组,请注意几点 1) 小心 Powershell 在管道中展开数组。如果下游管道命令需要一个数组,而您只返回一个普通数组,则下游将不会获取该数组 - 他们将分别获取数组中的每个对象。 2) 这种语法对于返回元组的函数调用者来说很方便:$xmlObj, $otherThing = do-myThing $arg1 $arg2。 3)最后,当您说 6 of 1 vs 1/2 打时,这取决于您的情况:a)性能有问题吗? b) 多大:1MB 还是 100MB? c) 脚本通常会运行多长时间?

标签: function powershell return-value


【解决方案1】:

如果需要通知调用者失败,我会抛出异常。 IMO 一个函数只有在实现状态检查时才应该返回一个布尔值,即如果布尔值是实际数据。或者如果语言不支持异常处理。

function Check-Something {
  if ($someCondition) {
    $true
  } else {
    $false
  }
}

如果您需要处理错误情况,我不会以与返回有效数据相同的方式返回错误信息。我会在函数内部进行状态记录以及非致命错误的记录,并为致命错误抛出异常。

function Do-Something {
  ...
  Write-Log 'regular log message'
  ...
  if ($somethingUnimportantFailed) {
    # log non-fatal error and continue
    Write-ErrorLog 'unimportant failure'
  }
  ...
  if ($somethingWentTeriblyWrong) {
    # abort what we're doing right now and notify caller
    throw 'error information here'
  }
  ...
  Write-Log 'other regular log message'
  ...
}

try {
  $returnedData = Do-Something
} catch {
  Write-ErrorLog $_.Exception.Message
  # more error handling here
}

一般来说,如果某些东西可以在函数内部处理,我认为它应该在函数内部处理。如果失败必须由调用者处理,我只会将有关失败的信息传递回调用者。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-07-23
    • 1970-01-01
    • 1970-01-01
    • 2022-06-15
    • 2021-11-14
    • 2018-12-22
    • 2015-07-27
    • 1970-01-01
    相关资源
    最近更新 更多