2010-11-03 22 views
1

Je construis une application Windows Phone 7 dans Silverlight. J'ai de la difficulté à utiliser IsolatedStorageFile.Difficulté avec IsolatedStorageFile

La méthode suivante est censé écrire des données dans un fichier:

private static void writeToFile(IList<Story> stories) 
    { 
     IsolatedStorageFile storage = IsolatedStorageFile.GetUserStoreForApplication(); 
     using (IsolatedStorageFileStream stream = storage.OpenFile(STORIES_FILE, FileMode.Append)) 
     { 
      using (StreamWriter writer = new StreamWriter(stream)) 
      { 
       StringBuilder toJson = new StringBuilder(); 

       IList<StoryJson> storyJsons = (from story in stories 
               where !storageStories.Contains(story) 
               select story.ToStoryJson()).ToList(); 

       writer.Write(JsonConvert.SerializeObject(storyJsons)); 
      } 

     } 

#if DEBUG 
      StreamReader reader = new StreamReader(storage.OpenFile(STORIES_FILE, FileMode.Open)); 
      string contents = reader.ReadToEnd(); 
#endif 
     } 

Le DEBUG à la fin est pour moi de vérifier que les données sont effectivement en cours d'écriture. J'ai vérifié que c'est. Cette méthode est appelée 6 fois et plus. Chaque fois, plus de données sont ajoutées.

Cependant, quand je vais lire les données, le seul JSON que je reçois est celui que j'ai écrit en un appel de writeToFile(). Voici ma méthode pour lire:

private static IList<Story> storageStories; 
    private static IList<Story> readFromStorage() 
    { 
     if (storageStories != null) 
     { 
      return storageStories; 
     } 

     IsolatedStorageFile storage = IsolatedStorageFile.GetUserStoreForApplication(); 

     if (! storage.FileExists(STORIES_FILE)) 
     { 
      storage.CreateFile(STORIES_FILE); 
      storageStories = new List<Story>(); 
      return storageStories; 
     } 

     string contents; 
     using (IsolatedStorageFileStream stream = storage.OpenFile(STORIES_FILE, FileMode.OpenOrCreate)) 
     { 
      using (StreamReader reader = new StreamReader(stream)) 
      { 
       contents = reader.ReadToEnd(); 
      } 
     } 

     JsonSerializer serializer = new JsonSerializer(); 
     storageStories = JArray.Parse(contents).Select(storyData => storyOfJson(serializer, storyData)).ToList(); 
     return storageStories; 
    } 

Que pourrais-je faire mal ici? Est-ce que j'écris mal dans le fichier? Je suis assez sûr que les seules données qui peuvent être relues sont de la première écriture.

Mise à jour: J'ai ajouté deux Flush() appels, mais il se bloque:

private static void writeToFile(IList<Story> stories) 
     { 
      IsolatedStorageFile storage = IsolatedStorageFile.GetUserStoreForApplication(); 
      using (IsolatedStorageFileStream stream = storage.OpenFile(STORIES_FILE, FileMode.Append)) 
      { 
       using (StreamWriter writer = new StreamWriter(stream)) 
       { 
        StringBuilder toJson = new StringBuilder(); 

        IList<StoryJson> storyJsons = (from story in stories 
                where !storageStories.Contains(story) 
                select story.ToStoryJson()).ToList(); 

        writer.Write(JsonConvert.SerializeObject(storyJsons)); 
        writer.Flush(); 
       } 
       // FAILS 
       // "Cannot access a closed file." {System.ObjectDisposedException} 

       stream.Flush(); 
      } 
     } 

Si je commente le stream.Flush() mais laisse writer.Flush(), j'ai le même problème.

Mise à jour 2: J'ai ajouté des instructions d'impression. On dirait que tout devient sérialisé:

Serializing for VID 43 
Serializing for VID 17 
Serializing for VID 6 
Serializing for VID 33 
Serializing for VID 4 
Serializing for VID 5 
Serializing for VID 3 

Mais seul le premier jeu est en fait collationnement:

Deserializing stories with vid: 43 

Je le test quelques fois. Je suis à peu près sûr que seul le premier élément est relu.

Répondre

0

À première vue, il semble que vos données de flux ne soient pas vidées sur le disque.

Vous pensez probablement que le bloc using va effectuer un vidage quand il Disposes le flux. Cependant, j'ai trouvé que ce n'est pas toujours le cas et parfois il est préférable de forcer un Flush() à la fin. Je me souviens récemment dans une base de code que nous avons reçu d'une équipe de Microsoft pour porter à WP7 qu'ils forçaient un Flush. Je l'ai interrogé initialement, en pensant que le Dispose devrait gérer cela, mais comme il était fonctionnant et nous étions sur une courte échéance, je n'ai pas enquêté plus loin.

Donnez-aller, voir ce qui se passe ... :)

+0

writer.Dispose() J'ai essayé, et ne fonctionne toujours pas (voir ci-dessus). –

0

Avez-vous essayé d'appeler explicitement

writer.Close() 

plutôt que de compter sur