“|DataDirectory|”在哪里定义?

50

这是一个关于 我的系统中那个文件在哪里? 的后续问题。

虽然 Stack Overflow 和网络上有很多相关的问题和答案,但是我找不到针对这个特定问题的答案。

一切都是默认设置,但是我找不到文件本身,

它不存在

|DataDirectory| 是从哪里定义的?

文件保存在哪里,甚至是否存在?如果不存在,发生了什么事情?

编辑:文件并没有位于 AppDomain.CurrentDomain.GetData("DataDirectory").ToString();,所有(零散)的答案都告诉我应该在那里。当我改变模型时,调试器会提示模型与表格不相等,所以它必须在某个地方。但是它不在那里

3个回答

75

|DataDirectory|并不是一个具体的文件。引用自一篇较早的MSDN文章:

默认情况下,|DataDirectory|变量将展开如下:

  • 对于放置在用户机器上的应用程序,这将是应用程序(.exe)文件夹。
  • 对于在ClickOnce下运行的应用程序,这将是由ClickOnce创建的特殊数据文件夹。
  • 对于Web应用程序,这将是App_Data文件夹。

在幕后,|DataDirectory|的值只是来自应用程序域上的属性。可以通过执行以下操作更改该值并覆盖默认行为:

AppDomain.CurrentDomain.SetData("DataDirectory", newpath)

关于您的模式不一致问题的进一步引用:

在使用本地数据库文件时需要知道的一件事是它们被视为任何其他内容文件。对于桌面项目,这意味着默认情况下,每次构建项目时,数据库文件将被复制到输出文件夹(即bin)。在按F5之后,它看起来会像以下这样保存在磁盘上:

 MyProject\Data.mdf

 MyProject\MyApp.vb

 MyProject\Bin\Debug\Data.mdf

 MyProject\Bin\Debug\MyApp.exe
在设计时,数据工具使用MyProject\Data.mdf。在运行时,应用程序将使用输出文件夹下的数据库。由于复制的原因,许多人认为应用程序没有将数据保存到数据库文件中。实际上,这只是因为涉及到两个数据文件的副本。当通过数据库浏览器查看模式/数据时,同样适用。工具使用项目中的副本,而不是bin文件夹中的副本。

3
当你的回答出现时,我已经打了一半了。研究得很充分! - JTMon
AppDomain.CurrentDomain.GetData("DataDirectory") 返回 NULL。 - monstro

19

|datadirectory| 算法位于 System.Data.dll 程序集中的内部 System.Data.Common.DbConnectionOptions 类中。以下是使用 ILSpy 显示的内容(请注意,现在可以在参考源代码库中找到该源代码:https://github.com/Microsoft/referencesource/blob/e458f8df6ded689323d4bd1a2a725ad32668aaec/System.Data.Entity/System/Data/EntityClient/DbConnectionOptions.cs):

internal static string ExpandDataDirectory(string keyword,
                                           string value,
                                           ref string datadir)
{
    string text = null;
    if (value != null && 
        value.StartsWith("|datadirectory|", StringComparison.OrdinalIgnoreCase))
    {
        string text2 = datadir;
        if (text2 == null)
        {
            // 1st step!
            object data = AppDomain.CurrentDomain.GetData("DataDirectory");
            text2 = (data as string);
            if (data != null && text2 == null)
                throw ADP.InvalidDataDirectory();

            if (ADP.IsEmpty(text2))
            {
                // 2nd step!
                text2 = AppDomain.CurrentDomain.BaseDirectory;
            }
            if (text2 == null)
            {
                text2 = "";
            }
            datadir = text2;
        }

        // 3rd step, checks and normalize
        int length = "|datadirectory|".Length;
        bool flag = 0 < text2.Length && text2[text2.Length - 1] == '\\';
        bool flag2 = length < value.Length && value[length] == '\\';
        if (!flag && !flag2)
        {
            text = text2 + '\\' + value.Substring(length);
        }
        else
        {
            if (flag && flag2)
            {
                text = text2 + value.Substring(length + 1);
            }
            else
            {
                text = text2 + value.Substring(length);
            }
        }
        if (!ADP.GetFullPath(text).StartsWith(text2, StringComparison.Ordinal))
            throw ADP.InvalidConnectionOptionValue(keyword);
    }
    return text;
}

默认情况下,它首先查找当前AppDomain中的数据(我认为没有定义“DataDirectory”数据),然后才能到达当前AppDomain的基本目录。其余部分大多是路径根和路径规范化的检查。


2
MSDN论坛上有一个类似但更简化的问题,它说:
默认情况下,|DataDirectory|指向您的应用程序文件夹(正如您在原始问题中自己发现的那样:指向App_Data)。
由于它只是到数据库的替换路径,因此您可以使用AppDomain.SetData自己定义路径。

Stack Overflow和互联网上有大量的问题和答案,但我找不到任何一个能回答这个特定问题的。 - user1555816

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接