【问题标题】:Creating an empty directory (NSIS)创建一个空目录 (NSIS)
【发布时间】:2015-01-27 11:30:47
【问题描述】:

如何通过 NSIS 2.46 做到这一点?

我知道这可能是一个愚蠢的问题,但是我到底要如何创建一个空目录并检查错误呢?

我这样做:

ClearErrors
CreateDirectory $R1
${If} ${Errors} 
  DetailPrint "failed"
  MessageBox mb_IconStop|mb_TopMost|mb_SetForeground "Can not create folder $R1"
  Abort
${Else}
  DetailPrint "done"
${EndIf}

如果变量 $R1 是

  • “c:\test” - 完成
  • “c:\con” - 失败(“con” - 在 Windows 上保留)
  • "qwer:\test2" - 完成
  • “qwer\test3” - 完成(不带“:”)

为什么“test2”和“test3”没有错误?

更新: 如何使它成为一个错误?

【问题讨论】:

    标签: windows installation nsis error-checking create-directory


    【解决方案1】:

    我决定:

    ClearErrors
    CreateDirectory $R1
    ${If} ${Errors} 
    ${OrIfNot} ${FileExists} "$R1\*.*"
      DetailPrint "failed"
      MessageBox mb_IconStop|mb_TopMost|mb_SetForeground "Can not create folder $R1"
      Abort
    ${Else}
      DetailPrint "done"
    ${EndIf}
    

    有更多想法?

    【讨论】:

      【解决方案2】:

      为了检查错误,您应该检查错误标志,这是正确的。我认为问题是你应该使用引号:

      CreateDirectory "$R1"
      

      【讨论】:

        【解决方案3】:

        NSIS 做了一些不幸的(恕我直言)路径修改,并且只接受 : 作为第二个字符,否则它会被默默地剥离。这意味着"qwer\test2""qwer:\test2" 在运行时被同等对待。您可以通过将其复制到特殊路径寄存器之一来验证这一点:

        !macro TestNsisPathMangling p
        Push $InstDir
        StrCpy $InstDir "${p}"
        DetailPrint "Old=${p}"
        DetailPrint "New=$InstDir"
        Pop $InstDir
        !macroend
        
        !insertmacro TestNsisPathMangling "qwer\test2"
        !insertmacro TestNsisPathMangling "qwer:\test2"
        

        这给我们留下了"qwer\test2",这是一个相对路径,在调用 CreateDirectory 时,它们的正式名称是 not supported。如果你在 NSIS 3 中尝试这个,你应该得到:

        CreateDirectory:不支持相对路径

        编辑:

        如果路径是用户输入的,可以调用Windows函数GetFullPathName获取绝对/完整路径:

        Push "qwer\test3"
        System::Call 'KERNEL32::GetFullPathName(ts,i${NSIS_MAX_STRLEN},t.r1,t)i.r0'
        ${If} $0 <> 0
            DetailPrint "GetFullPathName=$1"
        ${Else}
            DetailPrint "GetFullPathName failed"
        ${EndIf}
        

        【讨论】:

        • @AndreiKrasutski 这是什么意思?只需使用完整路径就可以了。
        • 变量 $R1 在页面自定义中设置用户,所以它可以设置一个错误的目录,但我必须检查。
        【解决方案4】:

        documentation for CreateDirectory - 相当不负责任地 - 明确表示 error flag is set 让偶尔的 NSIS 脚本编写者不清楚这意味着什么。

        毫不奇怪,NSIS 中的错误处理也被记录在 very sparsely... 但幸运的是,如果您仔细阅读 cmets,它们确实解释了如何捕获错误。

        如果设置了会跳转到[first param],否则跳转到[second param]

        请特别注意文档中的 goto 一词,它是对 GOTO line jumping 的回归。

        ClearErrors
        CreateDirectory $R1
        IfErrors 0 +2
        Call ErrorHandler
        

        不明显的是+2 JUMPS OVER 错误处理程序。现在可以推断0 将转到NEXT LINE——错误处理程序。

        鉴于:ErrorHandler 在您的脚本中的某处定义,上述示例应正确处理错误,可以用您喜欢的任何逻辑替换它。

        我推荐; Commenting heavily,因为如果您不每天使用这种脚本语言,可能会难以阅读。

        【讨论】:

          猜你喜欢
          • 2014-04-26
          • 1970-01-01
          • 2021-09-19
          • 2022-09-28
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多