我们在我们的应用中使用MvvmCross,并使用MvxSimpleIoCContainer
在应用启动时,我们会注册所有迁移 这很容易,因为所有迁移都是从IMigration
继承的typeof (IMigration)
.Assembly
.CreatableTypes()
.Inherits<IMigration>()
.AsTypes()
.RegisterAsLazySingleton();
注册迁移后,我们需要连续运行它们,因此MigrationRunner看起来像这样。
Mvx.Resolve<IMigrationRunner>().RunAll(SystemRole.Client, new List<IMigration>
{
Mvx.IocConstruct<Migration001>(),
Mvx.IocConstruct<Migration002>()
});
正如您所看到的,我明确地使用Mvx构建每个迁移。当一堆迁移最终在应用程序中时,这变得乏味并且容易出错。
我希望能够做的就是一举解决整个集合,而不是每次创建新的迁移时都不需要触摸它。
有没有办法通过MvvmCross来做到这一点?
伪代码
Mvx.Resolve<IMigrationRunner>()
.RunAll(SystemRole.Client, Mvx.ResolveAll<IMigration>());
答案 0 :(得分:2)
我会使用LINQ来获取类型列表。遗憾的是,无法获得已注册类型的列表,因此您必须再次枚举类型,就像注册时一样。您甚至可以按类型名称排序。现在您有了一个类型列表,您可以创建一个新的实例化/已解析类型列表以传递给RunAll()。类似的东西:
var migrationTypes = typeof (IMigration)
.Assembly
.CreatableTypes()
.Inherits<IMigration>()
.AsTypes()
.OrderBy(t => t.Name)
.ToList();
Mvx.Resolve<IMigrationRunner>()
.RunAll(SystemRole.Client,
migrationTypes.Select(t => Mvx.Resolve(t)).ToList());
这是“浏览器”代码,所以没有保证,但你得到了要点。
答案 1 :(得分:1)
好的,所以现在反思是这个问题的答案,最后,我想扩展我们的自定义MvxServiceLocator : IServiceLocator
以包含类似
public IEnumerable<object> GetAllInstances(Type serviceType){...}
但是现在我在应用中只获得了RunMigrations()
方法
private void RunMigrations()
{
var migrationType = typeof (IMigration); // IMigration is in a separate assembly
var migrations = GetType().Assembly
.GetTypes()
.Where(
t => migrationType.IsAssignableFrom(t) && !t.IsAbstract)
.OrderBy(t => t.Name)
.Select(m => _serviceLocator.GetInstance(m) as IMigration)
.ToList();
var migrationRunner = new MigrationRunner(Mvx.Resolve<IDbProvider>());
migrationRunner.RunAll(SystemRole.Client, migrations);
}
其中_serviceLocator.GetInstance(m)
只存在于我们的自定义MvxServiceLocator
public object GetInstance(Type serviceType)
{
return _ioCProvider.Resolve(serviceType);
}
编辑:这是我如何扩展我们的服务定位器包装器。
public class MvxServiceLocator : IServiceLocator
{
private readonly IMvxIoCProvider _ioCProvider;
public MvxServiceLocator(IMvxIoCProvider ioCProvider)
{
_ioCProvider = ioCProvider;
}
public IEnumerable<TService> GetAllInstances<TService>()
{
var serviceType = typeof(TService);
var registrations = GetType().Assembly
.GetTypes()
.Where(
t => serviceType.IsAssignableFrom(t) && !t.IsAbstract)
.Select(m => (TService)_ioCProvider.Resolve(m));
return registrations;
}
}