def test_callable_which_returns_none_raises_typeerror():
    def foo():
        pass

    def configure(config: Config):
        config.bind(T, foo)

    with pytest.raises(TypeError):
        create_container(configure)
def test_singleton_creates_singleton_objects_with_args():
    container = create_container(configure_singleton)
    s1 = container.get(Transient)
    s2 = container.get(Transient)
    assert s1.a == 42
    assert s1.b == 10.0
    assert s1 is s2
def test_singleton_lifetimes() -> None:
    container = create_container(configure_lifetime)
    s1 = container.get(MySingleton)
    s2 = container.get(MySingleton)
    assert s1 is s2
    t1 = container.get(MyTransient)
    t2 = container.get(MyTransient)
    assert t1 is not t2
def test_singleton_within_a_context():
    container = create_container(configure_singleton_with_context)
    t11 = container.get(UseT1)
    t12 = container.get(UseT1)
    t21 = container.get(UseT2)
    t22 = container.get(UseT2)
    assert t11.t.a == 1
    assert t11.t is t12.t
    assert t21.t.a == 2
    assert t21.t is t22.t
def test_scope_setting_within_a_context():
    container = create_container(configure_lifetime_with_context)
    t11 = container.get(UseT1)
    t12 = container.get(UseT1)
    t21 = container.get(UseT2)
    t22 = container.get(UseT2)
    assert t11.t.a == 1
    assert t11.t is not t12.t
    assert t21.t.a == 2
    assert t21.t is t22.t

    t31 = container.get(UseT3)
    t32 = container.get(UseT3)
    assert t31.t is t32.t
def test_container_resolves_chained_binding() -> None:
    container = create_container(configure_bind_hierarchy)
    concrete_object = container.get(H1)
    assert isinstance(concrete_object, H3)
def test_container_factory_is_class_static_method():
    container = create_container(configure_factory_class_static)
    needs_int = container.get(NeedsInt)
    assert needs_int.a_int == 10
def test_arg_factory():
    container = create_container(configure_arg_factory)
    my_arg = container.get(ArgFactory)
    assert my_arg.name == "foobar"
def test_stacked_binding_uses_singleton_of_bound_to_object_first():
    container = create_container(configure_stacked_binding_and_lifetime)
    s1 = container.get(MySB)
    s2 = container.get(MySB)
    assert isinstance(s1.sb, SB3)
    assert s1.sb is not s2.sb
def test_define_a_dependency_without_providing_it_raises_typeerror():
    def configure(config: Config):
        config.dependency(int)

    with pytest.raises(TypeError):
        create_container(configure)
def test_container_creates_simple_type():
    container = create_container()
    my_int = container.get(A)
    assert isinstance(my_int, A)
def test_transient_creates_transient_object_with_args():
    container = create_container(configure_transient)
    s1 = container.get(Transient)
    assert s1.a == 42
    assert s1.b == 10.0
    assert isinstance(s1.c, C)
def test_default_lifetime_is_transient() -> None:
    container = create_container()
    t1 = container.get(MyTransient)
    t2 = container.get(MyTransient)
    assert t1 is not t2
def test_default_lifetime_switched_to_singleton() -> None:
    container = create_container(default_lifetime=Lifetime.SINGLETON)
    s1 = container.get(MySingleton)
    s2 = container.get(MySingleton)
    assert s1 is s2
def test_instance_within_a_context():
    container = create_container(configure_instance_with_context)
    t1 = container.get(UseT1)
    t2 = container.get(UseT2)
    assert t1.t is t1_instance
    assert t2.t is t2_instance
def test_callable_within_a_context():
    container = create_container(configure_callable_with_context)
    t1 = container.get(UseT1)
    t2 = container.get(UseT2)
    assert t1.t.a == 1
    assert t2.t.a == 2
def test_instance_returns_provided_intance():
    container = create_container(configure_instance)
    instance = container.get(MyInstance)
    assert instance is MY_INSTANCE_INSTANCE
def test_give_a_non_registered_dependency_raises_type_error():
    with pytest.raises(TypeError):
        create_container(configure_without_dependencies, dependencies=[5])
def test_callable_is_called_with_args_for_return_type_dependency():
    container = create_container(configure_callable)
    instance = container.get(Transient)
    assert instance.a == 42
    assert isinstance(instance.c, C)
    assert instance.b == 0.0
def test_lifetime_of_binded_type_is_singleton():
    container = create_container(configure_bind_singleton)
    s1 = container.get(MyInterface)
    s2 = container.get(MyInterface)
    assert s1 is s2
def container() -> StaticContainer:
    return create_container()
def test_provide_arguments_for_a_callable_container():
    container = create_container(configure_arguments)
    my_arg = container.get(MyArg)
    assert my_arg.arg1 == "foobar"
def test_given_dependencies_are_used_for_resolution():
    dependency = Dependecy()
    container = create_container(configure_dependency, dependencies=[dependency])
    dependent = container.get(NeedsDependency)
    assert dependent.dependent is dependency
def test_parameter_and_factory():
    container = create_container(configure_parameter_and_factory)
    my_arg = container.get(ParameterAndFactory)
    assert my_arg.number == 42
    assert my_arg.text == "foobar"
def test_binding_within_a_context():
    container = create_container(configure_binding_with_context)
    f1 = container.get(UseF1)
    f2 = container.get(UseF2)
    assert isinstance(f1.f, F1)
    assert isinstance(f2.f, F2)
def test_container_factory_is_not_created_class_instance_method():
    container = create_container(configure_factory_not_created_class_instance_method)
    needs_int = container.get(NeedsInt)
    assert needs_int.a_int == 42
def test_given_a_binding_for_interface_creates_specified_concrete_type() -> None:
    container = create_container(configure_bind)
    concrete_object = container.get(MyInterface)
    assert isinstance(concrete_object, MyImplementation)