2016-05-04 8 views
2

私はこのゲームでguiceをしばらく使ってきましたが、私がこの場合にしたいものを達成する方法を理解するのに十分ではありません。 AssistedInjectThrowing Providers、およびMultibindingsの組み合わせが欲しいと思われますが、どのようにまとめたらいいか分かりません。これはうまくいかないボイルダウンコードです。 Guicierになる必要があります!名前のついた投げられたオブジェクトの投げ込みプロバイダ

public class Utilities { 
    public static String expensiveLookup(String key) throws IOException {...} 
} 

public class Helper { 
    @Inject private InjectedClass injectedValue; 

    public Helper(String value1, String value2, String value3) {...} 
} 

public class Workhorse { 

    // This map isn't very guicy. I'd prefer named bindings, or a multibinding 
    private static Map<String, Helper> helpers = new HashMap(); 

    public static void register(String name, Helper helper) { 
     helpers.put(name, helper); 
    } 

    //////// 

    @Inject lots of things 

    public void doHardWork(String helperName) { 
     Helper helper = helpers.get(helperName); 
     // do something hard 
    } 
} 

class UserModule extends AbstractModule { 
    protected void configure() { 

     // Helpers are created with `new`, so they don't get `injectedValue` 
     Workhorse.register("cheap helper", new Helper("cheap value", ...)); 

     try { 
      // This expensive lookup should be delay until needed 
      String expensiveValue = Utilities.expensiveLookup("expensive key"); 
      Workhorse.register("expensive helper", new Helper(expensiveValue, ...)); 
     } catch (IOException ex) { 
      // This exception should be handled in `doHardwork()` 
     } 
    } 
} 

私は一度の問題のいずれか2を解決する方法を見つけ出す、すべてではありません4することができます。■Guiceのを使用して作成する必要が

  • Helper、ないnew
  • expensiveLookupはする必要があります
  • IOExceptiondoHardWork
  • でキャッチして処理する必要があり、必要になるまで延期マップは、おそらく名前付きバインディングまたはマルチバインドで置き換えてください。これは私には難しい要件ではありませんが、それは正しいようです。

ヒントはありますか?

+0

ヘルパーコンストラクタのvalue2とvalue3は何ですか?キーを介して検索する値ですか?またはそれらは実行時に任意ですか? –

+0

これらも 'UserModule'で指定されていますが、単なる文字列です。ルックアップは必要ありません。 –

答えて

0

さて、私はついに解決策に取り組みました。私は確かにそれに満足していない、それは約2倍のコードを必要とし、理解するのが難しいので、それは動作します。私は心から簡単な方法があることを願っています。

public class Utilities { 
    public static String expensiveLookup(String key) throws IOException {...} 
} 

public class Helper { 
    private InjectedClass injectedValue; 

    @Inject 
    public Helper(
     @Assisted("value1") String value1, 
     @Assisted("value2") String value2, 
     @Assisted("value3") String value3, 
     InjectedClass injectedValue) { 

     this.injectedValue = injectedValue; 
     ... 
    } 

    public static <T extends Provider> void installProvider(
     Binder binder, String name, Class<T> providerClass) { 

     ThrowingProviderBinder.create(binder) 
      .bind(ProviderInterface.class, Helper.class) 
      .annotatedWith(Names.named(name)) 
      .to(providerClass) 
      .in(Singleton.class); 
    } 

    abstract public static Provider implements ProviderInterface { 
     @Inject private Factory factory; 

     protected Helper expensiveBuild(
      String expensiveKey, 
      String value2, 
      String value3) throws IOException { 

      String expensiveValue = Utilities.expensiveLookup(expensiveKey); 
      return cheapBuild(expensiveValue, value2, value3); 
     } 

     protected Helper cheapBuild(String value1, String value2, String value3) { 
      return Factory.create(value1, value2, value3); 
     } 
    } 

    interface ProviderInterface extends CheckedProvider<Helper> { 
     public Helper get() throws IOException; 
    } 

    interface Factory { 
     Helper create(
      @Assisted("value1") String value1, 
      @Assisted("value2") String value2, 
      @Assisted("value3") String value3); 
    } 
} 

class HelperModule exends AbstractModule { 
    protected void configure() { 
     install(new FactoryModuleBuilder() 
      .implement(Helper.class, Helper.class) 
      .build(Helper.Factory.class)); 
    } 
} 

public class Workhorse { 
    @Inject lots of things 
    @Inject private Injector injector; 

    public void doHardWork(String helperName) { 
     Key key = Key.get(Helper.ProviderInterface.class, Names.named(helperName)); 
     try { 
      Helper helper = injector.getInstance(key).get(helperName); 
      // do something hard 
     } catch (IOException ex) { 
      ... 
     } 
    } 
} 

class UserModule extends AbstractModule { 
    protected void configure() { 
     Helper.installProvider(binder(), "cheap helper", CheapProvider.class); 
     Helper.installProvider(binder(), "expensive helper", ExpensiveProvider.class); 
    } 

    private static class CheapProvider extends Provider { 
     public Helper get() { 
      return cheapBuild("cheap value", ...); 
     } 
    } 

    private static class ExpensiveProvider extends Provider { 
     public Helper get() throws IOException { 
      return expensiveBuild("expensive key", ...); 
     } 
    } 
} 

誰かがより良い答えを持っていれば、私はそれが大好きです!

関連する問題