Frage

Ok, so zu erklären; Ich entwickle ein System, das einen Stromausfall an einem beliebigen Punkt in der Zeit leiden kann, einen Punkt, den ich testen bin direkt, nachdem ich eine Datei aus einer Stream mit geschrieben habe. Der folgende Code:

// Write the updated file back out to the Shell directory.
using (StreamWriter shellConfigWriter =
        new StreamWriter(@"D:\xxx\Shell\Config\Game.cfg.bak"))
{
    for (int i = 0; i < configContents.Count; i++)
    {
        shellConfigWriter.WriteLine(configContents[i]);
    }
    shellConfigWriter.Close();
}

FileInfo gameCfgBackup = new FileInfo(@"D:\xxx\Shell\Config\Game.cfg.bak");
gameCfgBackup.CopyTo(@"D:\xxx\Shell\Config\Game.cfg", true);

Schreibt den Inhalt der shellConfigWriter (a List von Strings) in eine Datei als Zwischenspeicher verwendet wird, dann wird es über das Original kopiert. Jetzt, nach diesem Code der Leistung ausgeführt wird verloren beendet ist, beim Start wieder nach oben die Datei Game.cfg existiert und ist die richtige Größe, ist aber völlig leer. Zuerst dachte ich, dass dies zurückzuführen ist auf der Festplatte aktiviert Write-Caching ist, aber auch mit ihm weg kommt es immer noch (wenn auch weniger häufig).

Irgendwelche Ideen wäre sehr willkommen!

Update: Ok, so dass nach den .Close() Aussagen zu entfernen und rufen .Flush() nach jedem Schreibvorgang beenden die Dateien immer noch leer. Ich könnte noch einen Schritt weiter gehen und eine Sicherungskopie der Originaldatei erstellen, bevor Sie die neuen zu erstellen, und dann habe ich genug Backups eine Integritätsprüfung zu tun, aber ich glaube nicht, es wird das zugrunde liegende Problem zu lösen helfen ( dass, wenn ich ihm sagen zu, bündig zu schreiben und eine Datei schließen ... es ist nicht!).

War es hilfreich?

Lösung

Halten Sie das Betriebssystem von dem Ausgang Pufferung des FileOptions Parameter des FileStream Objekts Konstruktor:

    using (Stream fs = new FileStream(@"D:\xxx\Shell\Config\Game.cfg.bak", FileMode.Create, FileAccess.Write, FileShare.None, 0x1000, FileOptions.WriteThrough))
    using (StreamWriter shellConfigWriter = new StreamWriter(fs))
    {
        for (int i = 0; i < configContents.Count; i++)
        {
            shellConfigWriter.WriteLine(configContents[i]);
        }
        shellConfigWriter.Flush();
        shellConfigWriter.BaseStream.Flush();
    }

Andere Tipps

Zunächst einmal müssen Sie es shellConfigWriter.Close() nicht nennen. Die using Anweisung kümmern sich um sie. Was Sie vielleicht stattdessen zum Schutz vor Stromausfall Anruf shellConfigWriter.Flush() tun wollen.


Aktualisieren
Etwas anderes möchten Sie vielleicht zu prüfen, ist, dass, wenn ein Stromausfall wirklich passieren kann, jeder Zeit, in der Mitte eines Schreib passieren könnte, so dass nur einige der Bytes in einer Datei zu machen. Es gibt wirklich keinen Weg, das zu stoppen.

gegen diese Szenarien zu schützen, ein gemeinsames Verfahren ist Zustand / Zustand Flag-Dateien zu verwenden. Sie verwenden die Existenz oder Nicht-Existenz auf dem Dateisystem einer Null-Byte-Datei mit einem bestimmten Namen Ihrem Programm zu sagen, wo wieder abholen, wenn es wieder aufnimmt. Dann sind Sie nicht erstellen oder die Dateien zerstören, die einen bestimmten Zustand auslösen, bis Sie sicher Sie haben diesen Zustand erreicht und vollendet die vorherige.

Der Nachteil hierbei ist, dass es bedeuten könnte eine Menge Arbeit weg von Zeit zu Zeit zu werfen. Aber der Vorteil ist, dass es das Funktionsteil des Codes bedeutet, sieht aus wie normal:. Es gibt sehr wenig zusätzliche Arbeit zu tun, das System ausreichend robust zu machen

Sie möchten AutoFlush = true; einstellen

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top