2017-08-31 1 views
0

Ich entwickle gerade eine App, momentan stecke ich auf der Registrierungsseite meiner UWP App fest.Wie werden Enums in einer SQL Azure-Datenbank mit dem SQLite-Speicher im Client gespeichert?

Also habe ich ein Backend für meine app und einige Variablen in meinem Backend sind Aufzählungen wie zum Beispiel ich eine Klasse namens Personal haben, und es hat eine ENUM Variable wie diese öffentliche Geschlecht Sex {get; set;} das ist und Enum, Wann immer ich meine Tabelle seed, wird diese Variable in ein int in sql Azure konvertiert.

Es gibt kein Problem dafür, aber mein Hauptproblem ist es bei meinem Kunden. Ich folge Adrian Hall Book, so habe ich die folgenden Klassen an meinem Client:

public class Personal : TableData 
{ 
    [Required] 
    [StringLength(50)] 
    [JsonProperty(PropertyName = "name")] 
    public string Name { get; set; } 
    [Required] 
    [StringLength(50)] 
    [JsonProperty(PropertyName = "dadlastname")] 
    public string DadLastName { get; set; } 
    [Required] 
    [StringLength(50)] 
    [JsonProperty(PropertyName = "momlastname")] 
    public string MomLastName { get; set; } 
    [Required] 
    [StringLength(50)] 
    [JsonProperty(PropertyName = "email")] 
    public string Email { get; set; } 
    [Required] 
    [JsonProperty(PropertyName = "sex")] 
    public Gender Sex { get; set; }//ENUM TYPE 
    [Required] 
    [Column(TypeName = "date")] 
    [JsonProperty(PropertyName = "birthdate")] 
    public DateTime? BirthDate { get; set; } 

    public override bool Equals(object obj) 
    { 
     return Equals<Personal>(obj, this); 
    } 

    public override int GetHashCode() 
    { 
     return Id.GetHashCode(); 
    } 
} 

, wie Sie dies ist meine Enum sehen:

public enum Gender : Int32 
{ 
    [Display(Name = "EnumGenderMale")] 
    Male = 0, 
    [Display(Name = "EnumGenderFemale")] 
    Female = 1 
} 

Ich weiß Enum standardmäßig von Int32 erben, aber Ich versuche, dies zu tun, so dass jedes Mal, wenn ich meinen Backing Store initialisiere, mein sqllite.db erzeugt, aber der Enum Typ entsprechend meiner Protokollierung als Typ [TEXT] erstellt wird. Wenn ich versuche, auf mein Backend zu schreiben, wird ein HTTPStatusCode geworfen: 500 Interner Serverfehler, und es schreibt nichts auf meine sqlazure db.

Ich vermute das Hauptproblem ist, weil ich Enums seine Best Practice verwende, um enums im Client zu verwenden und auf meinem Backend schreiben zu können?

sind meine Fehler an meinem pushasync Methoden geworfen diese meine Klassen für meine Sync-Klasse sind:

public async Task SyncOfflineCacheAsync() 
    { 
     await InitializeAsync(); 

     try 
     { 
      await client.SyncContext.PushAsync(); 
     } 
     catch (MobileServicePushFailedException ex) 
     { 
      if(ex.PushResult != null) 
      { 
       foreach (var error in ex.PushResult.Errors) 
       { 
        var objString = error.Item.ToString(); 
        await ResolveAnyConflictAsync(error, objString); 
       } 
      } 
     } 
     catch(Exception ex) 
     { 
      Debug.WriteLine($"Database corrupted, purging database: {ex.Message}"); 
      //purge database 
     } 

     //Pull each sync table 
     var accountTable = await GetSyncTableAsync<Account>(); 
     await accountTable.PullAsync(); 

     var personalTable = await GetSyncTableAsync<Personal>(); 
     await personalTable.PullAsync(); 

     var laborTable = await GetSyncTableAsync<Labor>(); 
     await laborTable.PullAsync(); 

     var subscriptionTable = await GetSyncTableAsync<Subscription>(); 
     await subscriptionTable.PullAsync(); 
    } 

public async Task InitializeAsync() 
    { 
     //Short circuit to database if its already initialized. 
     if(client.SyncContext.IsInitialized) 
     { 
      Debug.WriteLine($"InitializedAsync: Short Circuit"); 
      return; 
     } 

     //create a reference to the local sqlLite store. 
     Debug.WriteLine("InitializeAsync: Initializing store"); 
     var store = new MobileServiceSQLiteStoreWithLogging("ceneam.db", true, true); 

     //Define Database Schema    
     store.DefineTable<Account>(); 
     store.DefineTable<Personal>(); 
     store.DefineTable<Labor>(); 
     store.DefineTable<Subscription>(); 

     //Actually create the store and update the schema. 
     Debug.WriteLine("InitializeAsync: Initializing SyncContext"); 
     await client.SyncContext.InitializeAsync(store); 

     //Do the sync 
     Debug.WriteLine("InitializeAsync: Syncing Ceneam Offline Cache"); 
     await SyncOfflineCacheAsync(); 
    } 

public static async Task ResolveAnyConflictAsync(MobileServiceTableOperationError error, string objString) 
    { 
     switch (GetModelErrorType(objString)) 
     { 
      case "Account": 
       { 
        await ResolvePushConflictAsync<Account>(error); 
        break; 
       } 
      case "Personal": 
       { 
        await ResolvePushConflictAsync<Personal>(error); 
        break; 
       } 
      case "Labor": 
       { 
        await ResolvePushConflictAsync<Labor>(error); 
        break; 
       } 
      case "Subscription": 
       { 
        await ResolvePushConflictAsync<Subscription>(error); 
        break; 
       } 
     } 
    } 

    static async Task ResolvePushConflictAsync<T>(MobileServiceTableOperationError error) where T : TableData 
    { 
     Debug.WriteLine($"Resolve conflict for {error.Item}"); 
     var serverItem = error.Result.ToObject<T>(); 
     var localItem = error.Item.ToObject<T>(); 

     // Note that you need to implement the public override Equals(TableModel item) 
     // method in the Model for this to work 
     if(serverItem.Equals(localItem)) 
     { 
      //Items are the same, so ignore the conflict 
      await error.CancelAndDiscardItemAsync(); 
      return; 
     } 

     //Client wins 
     localItem.Version = serverItem.Version; 
     await error.UpdateOperationAsync(JObject.FromObject(localItem)); 

     //Server wins 
     //await error.CancelAndDiscardItemAsync(); 
    } 

so sind diese Klassen gezeigt und an Adrian Hall Bücher lehrte ich meine eigenen Versionen dieses Buches angewendet hatte. In adrian Hallen Beispiel, das nur Booleans und Text verwendet Ich bin in der Lage, meine Datenbank ohne Fehler zu synchronisieren ich denke, es scheitert, weil ich Enums verwende, kann jemand zeigen mir in die richtige Richtung wie Enums zu behandeln, wenn Azure Mobile verwenden Apps, denn selbst wenn ich Offline-Unterstützung (sqlLite Store) loswerden wird es weiterhin Fehler und ich bekomme immer Fehlercode 500.

Antwort

1

Nach op's Beschreibung, habe ich dieses Problem auf meiner Seite und Download and run the client project und Server-Projekt von Quick Start überprüft Klinge auf azurblauem Portal.Es könnte so auf meinem lokalen Seite erwartet funktionieren, Sie zu meinem Test beziehen konnte wie folgt:

Server-Modell:

public class ToDoItem : EntityData 
{ 
    public string Text { get; set; } 
    public bool Complete { get; set; } 
    public Gender Sex { get; set; } 
} 

public enum Gender 
{ 
    [Display(Name = "EnumGenderMale")] 
    Male = 0, 
    [Display(Name = "EnumGenderFemale")] 
    Female = 1 
} 

Client-Modell:

public class TodoItem 
{ 
    public string Id { get; set; } 

    [JsonProperty(PropertyName = "text")] 
    public string Text { get; set; } 

    [JsonProperty(PropertyName = "sex")] 
    public Gender Sex { get; set; } 
} 

public enum Gender 
{ 
    [Display(Name = "EnumGenderMale")] 
    Male = 0, 
    [Display(Name = "EnumGenderFemale")] 
    Female = 1 
} 

Zugang der Daten über den Browser:

enter image description here

Client-App:

enter image description here

Fügen Sie einen neuen Datensatz, überprüfen Sie die lokalen SQLite-Speicher:

enter image description here

Anruf await App.MobileService.SyncContext.PushAsync();, verwenden Fiedler die Netz Spuren zu erfassen wie folgt:

enter image description here

can somebody point my in the right direction on how to treat enums when using Azure Mobile Apps, because even If I get rid of Offline support (sqlLite store) it keeps failing and I keep getting error code 500.

konfigurieren config.IncludeErrorDetailPolicy = IncludeErrorDetailPolicy.Always; unter Startup.MobileApp.cs Datei Ihrer mobilen App-Projekt die detaillierte Fehlermeldung zu erfassen. Sie können auch auf here verweisen, um das Backend Ihrer mobilen App zu debuggen.

+0

Danke Mann, ich fand meinen Fehler Danke für den letzten Teil Ihrer Antwort, Es stellt sich heraus, dass ich meine Setdomainmanager-Methode als öffentlich hatte. Sobald ich es in privat geändert habe, habe ich diesen Fehler nicht mehr erhalten: "Es wurden mehrere Aktionen gefunden, die der Anfrage entsprechen". und ich konnte auf meiner Datenbank posten. Du hast mir jede Menge Stunden gespart, ich habe Bullshit vermutet !!! –

Verwandte Themen