PicoContainer

# About

- What is PicoContainer?
- Introduction
- Javadoc
- Downloads
- News
- FAQ
- Project Goals
- Support

# Core Concepts

- Component Lifecycle
- Dependency Injection
- Scoped Containers

# Dependency Injection

- Constructor Injection
- Setter Injection
- Annotated Field Injection
- Annotated Method Injection
- Typed Field Injection
- Named Field Injection
- Method Injection
- Multiple Injection
- Composite Injection
- Factory Injection
- Reinjection
- Injection via Providers

# Configuration

- Disambiguation

# Modifying Component Behaviors

- Modifying Behaviors
- Caching and Singletons
- Hiding Implementations
- Thread Safety Behaviors
- AOP Style Interception

# Advanced Concepts

- Fluent Style
- Arrays, Collections and Maps
- Leveraging Parameter Names
- Building Containers
- Component Properties
- Component Configuration
- Monitoring Component Events

# PicoContainer's Architecture

- Design Patterns
- Inversion of Control
- Component Adapters
- Mock Objects
- Terminology
- Container Comparisons
- Transparency

# Container Choices

- DefaultPicoContainer
- CommandLinePicoContainer
- PropertiesPicoContainer
- SystemPropertiesPicoContainer
- TransientPicoContainer
- TieringPicoContainer

# Dependant & Related

- Web Frameworks
- Scripting Support
- Persistence
- Logging

# Anti-patterns

- Propagating Dependency
- Long Constructor Argument List
- Container Dependency
- Unit Tests Use Container
- Singleton

# Help Pages

- Ambiguous Injectable
- Unprocessed Properties

# History

- Inversion of Control History

# Project Info

- Project
- Team

# Hosted by

# Tools

## Component Configuration

## Choices

In true IoC style, configuration for a component is pushed into it.

With PicoContainer, there are a few ways to do this:

- Design a class to hold the configuration and have getters on it to allow depending components to access configuration.
- Manually set the configuration for components as you add them to a container
- Leverage the fact that PicoContainer can pick up on named components

### Configuration Object

    public interface BigFatComponentConfig {
      String getSpellingWebServiceURL();
      String getTimeout();
    }
    public class BigFatComponent {
      URL spellWebService;
      String timeout;
      public BigFatComponent(BigFatComponentConfig config) {
        this.spellWebService = new URL(config.getSpellingWebServiceURL());
        this.timeout = config.getTimeout();
      }
      // other methods
    }
    ...
    pico.addComponent(BigFatComponent.class)
    pico.addComponent(new BigFatComponentConfigBean("http://foo.com/foo.wsdl", 120))

### Setting config as part of addComponent(..)

    public class BigFatComponent {
      URL spellWebService;
      int timeout;
      public BigFatComponent(String spellingWebServiceURL, int timeout) {
        this.spellWebService = new URL(spellingWebServiceURL);
        this.timeout = timeout;
      }
      // other methods
    }

    ...
    pico.addComponent(BigFatComponent.class, new ConstantParameter("http://foo.com/foo.wsdl"), new ConstantParameter(120));

### Configuration using parameter names

Consider this component ...

    public class BigFatComponent {
      URL spellWebService;
      int timeout;
      public BigFatComponent(String spellingWebServiceURL, int timeout) throws MalformedURLExeption {
        this.spellWebService = new URL(spellingWebServiceURL);
        this.timeout = timeout;
      }
      public String toString() {
        return "URL=" + spellWebService + ", timeout=" + timeout;
      }

      // other methods
    }

And this composition ...

    pico.addConfig("spellingWebServiceURL", "http://foo.com/spelling.wsdl"); // matches constructor parameter name
    pico.addConfig("somethingOtherURL", "http://bar.com/other.wsdl");
    pico.addConfig("timeout", 120); // matches constructor parameter name
    pico.addConfig("timeout2", 456);
    pico.as(Characteristics.USE_NAMES).addComponent(BigFatComponent.class);

    BigFatComponent bfc = pico.getComponent(BigFatComponent.class);
    System.out.println("bfc: " + bfc.toString());
    // Prints .. "bfg: URL=http://foo.com/spelling.wsdl, timeout=120"

This feature of PicoContainer relies on the a non-JDK mechanism of accessing parameter names for methods and constructors. In this case named parameters spellingWebServiceURL and timeout.

There are two ways for this to work:

- relying on the fact that your component classes have debug info compiled into them.
- post-processing component classes with Paranamer before placing them in their jar

If the parameter name information cannot be accessed at runtime by PicoContainer, then Pico will be unable to differentiate between potential injectable classes of the same type and throws an exception that suggests that there is an ambiguity.

This is not a global variable facility. Its scoped with the container in question and its child containers.

## Taking configuration from the elsewhere

Configuration can also be bound to components with :

> CommandLineArgumentsPicoContainer

> PropertiesPicoContainer

> SystemPropertiesPicoContainer