Skip to content
Arxisos edited this page Feb 1, 2012 · 20 revisions

ServiceStack uses a slightly modified version of Funq - a very fast IoC container. Funq is also used internally for creating new service instances because of the high performance. Of course there's the possibility to use another IoC container as a dependency repository where Funq can try to access registered type which were not registered in Funq itself. So you aren't forced to use Funq as your IoC container.

So you can resolve any types from your custom IoC container except of:

  • Services
  • Filter attributes (are executed before a service gets called)
  • Validators (validates a request DTO before the service gets called)

These are main components of ServiceStack which have very high performance requirements, so they need to be heavily cached. You'll read more about filter attributes and validators in the next documentation pages.

Register factories

Funq has the option to register Func<TType> as factories. These functions can be anything which has the correct signature and are not limited to delegates of the form

c=> new MyType()

but could be

c => CreateAndInitialzeMyType(c.Resolve<IOne>(), c.Resolve<ITwo>)

The first is using the type-safe generic Register methods. There are versions for both named and un-named registrations. Both take as a parameter, a delegate which takes a Container as its single parameter and returns an instance of the type.

public IRegistration Register<TType>(Func<Container, TType> func)
public IRegistration Register<TType>(string name, Func<Container, TType>func)

Register instances

The second method is using the type-safe generic register instance methods. There are versions for both named and un-named registrations. Both take as a parameter, an instance of the type.

public void Register<TType>(TType instance)
public void Register<TType>(string name, TType instance)

Note: When using the methods above, the properties and the constructor of the registered type aren't auto-wired (ie the properties and the constructor are not injected). You would need to do that manually like that:

container.Register<T>(c => new Foo(c.Resolve<Some>(), c.Resolve<Other>(), c.Resolve<Dependencies>());

Register and auto-wire

public IRegistration<T> RegisterAutoWired<T>();
public IRegistration<TAs> RegisterAutoWiredAs<T, TAs>() where T : TAs;

If you are using one of these two methods, the constructor and the properties of the registered type will be injected, too.

Object lifetime

By default all dependencies registered with Funq are singleton. If you want that a new dependency is created everytime (ie transient scope), you need to define the reuse scope manually:

container.Register(c => new TodoRepository()).ReusedWithin(ReuseScope.None);

Use another IoC container

    public interface IContainerAdapter
    {
        T Resolve<T>();
        T TryResolve<T>();
    }

If you've registered a dependency repository (ie IContainerAdapter), the services itself are created by Funq, but the properties of the services are injected by your custom dependency repository (Windsor, Ninject, ...). So for every property on a service, the method TryResolve<T> is called. How the IContainerAdapter creates the type of the requested instance doesn't matter. Like for services, it work's the same with filter attributes and validators.

Of course custom attributes (like [Ignore] from Ninject which notify the Ninject container to not resolve the marked property) or something similar of your custom IoC container aren't noted in the services, because Funq is the one which creates a service. But for all types which are resolved by calling IContainerAdapter the behavior of your IoC container isn't changed.

So here are some example how to use some popular IoC containers side-by-side with Funq. Of course you aren't limited to the these IoC containers, you can use any IoC container of your choice.

Use Ninject

    public class NinjectIocAdapter : IContainerAdapter
    {
        private readonly IKernel kernel;

        public NinjectIocAdapter(IKernel kernel)
        {
            this.kernel = kernel;
        }

        public T Resolve<T>()
        {
            return this.kernel.Get<T>();
        }

        public T TryResolve<T>()
        {
            return this.kernel.TryGet<T>();
        }
    }

Then in the AppHost Configure(Container container) method you need to enable this adapter:

//Create Ninject IoC container
IKernel kernel = new StandardKernel();
//Now register all depedencies to your custom IoC container
//...

//Register Ninject IoC container, so ServiceStack can use it
container.Adapter = new NinjectIocAdapter(kernel);

Use StructureMap

public class StructureMapContainerAdapter : IContainerAdapter
{
	public T TryResolve<T>()
	{
		return ObjectFactory.TryGetInstance<T>();
	}

	public T Resolve<T>()
	{
		return ObjectFactory.TryGetInstance<T>();
	}
}

In AppHost Configure:

//Configure User Defined REST Paths
container.Adapter = new StructureMapContainerAdapter();

//Register your dependencies
ObjectFactory.Inject(typeof(IFoo), new Foo());

Note: Due a behavior of StructureMap, you need your AppHost declare as internal, eg: internal class AppHost : AppHostBase

Use Windsor

public class WindsorContainerAdapter : IContainerAdapter, IDisposable 
{ 
    private readonly IWindsorContainer _container; 

    public WindsorContainerAdapter() 
    { 
        _container = new WindsorContainer().Install(FromAssembly.InThisApplication(), 
             FromAssembly.InDirectory(new ApplicationAssemblyFilter())); 
    } 

    public T TryResolve<T>() 
    { 
        return Resolve<T>(); 
    } 

    public T Resolve<T>() 
    { 
        return _container.Resolve<T>(); 
    } 

    public void Dispose() 
    { 
        _container.Dispose(); 
    } 
} 


  1. Getting Started
    1. Create your first webservice
    2. Your first webservice explained
    3. ServiceStack's new API Design
    4. Designing a REST-ful service with ServiceStack
    5. Example Projects Overview
  2. Reference
    1. Order of Operations
    2. The IoC container
    3. Metadata page
    4. Rest, SOAP & default endpoints
    5. SOAP support
    6. Routing
    7. Service return types
    8. Customize HTTP Responses
    9. Plugins
    10. Validation
    11. Error Handling
    12. Security
  3. Clients
    1. Overview
    2. C# client
    3. Silverlight client
    4. JavaScript client
    5. Dart Client
    6. MQ Clients
  4. Formats
    1. Overview
    2. JSON/JSV and XML
    3. ServiceStack's new HTML5 Report Format
    4. ServiceStack's new CSV Format
    5. MessagePack Format
    6. ProtoBuf Format
  5. View Engines 4. Razor & Markdown Razor
    1. Markdown Razor
  6. Hosts
    1. IIS
    2. Self-hosting
    3. Mono
  7. Advanced
    1. Configuration options
    2. Access HTTP specific features in services
    3. Logging
    4. Serialization/deserialization
    5. Request/response filters
    6. Filter attributes
    7. Concurrency Model
    8. Built-in caching options
    9. Built-in profiling
    10. Messaging and Redis
    11. Form Hijacking Prevention
    12. Auto-Mapping
    13. HTTP Utils
    14. Virtual File System
    15. Config API
    16. Physical Project Structure
    17. Modularizing Services
  8. Plugins
    1. Sessions
    2. Authentication/authorization
    3. Request logger
    4. Swagger API
  9. Tests
    1. Testing
    2. HowTo write unit/integration tests
  10. Other Languages
    1. FSharp
    2. VB.NET
  11. Use Cases
    1. Single Page Apps
    2. Azure
    3. Logging
    4. Bundling and Minification
    5. NHibernate
  12. Performance
    1. Real world performance
  13. How To
    1. Sending stream to ServiceStack
    2. Setting UserAgent in ServiceStack JsonServiceClient
    3. ServiceStack adding to allowed file extensions
    4. Default web service page how to
  14. Future
    1. Roadmap
Clone this wiki locally