アプリケーションデータ保存場所の取得

2020-03-25

Windows7のVirtualStoreが登場する前は、
アプリケーションデータをEXEと同ディレクトリに設置しすることで、
アプリケーションを削除したい際、ディレクトリごと削除するだけで
環境を汚さずに処理することができた。

しかしVirtualStore実装以降、ProgramFilesディレクトリにアプリケーションを設置した場合、
最新のデータはAppDataに格納されてしまい、ProgramFilesに保存されたデータを手で変更したとしても、
AppDataのデータで上書きされてしまう問題が発生する。

アプリケーションを、 ProgramFilesに設置しようが、他のディレクトリに設置しようが、
AppDataにデータを格納してしまえば良いという考え方もあるが、
なるべくであれば、ProgramFiles以外の場合はEXEと同じディレクトリに設置したいと考え、
下記のようなコードでディレクトリパス取得を行った。

using System;
using System.IO;
using System.Reflection;

namespace UserClass
{
    public static class AppDataPath
    {
        /// <summary>
        /// アプリケーションデータディレクトリの取得
        /// (VirtualStore考慮)
        /// </summary>
        /// <returns></returns>
        public static string GetAppDataPath()
        {
            string strPath = "";

            try
            {
                // EXEのあるディレクトリを格納
                strPath = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);

                if (Environment.Is64BitOperatingSystem)
                {
                    // 64BitOS

                    if ((strPath.IndexOf(Environment.GetEnvironmentVariable("ProgramFiles(x86)")) >= 0) ||
                        (strPath.IndexOf(Environment.GetEnvironmentVariable("ProgramW6432")) >= 0))
                    {
                        // ProgramFilesディレクトリの場合はLOCALAPPDATA(VirtualStore)を返す
                        strPath = GetLocalApplicationData();
                    }
                }
                else
                {
                    // 32BitOS

                    if (strPath.IndexOf(Environment.GetEnvironmentVariable("ProgramFiles")) >= 0)
                    {
                        // ProgramFilesディレクトリの場合はLOCALAPPDATA(VirtualStore)を返す
                        strPath = GetLocalApplicationData();
                    }
                }

                // ディレクトリが無ければ構築
                if (Directory.Exists(strPath) == false)
                    Directory.CreateDirectory(strPath);
            }
            catch (Exception ex)
            {
                throw (ex);
            }

            return strPath;
        }

        /// <summary>
        /// %LOCALAPPDATA%[会社名][ソフトウェア名]
        /// </summary>
        /// <returns></returns>
        private static string GetLocalApplicationData()
        {
            string strPath = "";

            AssemblyTitleAttribute asmttl = (AssemblyTitleAttribute)Attribute.GetCustomAttribute(Assembly.GetExecutingAssembly(), typeof(AssemblyTitleAttribute));
            AssemblyCompanyAttribute asmcmp = (AssemblyCompanyAttribute)Attribute.GetCustomAttribute(Assembly.GetExecutingAssembly(), typeof(AssemblyCompanyAttribute));

            strPath = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData);
            strPath = Path.Combine(strPath, asmcmp.Company);
            strPath = Path.Combine(strPath, asmttl.Title);

            return strPath;
        }
    }
}