2012-10-02 9 views
27

Przepraszam, jeśli nie jestem super jasne z wyjaśnieniami, ale dodam i edytuję to pytanie dla jasności na żądanie.Konwertuj ForeignCollection na ArrayList - ORMLite, Gson i Android

Pracuję nad aplikacją dla systemu Android, która odbiera dane za pośrednictwem zewnętrznego interfejsu API i przechowuje dane lokalnie za pomocą interfejsu ORMLite. Przed przechowywanie danych lokalnie i przy użyciu ORMLite miałem modele, które pobrane JSON z serwera i przetwarzane go poprzez:

Gson gson = new Gson(); 

String result = ApiClient.httpPost("/user_route"); 

User user = gson.fromJson(result, User.class); 

Klasa użytkownika został określony

public class User { 
    int id; 
    String name; 
    ArrayList<Image> media; 
} 

a klasa Obrazu:

public class Image { 
    int id; 
    int creator_id; 
    String url; 
} 

To jest uproszczona reprezentacja modeli i metod, ale uważam, że zachowałem wszystkie istotne informacje. BTW, media jest obiektem JSON, który zawiera Images.

Teraz próbuję również przechowywać dane lokalnie. Aby uzyskać relacje między użytkownikami a obrazami za pomocą ORMLite, wydaje się, że musisz użyć klasy ForeignCollection i adnotacji @ForeignCollectionField. Nie wierzę, że Gson może bezpośrednio analizować Json dla pola media w klasie User jako obiekt ForeignCollection, więc pomyślałem, że muszę utworzyć dwa pola mediaCollection i media.

Korzystanie ORMLite klasy User teraz wygląda tak:

@DatabaseTable(tableName = "Users") 
public class User { 
    @DatabaseField(generatedId = true) 
    int id; 

    @DatabaseField 
    String name; 

    @ForeignCollectionField 
    ForeignCollection<Image> mediaCollection; 

    ArrayList<Image> media; 
} 

Klasa Obraz z ORMLite wygląda następująco:

@DatabaseTable(tableName = "Images") 
public class Image { 

    @DatabaseField(generatedId = true) 
    int id; 

    @DatabaseField(foreign=true, foreignAutoCreate=true, foreignAutoRefresh=true) 
    private User user; 

    @DatabaseField 
    int creator_id; 

    @DatabaseField 
    String url; 

} 

Jak przepływ aplikacji działa to pierwszy hit lokalny baza danych dla użytkownika. Wykonuję logikę, która następnie określa, czy muszę rzeczywiście trafić serwer, aby "zaktualizować" lub "odświeżyć" dane użytkownika.

Niezależnie od tego, czy dane są przesyłane lokalnie, czy z serwera zdalnego, muszę wyświetlić w tym samym widoku widok Image. W obecnej wersji adres URL urządzenia Image jest przechowywany w różnych typach obiektów w zależności od tego, czy dane są lokalne czy zdalne. Chciałbym to zrobić, jeśli Image jest przechowywany w obiekcie ForeginCollection, przekonwertować ten obiekt na ArrayList, a następnie kontynuować z resztą kodu, który wyodrębnia adres URL Image i wyświetla go.

Zgaduję, że są dwa pytania.

  1. Czy to dobry plan, czy powinienem napisać dwa całkowicie odrębne sposoby wydobywania Image URL z danymi, nie przekształcając obiekt z ForeignCollection do ArrayList?

  2. Jeśli jest dobry plan, w jaki sposób mogę przekonwertować ForeginCollection do ArrayList?

+0

zobacz odpowiedź w innym wątku pokrewnym: http://stackoverflow.com/a/31598771/3495371 –

Odpowiedz

20

Czy to dobry plan, czy powinienem napisać dwa całkowicie odrębne sposoby wydobywania URL obrazu z danych, nie przekształcając obiekt z ForeignCollection do ArrayList?

Powinno działać. Nie widzę łatwego sposobu, aby to zrobić inaczej.

Niektóre punkty:

  • Czy jest jakiś sposób, aby zaznaczyć ForeignCollection jako przejściowy, dlatego jest ignorowany podczas transferu przez JSON? Następnie możesz użyć tego samego obiektu User zarówno dla JSON, jak i ORMLite.
  • Pewna metoda oznaczania hydrate() byłaby dobra, aby przekonwertować z media ->mediaCollection i na odwrót.
  • Jeśli musisz załadować przeniesione obrazy JSON do zagranicznej kolekcji, powinieneś użyć metody Dao.getEmptyForeignCollect(...). Po utworzeniu kolekcji możesz dodać do niej obrazy, które zostaną dodane do tabel.

Jeśli jest to dobry plan, w jaki sposób mogę przekonwertować ForeignCollection do ArrayList?

To jest łatwiejsze. A ForeignCollection to Collection. Można po prostu zrobić:

media = new ArrayList<Image>(mediaCollection); 

Więc metoda User.getMedia() powinien sprawdzać null a jeśli tak, konwersja z pola mediaCollection.

+0

Czy możesz rozwinąć konwersję z 'ForeignCollection' ? Próbuję uzyskać tablicę za pomocą 'Image [] media = mediaCollection.toArray (new Image [0])' ale to rzuca 'java.lang.IllegalStateException: próba ponownego otwarcia już zamkniętego obiektu: SQLiteDatabase [ ...] 'pochodzące z' LazyForeignCollection: 232'. –

0

Nie można utworzyć ForeignCollection inny niż pierwszy przechowywania obiektów w bazie danych, a następnie mieć ormlite odzyskać je w ForeignCollection. Możesz użyć kolekcji zamiast kolekcji ForeignCollection, ale działa to w ten sam sposób.Co mogę zrobić, to: Mam dwie kolekcje w klasie nadrzędnej. Jednym z nich jest ArrayList, w którym json lub xml jest przekształcane do postaci szeregowej. Kiedy obiekt nadrzędny zostanie zapisany, dao przechowuje obiekty z listy szyku do bazy danych, w tabeli, która jest połączona z inną kolekcją, z kolekcją zagraniczną. Gdy obiekt nadrzędny zostanie pobrany, automatycznie zawiera obiekty w kolekcji ForeignCollection. Nie jest doskonały, ale działa.

+2

Jest to niepoprawnie. Możesz uzyskać nową kolekcję 'ForeignCollection', używając metody' Dao.getEmptyForeignCollection (...) '. Zobacz tutaj: http://ormlite.com/javadoc/ormlite-core/com/j256/ormlite/dao/Dao.html#getEmptyForeignCollection(java.lang.String%29 – Gray

2

Wystarczy przekonwertować z @ForeignCollectionField do ArrayList<Object> można to zrobić:

ArrayList<Object> taskFieldsList = new ArrayList<Object>(your collection); 

nadzieję, że to pomoże.