Archive for the ‘MicroKernel’ Category

Some Castle related news

January 5th, 2009

During the holiday – and between Wow quests and dungeons – I’ve managed to apply a bunch of patches and to fix some outstanding bugs on the Components and Windsor projects.

Another interesting accomplishment is some contributions finally made in and Castle.Core, Castle.MicroKernel and Castle.Windsor are now Silverlight ready.

Last but not least, I recently applied a patch that made Castle.DynamicProxy 2 also available for Silverlight.

The pending items now are:

- Fix the build so the bits targeting SL will be correctly build and made available through our build server

- Change Windsor to use the SL version of DynProxy.

Thanks for all the patches, people. Keep them coming! :-)

Autoregistration without Binsor

May 13th, 2008

On my Global.cs I usually have:

private static void RegisterWebComponents()
{
    container.Register(AllTypes.Of<SmartDispatcherController>().
        FromAssembly(typeof(HomeController).Assembly));

    container.Register(AllTypes.Of<ViewComponent>().FromAssembly(typeof(Global).Assembly)
            .Configure(
                delegate(ComponentRegistration reg)
                {
                    reg.Named(reg.ServiceType.Name);
                }));

}

To get Windsor integration:

First, make the Global implement the IContainerAccessor

public class Global : HttpApplication, IContainerAccessor

Then add a static field to hold the container

private static WindsorContainer container;

The App_Start/End and the IContainerAccessor implementation:

protected void Application_Start(object sender, EventArgs e)
{
    container = new WindsorContainer(new XmlInterpreter());
    container.AddFacility("mr", new MonoRailFacility());

    RegisterWebComponents();
}

protected void Application_End(object sender, EventArgs e)
{
    container.Dispose();
}

public IWindsorContainer Container
{
    get { return container; }
}

To Configure MonoRail using code

Make the global implement IMonoRailConfigurationEvents and implement the method Configure:

public class Global : HttpApplication, IContainerAccessor, IMonoRailConfigurationEvents
{
    public void Configure(IMonoRailConfiguration configuration)
    {
        // Configuring ViewEngine
        configuration.ViewEngineConfig.ViewPathRoot = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Views");
        configuration.ViewEngineConfig.ViewEngines.Add(new ViewEngineInfo(typeof(NVelocityViewEngine), false));

        // You can configure other things, and hopefully in the future 
        // we can expose a kind of fluent interface to guide you on this process
    }
}

Windsor: for all tastes

March 7th, 2008

So, in donjon code base we have service like the following:

public class AppStarter
{
  public AppStarter(IModuleInstaller[] installers) 
  {
     ...

By default, Castle.MicroKernel will expect you to define what should be included in the array. This can be done through the external configuration or through the code, using the cool fluent interface Craig has developed.

In my case, though, I always want all module installers registered to be available to my service. How to accomplish that?

The first guess is using a custom ITypeConverter implementation. However, those are only used by the container to convert a representation into something that can fulfill a dependency. This is definitely not my case.

Second guess is using a custom dependency resolver. “What? You mean I need to write a new dependency resolver for the whole damn thing?” No, not really necessary. The default dependency resolver allow you to add more sub resolver to handle your special situations. So all I had to do was:

class ArrayResolver : ISubDependencyResolver
{
	private readonly IKernel kernel;

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

	public object Resolve(CreationContext context, ISubDependencyResolver parentResolver, 
                              ComponentModel model,
                              DependencyModel dependency)
	{
		return kernel.ResolveAll(dependency.TargetType.GetElementType(), null);
	}

	public bool CanResolve(CreationContext context, ISubDependencyResolver parentResolver, 
                              ComponentModel model,
                              DependencyModel dependency)
	{
		return dependency.TargetType != null && 
			dependency.TargetType.IsArray && 
			dependency.TargetType.GetElementType().IsInterface;
	}
}

And then, when you instantiate your container, you have to register the sub dependency resolver:

Kernel.Resolver.AddSubResolver(new ArrayResolver(Kernel));

A few lines of code, and you just got Windsor doing exactly what you want.

News directly from Castle’s trunk

March 1st, 2008

This has just been committed. Checking the test cases, it shows how it should work:

container.Register( AllTypesOf<IService>.
    FromAssembly( Assembly.Load("MyServicesAssembly") ) );

Check the message for more usage examples. I hope it’s the end of the Batch Registration Facility :-)

Craig, you’re the man!

Windsor: Component Burden described as a (bad) side effect

February 26th, 2008

This blog entry is fantastic. It explains how Windsor (well, MicroKernel) deals with non-singletons that are disposable. In the end, the author makes an interesting test:

public class DisposableCon : IDisposable {
 
   public ITest ITest;
 
   public DisposableCon(ITest iTest) {
      ITest = iTest;
   }
 
   public void Dispose() {
 
   }
 }

This class simply declare a Constructor dependency, and implements IDisposable, but in the dispose does not do any stuff. The following test shows you that the container does not keeps a reference nor dispose the inner ITest object.

DisposableCon tran;
using (WindsorContainer ioc = new WindsorContainer(new XmlInterpreter(“config1.xml”))) {
   tran = ioc.Resolve(“TransientDisposableCon”);
}
Assert.IsFalse(tran.ITest.AProperty);

So it is your duty to be sure that the inner objects injected by the container will be disposed correctly.

So this behavior is wrong! WRONG! You should not have to care about releasing the dependencies yourself, the container should keep track of them.

Explaining again. Suppose you have the following components:

DependencyA
  DependencyB
Service

Services depends on DependencyA, which depends on DependencyB. Let’s consider that all of them are transients.

When the “Service” is requested from the container, Windsor creates the dependencies in the bottom-top order:

1. Create DependencyB
2. Create DependencyA
3. Create Service

Service can be returned.

In an ideal world, when Service is released (container.Release(service) or container.Dispose()), Windsor needs to release all of them in the inverse order:

1. Dispose Service
2. Dispose DependencyA
3. Dispose DependencyB

DependencyA is the “burden” of Service. DependencyB is the “burden” of DependencyA. That’s what I call Component Burden. The container being able to keep track of these things that need to be release.

Of course, for 90% of the container usage, you’d use singletons, so that’s why the component burden – which is missing on Windsor and maybe on every other IoC container out there – is not missed that much. It’s only required for non-singletons components that have a decommission phase (for example, Disposable ones).

Anders has started working on this back in March of 2007. He renamed it to component responsability. The implementation wasn’t ideal, so I started reviewing it before applying. Never found the time to finish.

So, if you really want to dig into the internals of the MicroKernel, figure out an optimal strategy that will keep the “burden” only when necessary, make it beautiful, test it, license it as ASL 2.0 and send it to us, we would greatly appreciate it :-)

donjon – a teaser

January 20th, 2008

A picture still worth a thousand words.

donjon1.png

Extending and customizing MonoRail

June 14th, 2007

Recently I’ve built a CMS like infrastructure on top of MonoRail. Much of what I’ve used is described in a earlier post about Portlets, but that covers only one aspect of what has been built and how. I’ve asked my client to release what has been done back to the Open Source community, but I don’t think this is going to happen. Obviously they hold the IP of what has been created, so I cannot share anything. What I’m going to try here, however, is to show where are MonoRail’s extensibility points — at least some of them — and how to use them.

As you know my writing style is a clear-cut, show me the code but let me know the whys and where, with a pinch of poor english. I’m going to try to list the main challenges in building a extensible platform with MonoRail.

The scenario

Suppose you want to develop a general purpose CMS app, much like Cuyahoga. As any decent CMS, adding and changing content must be awfully si\mple, but it cannot stop there. It must be extensible. Pre-built packages of extensions may come with it, but you may also want to expose the API so anyone can develop extensions (think blog, forum, product catalog, shopping basket).

For an example on how to do that using WebForms refer to Cuyahoga itself or dotnetnuke. I’ll not comment on how easier or harder it is to do with MonoRail, leaving that judgment to you.

The core

At this point you have to decide if your app is going to be purely driven by extensions (let’s call it modules from now on) or it will be a core set of features that can eventually be extended by the modules. This is a significant decision with some complex impacts. For example, if the app targets an specific market say, CRM for gadgets sellers, you will have to offer extension points on your API as well.

Let’s just assume that your app is just a host for modules. Even that bring some complexity to the table. How much orthogonal will it be? In other words, how much a module can impact on loaded modules? And how much a module can change the behavior of existing modules on purpose? Being concrete, we could create a single captcha module that affects all other modules that post relevant data back to the app.

Before we get buried into the complexity and the consequences of every path, let’s just assume that it must be orthogonal, with no intentional or unintentional side effects.

MonoRail’s Services

MonoRail is made of a set of services and their default implementation. From those I’d emphasize a few:

  • IControllerTree: it’s a registry of controllers, sorted by the areas
  • IUrlTokenizer: breaks the url requested into pieces to extract the area, controller name and action
  • IUrlBuilder: used to output a url. All standard helpers rely indirectly on it
  • IViewSourceLoader: used by view engines to access the view template stream. This layer of abstraction allows us to sometimes use the filesystem, and sometimes assemblies resources

These services are initialized by that module you add to your web.config and always wonder “what heck does that do?”. Yes, the EngineContextModule. It does more than that, though. But it’s important that you know that this module — and any other ASP.Net module — is only loaded after the Application_OnStart event is fired. This might makes sense, but might make our life a little more miserable. I’ll show why soon.

Adding controllers and views in runtime

Before imagining and playing with the concept of modules, it’s a good thing to learn how we can add controllers and its views in runtime. IControllerTree is the one you’d use to register controllers, and IViewSourceLoader to include views.

Something like:

IControllerTree tree = 
    ServiceContainerAccessor.ServiceContainer.GetService(typeof(IControllerTree));

IViewSourceLoader loader = 
    ServiceContainerAccessor.ServiceContainer.GetService(typeof(IViewSourceLoader));

// Area: empty, controller: home
// url: http://host:port/virtualdir/home/actionname.castle
tree.AddController(string.Empty, "Home", typeof(MyCoolController)); 

// Area: CMS/Admin, controller: Emails
// url: http://host:port/virtualdir/CMS/Admin/Emails/actionname.castle
tree.AddController("CMS/Admin", "Emails", typeof(EmailManagerController)); 

loader.AddAssemblySource(new AssemblySourceInfo("AssemblyName", "NamespaceThatPreceedsViewFolder"));

You can also use the controller tree to “replicate” a controller, and let it handle more than a single url. Another thing I need to mention is that when you’re using Windsor integration, you just need to add a new controller to the container, and it will be added to the controller tree automatically (by the RailsFacility).

But that is not the difficult part, it’s “when” to run such code. But we will get back to it.

Handling unanticipated actions

By default actions are instance methods on your controller classes. You can also use dynamic actions. But another approach is to use a default action.

A default action is a method that will be executed whenever an action cannot be mapped to an instance method on your controller. This is how you use it:

[DefaultAction("Whoops")]
public class MySmartController : Controller
{
    public void Whoops()
    {
       // I'm going to be executed if the user types /mysmart/foobar.castle
       // You can use the property Action to see exactly what has been typed on the URL (regarding the action) 
    }
}

A different folder structure is possible

You don’t need to be restricted to the folder default structure. You can organize views in different folders, in a way that makes sense for you project. The only restriction is that there must be a single common root folder for the views (usually the folder is called “Views” too).

To make the controller render a different view, in a different location, use RenderSharedView, something like:

public class HomeController : Controller
{
    public void Index()
    {
       RenderSharedView("Clients/Something/SomethingElse/index"); 
    }
}

Changing actions and layouts in runtime

The view engine uses the controller’s SelectedViewName property to resolve the view it needs to render. And this property is writable. So it’s not difficult to perform some logic to render different views, or views in different places. I usually do this with a filter.

For Layouts, the same idea applies. The property LayoutName defines the layout to be used. There’s a little trick if you do not want to use the default “layouts” folder, though. When specifying the new path use “/” as the first character.

Putting it all together

Well, not all, but some. I’ve created a sample application that illustrates some of the above topics. It’s an example CMS app that does not have anything of CMS, aside from the name. It illustrates how to get modules working — using Windsor –, controllers being added by modules, views and default actions.

Remember what I said regarding “where to put the code”? Well, I’m using the first BeginRequest to start up all the modules. Looks really odd, and I’d definitely appreciated a better idea:

public GlobalApplication()
{
    BeginRequest += new EventHandler(OnFirstRequest);
}

[MethodImpl(MethodImplOptions.Synchronized)]
private void OnFirstRequest(object sender, EventArgs e)
{
    // This is sample code, so the locking strategy here is, well, a lazy one. 
    // Please implement something more robust for a real project

    if (modulesLoaded) return;

    if (!modulesLoaded)
    {
        modulesLoaded = true;
    }

    ModuleInstallerManager manager = container.Resolve();

    manager.InstallModules();

    BeginRequest -= new EventHandler(OnFirstRequest);
}

Download the sample code.

As usual, comments are welcome.

Some more information about Castle, and why we are not 1.0

March 18th, 2007

As Castle, a more than two years old project, is getting some deserved buzz, it’s a good thing to come on public and say “hey, it’s not perfect”. And I think I might be the best person to let you know what is wrong or missing with it. The good thing about OSS compared to commercial products is that nothing stop us from saying the limitations and problems. I’ll leave the comparison with other company’s strategies as an exercise to the reader.

First, what Castle Project is all about? To fully explain that, I have to give you some more information about my life.

A long long time ago, in a distant galaxy

Back to 2003 when I was a member of the Apache Avalon project I had my view of what could be a close-to-perfection IoC container. In my view it should be minimalist and yet be so easily extensible that it could handle situation we would never anticipate. That is far different from what Avalon, Hivemind and Spring tries to be. Around that time I read The Pragmatic Programmer and the orthogonality concept made a lot of sense to me, that was the almost mathematical design that should be applied to this new container.

Apache Avalon was closed due to a very disruptive community, I’ve sadly resigned from it, and a new project was started: Apache Excalibur. Again I was excited, but the community settled to be a supportive community instead of riding the tide and provide a killer IoC container to the Java community, we had the brains, we had the vote of confidence from Apache. I engaged into endless discussion about this new direction, but I can’t change the world, can I?

September of 2004 I went to London to study english and had an interview at ThoughtWorks. Met some great guys on Geek Nights, some of them I still in touch today. Was reject from ThoughtWorks because I used “final” on my variables (something that was on the guideline for Apache’s projects) and couldn’t agree that my interviewer refactorings made the code flow better (and I still can’t). So if you’re applying for TW remember to swallow your opinion and just nod, there are some very inflated egos there.

Back in Brazil, October of 2004, I was zen. Decided to sell my car and work and study on what I wanted. My passions haven’t changed since then. AI, compilers, transaction management and IoC containers. Founded Castle to provide this IoC container I have been writing for almost two years. In the meantime I was also introduced to Ruby on Rails and decided to create something for real using it. It was distant from 1.0 at the time, and I had a large amount of problems. .Net provided a much richer API than Ruby. While there was Ruby projects to fill the gap, they weren’t mature, and making everything work wasn’t easy, especially on Windows. The performance wasn’t something thrilling too. Nevertheless the simplicity offered by RoR could not be ignored.

I’ve written a book on ASP.Net WebForms, so it was hard to admit that it didn’t work as nicely as RoR. Relying on WebForms in a real, complex system led to major headaches. At this point I decided to broad Castle’s ambitious and provide a complete development stack. The major goal was to simplify our life. That was the itchy I tried to scratch: simplification.

Due to my experience on Apache Avalon I also knew what not to do to create a healthy community. Though I’ve made a lot of mistakes, I can be proud of the community fostered around Castle.

IoC and the .net camp

Though my article on Castle was well received, I understood that the .net camp wasn’t ready for IoC containers. It was wrong to push it if people are not prepared to see the benefits, and just see it as a burden (damn, I have to register components, what is that for?). I can still remember the angry reviews on blogs and blogs comments all around.

The MicroKernel (and Windsor) are the projects I most proud of, and still the projects that receive less attention. Some things that were there since the first SVN commit received some attention last week (ie interceptors support). Seems that MS has to push something to have people realizing what IoC containers are for, what interceptors could do. Having to wait for this MS pushes is kind of depressing.

Castle and the Stronghold

After being requested for consulting a few times, I decided to open a business to offer Castle related support, development and consulting. We received so many requests that shortly I had to start rejecting development and consulting requests. The good thing is that developing for so different project scenarios bring to the surface many weakness on Castle, which were fixed to proceed with the development.

That’s how the validation support came to the surface, many view components and bug fixes. The current documentation state was created in a way that we could use it, instead of always checking the source code. While this is an improvement I admit that it still lacking documents.

Offering a ‘throat to choke’ is also a good way to lowering the barriers for adoption. We know that some companies won’t embrace anything unless there’s an entity behind it that can be sued in the event of any problems.

What is missing

OSS projects have a different life cycle compared to commercial or products. On Castle we make a release and then start to implement all crazy ideas that were voiced. Stabilize the code and repeat.

Some things, in my perception, stop us from releasing a 1.0. As you will see there aren’t many, and I’m trying do decide if we should work on them now and release a 1.0, or release another Candidate and continue to work on the missing pieces.

The Component Burden, on the MicroKernel

This is somewhat difficult to explain, but stay with me. Every time you request a component from the container it might have dependencies on components with different lifestyles. For example, you might request a component that is transient, and depends on transient and pooled instances.

Today you can release the transient (root) instance, but the dependencies won’t be properly released. This is a major limitation, but fortunately 99% of scenarios do not depend on this. Anyway this is not an excuse to not implement this support.

Btw, when I say properly release, what I mean is the decommission steps won’t run and the component will not be returned to the lifecycle manager. For pooled components that means that it wont returned to the pool. Components that implement IDisposable wont have the Dispose being invoked by the container. But rest assured that the container will not hold instances creating a memory leak.

Container Scopes

Another complex usage of containers and very useful for complex situations were components (and possibly business logic) can vary depending on some external factor. The idea is to create an hierarchy of containers. The top level container contains the invariant components, or the system core. Lower in the hierarchy you’ll find container specifically set for a client, or for a host name, or for anything that indicates the necessity of a different set up.

While I’m involved with at least three projects that will require this support at some point, I still don’t have enough use cases to implement it right. Bill Pierce has implemented almost everything required, though, but there are some issues on the backlog to be resolved.

Validator component and ActiveRecord validation infrastructure

We have to drop AR validation infrastructure in favor of the new validation component. No point in maintaining two.

ActiveRecord

While AR can make you map your database in no time, it also leads to a Domain Model that is tightly coupled with your entities on the database. Sometimes this is a big problem, so careful when adopting it on an app that will ask for a richer domain model.

MonoRail’s controller testability

The TestSupport component offered by MonoRail is totally flawed. It is useful for us, as we can use it to test how MonoRail is correctly integrated with the ASP.Net API, but it useless for any enterprise project.

The approach Aaron explains on his blog is a good way to test controllers, and I think MonoRail should offer something like that out of the box. I tried to refactor it last night to accomplish that. I gave up.

I should have used TDD to code MonoRail. Using that small time window (getting home after work, dining in front of the computer while coding changes) unsurprisingly does not create the best design. That is something I can only fix on MonoRail 2.0, or with a heavy refactoring. I’m still thinking about it…

NVelocity and Brail view engines could be better

We could work on a pre-processor that could translate more pleasant constructions into method calls or directives.

I for one dislike the usage of view components from NVelocity, but there isn’t another way to integrate it with their AST. A new view engine is being considering for a long time. IronPython view engine is also on the backlog.

View component parameters bindings

Grabbing and converting data from the ComponentParams dictionary is boring. We need a way to wire this data directly to view component’s properties.

Generators

While we have a project generator, it is not enough. Creating complex html forms is repetitive. If you have the object the form should fill, we can have the computer generating the form. You can make a change here and there, and this is something I’m working on. Marc-Andre has created a Rails-like generator, and we would like to merge it with the VS.Net add in generator. Not an easy task, though.

ActiveWriter solves the ActiveRecord generation and in a divine way.

Support for .net 1.1

This is something that was requested and with some heat, but the way DynamicProxy 2 was coded makes it an almost impossible task. I’m considering dropping this support, even if that will turn some users into enemies. :-(

We tried to do it last Friday, gave up. I tried yesterday and got sick..


As you see, lots of issues to take care of, and it’s always an opportunity to consider getting involved with Castle. Rest assured it’s an experience where everyone learns a lot.

Web Client Software Factory vs MonoRail

March 15th, 2007

David Hayden asks “Can MonoRail compete with WCSF?”. I’d rather say “Can WCSF compete with MonoRail?” ;-)

A fair analysis would require a deep understanding of both projects. I’ll investigate WCSF in a near future, but for now, I’ll just give David some clues about some MonoRail features, as he lists what WCSF is going to support:

- Data-Drive UI: I’m not sure exactly what he meant by that. I can say that MonoRail has scaffolding support and a combination of FormHelper/DataBindAttribute is enough to save you a good number of repetitive lines of code.

- Validation: Castle has the Castle.Component.Validator, and MonoRail is fully integrated to it. This screencast might explain it a little better.

- UI Responsiveness: is that Ajax? MonoRail just relies on prototype to offer ajax support, although you can use any library you want. MonoRail also supports JS generation for more complex scenarios.

- Complex workflows: not sure what that means. As Ayende pointed out, we have wizard support.

On top of that, if you know what you’re doing, you can enable Windsor integration. That means that MonoRail will use Windsor to resolve Controllers, ViewComponents and Filters (optionally). So you gain all facilities and features offered by Windsor on your MR project. If you don’t like Windsor, you can even use Spring.

And last but not least, Castle is an OSS project with a strong community behind. Want to ask us “why did you implement this way and not some different way?”, join the list. Bumped into a bug, check our issue tracker. Want to ask a lightweight question, check our forum. And if you show commitment to the project, you will gain access to our SVN. While for some these might be not important things to reason, it’s clearly becoming something to pay attention for a growing number of people.


Update: Brian has used both, and shared his thoughts.

Windsor container and “environments”

February 12th, 2007

I bumped into a challenge today that might be of interest to others. We wanted to have a single web site project, and use it to run tests and to the usual development. During development it should use the standard devel database, for test cases, it should use the Test database which is always dropped/re-created by the test cases.

The problem is that we only have one web.config, and one setting for the connection string. Fortunately the connection string is kept by Windsor, in a properties.config but we couldnt think of a way to signalize the environment to it (test/devel).

Our solution was to create a new entity on Castle Windsor’s: IEnvironmentInfo. This interface allows a programmer to return the environment’s name based on, well, anything he wants. In our case we use IIS and VS.Net’s web server. The latter for standard development, the former to run the test cases. We could then use the web server port to distinguish the environment. If the application is running on 80 (IIS) it is being tested, otherwise it’s just a developer working on it.

Whatever is returned by IEnvironmentInfo is transformed into a define to Windsor’s configuration. So you can have

<configuration>
    <properties>
<?if devel ?>
        <connectionstring>...</connectionstring>
<?else?> <!-- this is for test -->
        <connectionstring>...</connectionstring>
<?end?>
    </properties>
</configuration>

In our case we have:

public class WebEnvironment : IEnvironmentInfo
{
    private readonly HttpApplication app;

    public WebEnvironment(HttpApplication app)
    {
        this.app = app;
    }

    public string GetEnvironmentName()
    {
        return app.Context.Request.Url.Port == 80 ? "test" : "devel";
    }
}

And all we have to do is pass that to Windsor when we instantiate it:

container = new WindsorContainer(new XmlInterpreter(), new WebEnvironment(this));

This might make no sense at all if you havent faced the challenge yet, but make sure you re-read this post when it clicks for you ;-)