2017-07-03 3 views
0

私のアプリでは、多くのローカライズ可能なエンティティがあります。このエンティティのデータベース構造 はhereです。いくつかのテーブルのPKのタイプは異なるかもしれません(それらのうちのいくつかはintで、あるものはbigintです)。テーブルに格納されるデータの量によって異なります。 ORMとしてDapperを使用します。C#リポジトリとローカライズ可能なエンティティ

今私は、このソリューションを持っている(しかし、何かが内部でこのソリューションが悪いと言われます):

// ENTITY 
public abstract class Entity 
{ 
    public object Id { get; set; } 
} 

public abstract class Entity<TKey> : Entity 
{ 
    public new TKey Id { get; set; } 
} 

// LOCALIZABLE ENTITY 
public abstract class LocalizableEntity<TTranslation> : Entity 
    where TTranslation : EntityTranslation 
{ 
    public ICollection<TTranslation> Translations { get; set; } 
} 

public abstract class LocalizableEntity<TKey, TTranslation> : Entity<TKey> 
    where TTranslation : EntityTranslation 
{ 
    public ICollection<TTranslation> Translations { get; set; } 
} 

// ENTITY TRANSLATION 
public abstract class EntityTranslation 
{ 
    public object LocalizableId { get; set; } 

    public int LanguageId { get; set; } 
} 

public abstract class EntityTranslation<TKey> : EntityTranslation 
{ 
    public new TKey LocalizableId { get; set; } 
} 

// REPOSITORIES 

public class BaseRepository: IRepository, IDisposable 
{ 
    public string ConnectionString { get; set; } 

    // .... 
} 

public abstract class BaseEntityRepository: BaseRepository 
{ 
    protected IDbConnection Connection => _connection ?? (_connection = CreateDbConnection(GetConnectionStringValue(ConnectionString))); 

    protected abstract IDbConnection CreateDbConnection(string connectionString); 

    // SaveEntity<T>(T entity), DeleteEntity(object id) 
} 

public abstract class BaseEntityRepository<TEntity, TKey, TSearchOptions, TLoadOptions> : BaseEntityRepository 
    where TEntity : Entity<TKey> 
    where TSearchOptions : SearchOptions 
    where TLoadOptions : LoadOptions 
{ 
    // GetEntities(TSearchOptions sopts, TLoadOptions lopts), EntityCount(TSearchOptions) ... 
} 

public abstract class BaseLocalizableEntityRepository<TEntity, TKey, TEntityTranslation, TSearchOptions, TLoadOptions> : BaseEntityRepository<TEntity, TSearchOptions, TLoadOptions> 
    where TEntity : Entity<TKey> 
    where TEntityTranslation : EntityTranslation<TKey> 
    where TSearchOptions : SearchOptions 
    where TLoadOptions : LoadOptions 
{ 
    // GetTranslations, SaveTranslation ... 
} 

は、それが良いか悪いですか?悪い場合はどうしたらいいですか?

+0

'.resx'ファイルを使って行われる組み込みローカライゼーションはオプションですか?または、高度にカスタマイズ可能なローカリゼーションですか?すなわち、ユーザが翻訳を書かなければならない。 –

+0

@MichaelMairegger高度にカスタマイズ可能なローカリゼーションが必要です。 – Alex

+0

これに伴う1つの問題は照合です。 1つのDB列に異なる言語がある場合、照合順序が列に属するので、特定の言語の正しい照合順序でソートすることができない場合があります。私はこれに対する解決策を知らない。代替案はすべて動的SQLを含むように見えるので、見つけてもいいでしょう。 – bbsimonbb

答えて

0

高度にカスタマイズ可能なローカリゼーションが必要なので、ソリューションはそれほど悪くありません。私は翻訳が必要な場合、同じ方法を実行します。

CREATE TABLE Test_Translations 
(
    Language char(10) NOT NULL, 
    TextId int NOT NULL, 
    Value text NOT NULL, 
    CONSTRAINT Test_Translations_Language_TextId_pk PRIMARY KEY (Language, TextId) 
); 

CREATE TABLE Test_LocalizableStrings 
(
    Id int NOT NULL CONSTRAINT Test2_Test1Id_pk primary key 
); 

ALTER TABLE Test_Translations ADD FOREIGN KEY (TextId) REFERENCES Test_LocalizableStrings; 

Resulting Tables

そして、翻訳支援を必要とする表にちょうど参照を作成します。しかし、その代わりに私は翻訳の参照をサポートする任意のエンティティが先のユニークなテーブルを持っているエンティティ翻訳ごとに異なるテーブルを持ちますTest_LocalizableStringsのキーです。クエリ時にTextIdLanguageのクエリ。

関連する問題