You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Haskell的optparse-applicative中为子命令设置同义词

解决方案

你可以借助optparse-applicative库的内置能力实现需求,既复用全部逻辑,又不会在帮助里出现重复条目,具体实现方式如下:


完整修改后的可运行代码

#!/usr/bin/env stack
-- stack --resolver lts-18.17 script --package optparse-applicative

import Options.Applicative
import Data.Semigroup ((<>))

data Options = CmdGreet GreetArgs | CmdGroot GreetArgs

newtype GreetArgs = GreetArgs String

main :: IO ()
main = do
    cmdOpts <- customExecParser (prefs showHelpOnEmpty) (info optParser fullDesc)
    runCmd cmdOpts

optParser :: Parser Options
optParser = subparser (
    command "greet" (info (CmdGreet <$> sample) (progDesc "Print greeting 1")) <>
    -- 注册别名gruut,复用完全相同的parser,加internal修饰符让它不在帮助列表中显示
    command "gruut" (info (CmdGreet <$> sample) (internal <> progDesc "Alias for greet")) <>
    command "groot" (info (CmdGroot <$> sample) (progDesc "Print greeting 2"))
    -- 自定义帮助的命令列表展示,实现greet|gruut的显示效果
    ) & help "Available commands:\n\
             \  greet|gruut              Print greeting 1\n\
             \  groot                    Print greeting 2"

runCmd :: Options -> IO ()
runCmd o = case o of
    CmdGreet opts -> greet opts
    CmdGroot opts -> groot opts

greet :: GreetArgs -> IO ()
greet (GreetArgs h) = putStrLn $ "Hello, " ++ h ++ "!"

groot :: GreetArgs -> IO ()
groot (GreetArgs h) = putStrLn $ "Howdy, " ++ h ++ "!"

sample :: Parser GreetArgs
sample = GreetArgs <$> strArgument ( metavar "TARGET" )

更简洁的高版本方案

如果你使用0.16及以上版本的optparse-applicative,可以用库内置的commandAlias函数进一步简化代码:

optParser :: Parser Options
optParser = subparser (
    command "greet" (info (CmdGreet <$> sample) (progDesc "Print greeting 1")) <>
    commandAlias "gruut" "greet" <> -- 直接声明gruut是greet的别名,无需重复写parser
    command "groot" (info (CmdGroot <$> sample) (progDesc "Print greeting 2"))
    ) & help "Available commands:\n\
             \  greet|gruut              Print greeting 1\n\
             \  groot                    Print greeting 2"

效果验证

  • 运行./opt_ex.hs greet John和./opt_ex.hs gruut John都会返回Hello, John!,行为完全一致
  • 直接运行./opt_ex.hs查看帮助,输出完全符合你期望的格式,没有重复的命令条目

内容的提问来源于stack exchange,提问作者nevrome

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.24 22:24:05