如何检查/检测在我的 VSPackage 下运行的 Visual Studio 版本?
我无法从注册表中获取,因为计算机可能安装了多个版本,所以我想有一个 API 可以获取它。
有人知道如何使用 C# 从托管的 Visual Studio 包中获取它吗?
如何检查/检测在我的 VSPackage 下运行的 Visual Studio 版本?
我无法从注册表中获取,因为计算机可能安装了多个版本,所以我想有一个 API 可以获取它。
有人知道如何使用 C# 从托管的 Visual Studio 包中获取它吗?
您可以尝试通过自动化 DTE 对象获取版本。在 MPF 中,您可以通过以下方式获得它:
EnvDTE.DTE dte = (EnvDTE.DTE)Package.GetGlobalService(typeof(EnvDTE.DTE));
还有一些其他相关的东西可以检索 DTE 对象 - 通过Project.DTE ,如果您为 DTE 获得空值,也请阅读此线程。
然后您可以使用DTE.Version 属性获取版本。
也可以在 Carlos Quintero (VS addin ninja) 网站HOWTO: Detect installed Visual Studio editions, packages or service packs上找到有用的信息
最后我写了一个类来检测 Visual Studio 版本。测试和工作:
public static class VSVersion
{
static readonly object mLock = new object();
static Version mVsVersion;
static Version mOsVersion;
public static Version FullVersion
{
get
{
lock (mLock)
{
if (mVsVersion == null)
{
string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "msenv.dll");
if (File.Exists(path))
{
FileVersionInfo fvi = FileVersionInfo.GetVersionInfo(path);
string verName = fvi.ProductVersion;
for (int i = 0; i < verName.Length; i++)
{
if (!char.IsDigit(verName, i) && verName[i] != '.')
{
verName = verName.Substring(0, i);
break;
}
}
mVsVersion = new Version(verName);
}
else
mVsVersion = new Version(0, 0); // Not running inside Visual Studio!
}
}
return mVsVersion;
}
}
public static Version OSVersion
{
get { return mOsVersion ?? (mOsVersion = Environment.OSVersion.Version); }
}
public static bool VS2012OrLater
{
get { return FullVersion >= new Version(11, 0); }
}
public static bool VS2010OrLater
{
get { return FullVersion >= new Version(10, 0); }
}
public static bool VS2008OrOlder
{
get { return FullVersion < new Version(9, 0); }
}
public static bool VS2005
{
get { return FullVersion.Major == 8; }
}
public static bool VS2008
{
get { return FullVersion.Major == 9; }
}
public static bool VS2010
{
get { return FullVersion.Major == 10; }
}
public static bool VS2012
{
get { return FullVersion.Major == 11; }
}
}
我认为以下代码更好:
string version = ((EnvDTE.DTE) ServiceProvider.GlobalProvider.GetService(typeof(EnvDTE.DTE).GUID)).Version;
要获得包含补丁号的完整语义版本,例如“15.9.6”,DTE.Version
文件版本和文件版本都没有提供足够的信息。
我在新的托管项目系统(https://github.com/dotnet/project-system)中找到了一个解决方案,该解决方案似乎至少在 VS2017 中有效。
基本上,它使用的IVsAppId
是您需要声明的 COM 接口,就像在这个文件中一样。(您基本上可以按原样复制该文件。)
一旦你这样做了,你需要IVsAppId
通过服务提供者以通常的方式获得实现,并调用GetProperty
方法VSAPropID.VSAPROPID_ProductSemanticVersion
(枚举也在链接文件中定义):
var vsAppId = serviceProvider.GetService<IVsAppId>(typeof(SVsAppId));
vsAppId.GetProperty((int)VSAPropID.VSAPROPID_ProductSemanticVersion, out var semanticVersionObj);
上面示例中的semanticVersionObj
将包含一个字符串,格式为15.9.6+28307.344
. 获取之前的部分+
(有时-
)会为您提供语义版本:15.9.6
.
顺便说一句:它在这里用于托管项目系统。
(MS 将新项目系统代码开源真是太好了。它提供了很好的信息来源,您还可以在其中找到有用的模式。)
@gaspar-nagy 答案提供了最精确的版本。但是,它可以进一步增强。就像您需要添加IVsAppId
/SVsAppId
接口声明的答案建议一样,获取版本的代码也几乎相同。但是,您需要使用VSAPROPID_ProductDisplayVersion
枚举值而不是VSAPROPID_ProductSemanticVersion
来自VSAPropID
枚举:
var vsAppId = serviceProvider.GetService<IVsAppId>(typeof(SVsAppId));
vsAppId.GetProperty((int)VSAPropID.VSAPROPID_ProductDisplayVersion, out var versionObj);
我的 VS 16.9.4 的 @gaspar-nagy 答案的语义版本是“16.9.4+31205.134”,需要进一步解析。但是这个显示版本是用户友好的,它的版本是“16.9.4”。
UPDATE:
One important thing I've discovered recently is that in case of preview VS the version string in my answer will look something like 16.11.0 Preview 3.0
. It may be important if you pass the obtained raw version string without any extra processing to some other APIs like System.Version
constructor.
var shell = _package.GetService(typeof(SVsShell)) as IVsShell;
shell.GetProperty((int)__VSSPROPID5.VSSPROPID_ReleaseVersion, out object ver);
return ver.ToString();