Что приводит к тому, что user.config очищается?И как восстановить без перезагрузки? - PullRequest
19 голосов
/ 05 марта 2012

Я заметил, что на нескольких машинах файл user.config моего приложения каким-то образом поврежден и при открытии пуст. Я не могу понять, почему это произошло. Есть ли что-то общее, что могло бы вызвать это? Любой способ безопасно предотвратить это?

Мой второй вопрос: как мне восстановить состояние? Я ловлю исключение и удаляю файл user.config, но не могу найти способ восстановить конфигурацию без перезапуска приложения. Все, что я делаю с объектом Properties, вызывает следующую ошибку:

«Не удалось инициализировать систему конфигурации»

Сброс, перезагрузка и обновление ничего не делают для решения проблемы.

Вот мой код для удаления после исключения:

catch (System.Configuration.ConfigurationErrorsException ex)
{
    string fileName = "";
    if (!string.IsNullOrEmpty(ex.Filename))
        fileName = ex.Filename;
    else
    {
        System.Configuration.ConfigurationErrorsException innerException = ex.InnerException as System.Configuration.ConfigurationErrorsException;
        if (innerException != null && !string.IsNullOrEmpty(innerException.Filename))
            fileName = innerException.Filename;
    }
    if (System.IO.File.Exists(fileName))
        System.IO.File.Delete(fileName);
}

Ответы [ 4 ]

18 голосов
/ 22 сентября 2015

У нас была эта проблема в нашем приложении - и я не смог выяснить ПОЧЕМУ (я предположил, что я писал в Properties.Settings слишком часто, но я не уверен). Во всяком случае, мой обходной путь для ниже. Ключ должен удалить поврежденный файл и вызвать Properties.Settings.Default.Upgrade()

try
{
     ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.PerUserRoamingAndLocal);
}
catch (ConfigurationErrorsException ex)
{
    string filename = ex.Filename;
    _logger.Error(ex, "Cannot open config file");

    if (File.Exists(filename) == true)
    {
        _logger.Error("Config file {0} content:\n{1}", filename, File.ReadAllText(filename));
        File.Delete(filename);
        _logger.Error("Config file deleted");
        Properties.Settings.Default.Upgrade();
        // Properties.Settings.Default.Reload();
        // you could optionally restart the app instead
    }
    else
    {
        _logger.Error("Config file {0} does not exist", filename);
    }
}
4 голосов
/ 06 июня 2014

Это может быть немного поздно, но я провел еще несколько исследований по этому вопросу. Файл user.config, кажется, поврежден по неизвестной причине и не позволяет запускать приложение. Вы можете поместить небольшую логику try / catch в ваш app.xaml.cs и проверить, когда он запускается, чтобы убедиться, что эта проблема обнаружена в источнике. Когда приложение запускается и пытается программно перезагрузить файл settings.default и не удается, оно перейдет к исключению, дающему пользователю возможность удалить файл.

try {
Settings.Default.Reload();
} 
catch ( ConfigurationErrorsException ex ) 
{ 
  string filename = ( (ConfigurationErrorsException)ex.InnerException ).Filename;

if ( MessageBox.Show( "<ProgramName> has detected that your" + 
                      " user settings file has become corrupted. " +
                      "This may be due to a crash or improper exiting" + 
                      " of the program. <ProgramName> must reset your " +
                      "user settings in order to continue.\n\nClick" + 
                      " Yes to reset your user settings and continue.\n\n" +
                      "Click No if you wish to attempt manual repair" + 
                      " or to rescue information before proceeding.",
                      "Corrupt user settings", 
                      MessageBoxButton.YesNo, 
                      MessageBoxImage.Error ) == MessageBoxResult.Yes ) {
    File.Delete( filename );
    Settings.Default.Reload();
    // you could optionally restart the app instead
} else
    Process.GetCurrentProcess().Kill();
    // avoid the inevitable crash
}

Кредит - http://www.codeproject.com/Articles/30216/Handling-Corrupt-user-config-Settings

Надеюсь, это кому-нибудь поможет:)

4 голосов
/ 07 мая 2012

У меня похожая ситуация. Для меня, как только я удаляю неверный файл конфигурации, я просто продолжаю приложение. При следующем доступе к настройкам будут использоваться настройки приложения по умолчанию.

0 голосов
/ 08 февраля 2019

Вот как мы решили проблему. Эта функция должна называться ДО ЛЮБОГО использования Properties.Settings ... В противном случае вы застряли (как описано в tofutim и avs099).

private bool CheckSettings()
    {
        var isReset = false;
        string filename = string.Empty;

        try
        {
            var UserConfig = System.Configuration.ConfigurationManager.OpenExeConfiguration(System.Configuration.ConfigurationUserLevel.PerUserRoamingAndLocal);
            filename = UserConfig.FilePath;
            //"userSettings" should be replaced here with the expected label regarding your configuration file
            var userSettingsGroup = UserConfig.SectionGroups.Get("userSettings");
            if (userSettingsGroup != null && userSettingsGroup.IsDeclared == true)
                filename = null; // No Exception - all is good we should not delete config in Finally block
        }
        catch (System.Configuration.ConfigurationErrorsException ex)
        {
            if (!string.IsNullOrEmpty(ex.Filename))
            {
                filename = ex.Filename;
            }
            else
            {
                var innerEx = ex.InnerException as System.Configuration.ConfigurationErrorsException;
                if (innerEx != null && !string.IsNullOrEmpty(innerEx.Filename))
                {
                    filename = innerEx.Filename;
                }
            }
        }
        catch (System.ArgumentException ex)
        {
            Console.WriteLine("CheckSettings - Argument exception");
        }
        catch (SystemException ex)
        {
            Console.WriteLine("CheckSettings - System exception");

        }
        finally
        { 
            if (!string.IsNullOrEmpty(filename))
            {
                if (System.IO.File.Exists(filename))
                {
                    var fileInfo = new System.IO.FileInfo(filename);
                    var watcher
                         = new System.IO.FileSystemWatcher(fileInfo.Directory.FullName, fileInfo.Name);
                    System.IO.File.Delete(filename);
                    isReset = true;
                    if (System.IO.File.Exists(filename))
                    {
                        watcher.WaitForChanged(System.IO.WatcherChangeTypes.Deleted);
                    }

                    try
                    {
                        Properties.Settings.Default.Upgrade();                          
                    } catch(SystemException ex)
                    {
                        Console.WriteLine("CheckSettings - Exception" + ex.Message);
                    }
                }
            } 
        }
        return isReset;
    }
...