Possiedo un'applicazione multi-tenant che include un livello di servizio OData API Web. Ho un nuovo requisito per supportare campi personalizzati, che saranno unici per ciascun titolare, e l'aggiunta di colonne generiche "customfield01", "customfield02" alle mie tabelle non è abbastanza flessibile.API Web OData V4 Tipi aperti: configurazione del contesto di controller e dati
Ho esplorato una serie di modi per descrivere e mantenere i dati personalizzati sul back-end, ma la parte più impegnativa sembra estendere i miei servizi odata per includere i campi personalizzati, in modo diverso, per ciascun titolare.
Il seguente collegamento descrive "Tipi aperte" in odata v4 con API Web:
Il codice di esempio funziona bene e fornisce il comportamento proprietà dinamica ho bisogno i miei soggetti. Tuttavia, il codice raggiunge solo l'utilizzo di un elenco di valori codificati per il back-end. Non è del tutto chiaro come popolare le entità da un contesto di dati di Entity Framework.
Inizialmente, sembrava che fosse facile avere una vista specifica del titolare nel database, per ogni titolare, ma il problema è che le proprietà estese devono davvero essere "non orientate" dalle colonne, in chiave coppie di valori. Per questo motivo, mi chiedo se ho bisogno di un'entità separata per le proprietà di "estensione". Così, ho potuto avere qualcosa di simile per il mio Pocos:
public class Item
{
[Key]
public Guid ItemId { get; set; }
public Guid TenantId { get; set; }
// navigation property for the extension entity
public virtual ItemExtension ItemExtension { get; set; }
}
public class ItemExtension
{
[Key]
public Guid ItemId { get; set; }
// dynamic properties for the open type
public IDictionary<string, object> DynamicProperties { get; set; }}
}
Ma ancora una volta, la questione diventa come popolare questi oggetti con i dati dal mio contesto dati. Ancora una volta, ho pensato che avrei avuto la possibilità di aprire le colonne, ma questo non funziona perché potrei avere diversi tipi di dati (che mi importano) per ogni proprietà dinamica.
Così, ho davvero alcune domande:
- Fa il modello POCO sopra ha senso per quello che sto cercando di realizzare?
- Quale dovrebbe essere il mio codice ItemController apparire come per includere l'ItemExtension per tutti i verbi HTTP (GET, POST, PUT, PATCH, DELETE)
- Quale dovrebbe essere il mio contesto dati hanno per l'ItemExtension per consentirgli di accedere alle colonne estesi su il back-end
- Come dovrebbero essere mantenute le colonne estese sul back-end per supportare questo.
Per quanto riguarda quello che ho provato - un sacco di cose che non funzionano, ma ho optato per il seguente (supponendo che non c'è un modo migliore):
una base POCO per ogni entità "estendibile" con una "estensione" separata entità per ogni (come il modello precedente)
sul back-end, dal momento che ho bisogno flexiblity illimitato e forti i tipi di dati, ho intenzione di avere un tabella di estensione separata per ogni combinazione di titolare/entità (sarebbe denominata [TenantId]. [ItemExtension] wi ogni colonna nominata e digitata come necessario).
Quello che mi manca è tutto tra i miei dati e il mio modello. Qualsiasi aiuto sarebbe molto apprezzato.
Grande questione, che sono davvero bloccato ora, qualcuno ha usato con successo OData v4 Open Types con backend EF6? Nota: non NHibernate ... alla ricerca di una soluzione EF6 Prenderò prima il codice o il modello –
Quello che sto facendo attualmente è utilizzare la connessione del contesto EF per eseguire una stored procedure. Quindi, devo scorrere i dati per creare il tipo aperto. Funziona, vorrei solo non dover "elaborare" i dati nel controller prima di restituirlo al chiamante. –
Si è verificato un problema leggermente diverso da questo, ho funzionato tutto eccetto che qualsiasi chiamata GET che non specificava un'istruzione $ select falliva quando il runtime ha provato ad applicare le queryoptions che sono state passate in ... Il mio problema era che quando non si specifica $ select, questo è lo stesso di una selezione SQL *, solo il runtime inietta tutte le colonne nei parametri select, incluso DynamicProperties. Ho dovuto ignorare EnableQuery ... Non sono sicuro che si possa andare in giro a dover "elaborare" i dati, altrimenti avremmo potuto anche codificare le proprietà personalizzate nei DTO. –