在 Visual Studio 代码中使用 msys shell

Using msys shell in Visual Studio Code

我正在学习 Visual Studio 代码,因为我喜欢它的轻量级设计和灵活性。它有一个集成终端,可以 运行,我相信,任何 shell [see here]. I'd like to use it run the msys shell that I've been using lately. Setting the terminal to run another shell other than the default powershell.exe should be as simple as changing the settings as described [here]。但是,我按照 mingw.org.

上的建议,通过 运行 宁 msys.bat 文件来使用 msys shell

所以我的问题是,我需要将终端设置为 msys shell 的 .exe 文件在哪里?或者 运行 以这种方式在没有 .bat 的情况下使用 shell 是不可能的吗?谢谢!

根据 msys.bat 脚本,实际启动的可执行文件取决于您的 TTY 设置。默认设置使用本机命令提示符并启动 sh.exe 文件,您可以从以下代码片段中看到:

:startsh
if NOT EXIST %WD%sh.exe goto notfound
start %WD%sh --login -i
exit

要使其在 Visual Studio 代码中运行,您需要添加以下用户设置:

"terminal.integrated.shell.windows": "C:\MinGW\msys\1.0\bin\sh.exe",
"terminal.integrated.shellArgs.windows": ["--login", "-i"]

sh.exe 文件的路径可能会有所不同,具体取决于 MSYS 的安装位置。

编辑:(2019-01-20)

虽然以上仍然适用于 MSYS v1.0,但我已切换到 MSYS2 (https://www.msys2.org/)。您可以使用以下设置来设置您的 Visual Studio 代码以与 v1.0 一样使用 MSYS2(同样,您的安装位置可能与我的不同):

"terminal.integrated.shell.windows": "C:\msys64\usr\bin\bash.exe",
"terminal.integrated.shellArgs.windows": ["--login", "-i"]

为了加分,我们将修改一个环境变量,以便我们始终在当前目录中打开终端。有多种方法可以通过脚本等实现这一点。但是,在我看来,最简单的方法是使用 CHERE_INVOKING 环境变量。通过将此标志设置为 1,它将通知 shell 使用当前目录作为默认入口点。以下是有关如何启用此标志的完整教程:

  1. 按 windows 键并输入 run 并回车
  2. 在 运行 对话框中,键入以下内容:

    rundll32.exe sysdm.cpl,EditEnvironmentVariables
    

  3. 在打开的“环境变量”对话框中,添加一个名为 CHERE_INVOKING 的新用户变量并将其值设置为 1

在 Windows 系统中启用此标志后,它应该会自动从您调用 bash.exe 可执行文件的位置打开终端。对于 Visual Studio 代码,这将是您的根项目目录。享受!

上一个答案的扩展:

要让它在您当前的工作目录中打开,出于某种原因,它必须先 运行 通过本机 shell。我们可以使用 非常直观 PowerShell 包装器来设置 cd 并启动 bash 或另一个 shell.

这是让它为我工作的配置:

"terminal.integrated.shell.windows": "C:\WINDOWS\System32\WindowsPowerShell\v1.0\powershell.exe",
"terminal.integrated.shellArgs.windows": [
    "C:\msys64\usr\bin\sh.exe",
    "--login",
    "-i",
    "-c",
    "(\"cd \`\"``cygpath '{0}'``\`\"; /usr/bin/bash --login -i\" -f (Resolve-Path .).Path )"
],

您可以根据需要将 bash 替换为不同的 shell,例如 zsh

Bash 和 JSON 转义使用 \ 字符,但 PowerShell 使用 ` 代替,然后 bash 会尝试使用它来执行命令,所以要小心所有转义字符。

此外,您必须指定 PowerShell 二进制文件,而不是 built-in "PowerShell" shell。老实说,我不知道为什么。

Jonny Morril 的回答对我很有帮助。 设置时,随时会自动进入home文件夹。

Here 我找到了资源管理器菜单的有效解决方案。但是你不需要实现它。导入行是:

If you try it out, you will notice that it opens a new MSYS window, but it automatically goes to the home directry instead of the current directory you're in. To fix this you need to edit "C:\MinGW\msys.0\etc\profile". Find the cd "$HOME" line (probably the last line) and comment it out (by adding a # before it).

在 removing/comment-out 行之后,一切正常,没有任何解决方法,就像 Bryan K 的建议。

要在您的项目文件夹中打开 MSys,您只需

一个。在 Visual Code 的个人设置中添加以下设置(假设您的 Msys 文件夹是 C:\msys.0):

"terminal.integrated.shell.windows": "C:\msys\1.0\Run_MSYS.bat",

乙。将getcp.exe复制到MSys的bin文件夹中(即C:\msys.0\bin);你可以在这里找到它:https://github.com/msysgit/msysgit/blob/master/mingw/bin/getcp.exe

C。在您的 MSys 文件夹中创建文件 Run_MSYS.bat,如下所示:

@rem Do not use "echo off" to not affect any child calls.
@SETLOCAL
@SETLOCAL ENABLEEXTENSIONS

:: Figure out where msys's root folder. If you want, you could just add the folder in the line
:: below.
@set MSYSROOT=
@if "x%MSYSROOT%"=="x" @if exist "%~dp0msys.bat" @set MSYSROOT=%~dp0
@if "x%MSYSROOT%"=="x" @if exist "%~dp0.msys-root" @set /P MSYSROOT=<%~dp0.msys-root
@if "x%MSYSROOT%"=="x" (
@echo Could not locate your mysys root folder.
@set /P MSYSROOT=Location:
)
:: Read as MSYSROOT.trim()
@if not "x%MSYSROOT%"=="x" (
@for /f "tokens=* delims= " %%a in ("%MSYSROOT%") do @set MSYSROOT=%%a
@for /f "useback tokens=*" %%a in ('%MSYSROOT%') do @set MSYSROOT=%%~a
@if not "%MSYSROOT:~-1%"=="\" @set MSYSROOT=%MSYSROOT%\
)
:: Verify that root folder exists
@if not exist "%MSYSROOT%" (
@echo "%MSYSROOT%" is not a valid folder. Please check for .msys-root in %~dp0, or if you entered the path above, please rerun this script and select a valid folder.
@exit /B 1
) else (
@if not "%MSYSROOT%"=="%~dp0" @echo %MSYSROOT%>%~dp0.msys-root
)

:: Home Folder
:: If you'd prefer the home directory set to your C:\Users\Username folder, uncomment the two lines
:: below.
@rem @if not exist "%HOME%" @set HOME=%HOMEDRIVE%%HOMEPATH%
@rem @if not exist "%HOME%" @set HOME=%USERPROFILE%
@if not exist "%HOME%" @if not "%MSYSROOT%"=="" @set HOME=%MSYSROOT%home\%USERNAME%
@if not "x%WD%"=="x" @set WD=
@set PLINK_PROTOCOL=ssh
@if not exist "%WD%msys-1.0.dll" @set WD=%MSYSROOT%\bin\
@set MSYSCON=sh.exe

:: Default action, open msys and go to the current folder.
@set OLDCD=%CD%
@if not "x%OLDCD%"=="x" @set CURRCD=%CD%
:: Get the current console ("OEM") codepage.
@for /f %%i in ('"%MSYSROOT%bin\getcp.exe" -oem') do @set cp_oem=%%i
:: Get the current GUI ("ANSI") codepage.
@for /f %%i in ('"%MSYSROOT%bin\getcp.exe" -ansi') do @set cp_ansi=%%i
:: Set the console codepage to match the GUI codepage.
@chcp %cp_ansi% > nul < nul
@if not "x%OLDCD%"=="x" (
@"%MSYSROOT%bin\bash.exe" -l -i -c "cd \"$CURRCD\"; exec /bin/bash -rcfile ~/.bash_profile"
) else (
@"%MSYSROOT%bin\bash.exe" -l
)
:: Store the error level returned by bash.
@set ErrorLevel=%ErrorLevel%
:: Restore the original console codepage.
@chcp %cp_oem% > nul < nul
:: If we had a current directory at the store of the script, go back to it.
@if not "x%OLDCD%"=="x" chdir /D "%OLDCD%"

:: quit script with the current error level.
@exit /b %ErrorLevel%

这是(可能)在此处找到的脚本的较短版本:https://gist.github.com/juntalis/1291621

感谢 Juntalis 的精彩剧本!!

干杯

进一步完善 Bryan K 的回答:

我们将改为在终端配置文件下拉列表中添加 MSYS2 配置文件。 在 settings.json 中,在 "terminal.integrated.profiles.windows" 中,我们将为 MSYS2 添加一个新条目,例如:

"MSYS2": {
  "source": "PowerShell",
  "args": [
    "C:\msys64\usr\bin\bash.exe",
    "--login",
    "-i",
    "-c",
    "(\"cd \`\"``cygpath '{0}'``\`\"; /usr/bin/bash --login -i\" -f (Resolve-Path .).Path )"
}

更改路径以匹配您的 MSYS2 安装(以上为默认路径)。

现在终端下拉菜单中会有一个 MSYS2 选项,它将在当前工作目录中打开。

今天我遇到了同样的问题,在当前日期(24/10/2021),这是对我来说可行的解决方案: 在文件 settings.json 中你应该有这些行:

"terminal.integrated.env.windows": {
    "CHERE_INVOKING": "1" // open mysys terminal at the current path
},
"terminal.external.windowsExec": "C:\msys64\mysys2.exe",
"terminal.integrated.defaultProfile.windows": "MYSYS",  // I am using default MYSYS(this line is optional)
"terminal.integrated.profiles.windows": {
    "MYSYS": {
        "path": "C:\msys64\usr\bin\bash.exe",
        "args": [
            "--login",
            "-i"
        ]
    }
}

根据MSYS terminals,我们可以这样使用:

    "terminal.integrated.profiles.windows": {
        "msys mingw64": {
            "path": "C:/msys64/msys2_shell.cmd",
            "args": [
                "-defterm",
                "-here",
                "-no-start",
                "-mingw64"
            ]
        }
    },

这将启动 msys mingw64。要启动其他 shell,只需将 -mingw64 更改为 -mingw32-msys.