以下は私が直面している問題の概算です。
いくつかのルールを備えたパスワードバリデーターがあると考えてください。
public interface RuleChecker{
//Checks for a password strenght, returns 10
//for strong or 0 for soft password.
int check(String pass);
}
そして、いくつかの実装があります。私たちのサービスは、8スコアを超える場合にのみパスワードを受け入れます。
public class NoCheck implements RuleChecker {
public int check(String pass){return 10;}
}
public class LengthCheck implements RuleChecker{
...
}
public class AlphanumericCheck implements RuleChecker{
...
}
public class AlphaAndLenghtCheckAdapter implements RuleChecker{
...
}
ただし、テストの目的で、これらのルールを「管理」できるアプリケーション内にWebサービスを実装し、ルールを選択する必要があります。
public class PasswordCheckService{
private RuleChecker checker;
@Inject
public PasswordCheckService(final RuleChecker checker){
this.checker = checker;
}
public boolean checkPassword(String password){
return checker.check(password) > 8;
}
}
では、Guiceには、実行時に変更する方法がありますか?サービスにインジェクションがありますか?
例:
アプリケーションを起動し、デフォルトでLengthCheckが選択されてアプリケーションに注入されます。ウェブサイトで、NoCheckチェックボックスを選択し、データベースに保存されているオプションを保存します。サービスが以前に注入したBeanを自動的に変更するようにGuiceを構成できますか?それで、これからは新しいパスワードのチェックはありませんか?
-
今のところ、私はそれらのトピックを見つけました
Google Guiceと実行時のさまざまなインジェクション しかし、その種のプロバイダーが私の問題に適合するかどうかはわかりません。
Guiceランタイム依存関係パラメーターの再注入 その素晴らしい質問は似たようなことを話しているが、私が探しているものではない。
guice:コマンドラインでのランタイムインジェクション/バインディング これは私の問題に最も近いですが、彼は「ランタイム」の開始時にのみ実行し、時間の経過とともに変更しません。
何か助けはありますか?
ありがとうございました!
最初のコメントのヒントを使用して、このPOCを実装しましたが、それでも機能しません。別のボタンを選択して変更すると、サービスBeanは更新されません。 https://bitbucket.org/ramonboza/guicedynamicconfig
各フィールドタイプ(ログイン、パスワード、生年月日など)のプロバイダーを作成し、返される実装を変更するパラメーターを指定します。
_public class MyModule extends AbstractModule {
public void configure() {
bind(RuleChecker.class).annotatedWith(named("password")).toProvider(PasswordRuleCheckerProvider.class);
bind(RuleChecker.class).annotatedWith(named("login")).toProvider(LoginRuleCheckerProvider.class);
}
}
public static class PasswordRuleCheckerProvider implements Provider<RuleChecker> {
private static CheckType type = CheckType.ALPHANUMERIC;
// static type setter.
public RuleChecker get() {
// it would even be better if you could use singletons here.
switch(type) {
case LENGTH:
return new LengthCheck();
case ALPHANUMERIC:
return new AlphanumericCheck();
case ALPHALENGTH:
return new AlphaAndLenghtCheckAdapter();
case NONE:
default:
return NoCheck();
}
}
}
// Almost same provider for your LoginRuleCheckerProvider. You could do something generic.
_
管理セクションで「タイプ」の値を変更すると、ルールが変更されます。注釈のおかげで、限られたフィールドのセットに影響を与える可能性があります。例:PasswordRuleCheckerProvider.setType(CheckType.LENGTH);
。 @Named('password')
のフィールドにのみ影響します。
このようにフィールドとサービスを宣言する必要があります:
_public abstract class DynamicService {
protected void updateService() {
// Reinject with the new implementations the members.
App.getInjector().injectMembers(this);
}
}
public class PasswordCheckService extends DynamicService {
@Inject
@Named("password")
private RuleChecker passwordChecker;
public void changePasswordCheckType(CheckType type) {
PasswordRuleCheckerProvider.setType(type);
// Reinject, so you have your new implementation.
updateService();
}
// [...]
}
_