How to do object composition and population the coldbox way

I am just trying to understand how best to implement and use Model Data Binding and the composeRelationships flag in populateModel.

Trivial example.

So I have a User object which has a property of Address which as you might assume is a class of its own with it’s own service and object model.

What would be the preferred/standard way to manage this in a non ORM configuration.

User
component accessors="true"{

	// Properties		
	property name="username" type="string";
	property name="address" type="Address";


	/**
	 * Constructor
	 */
	address function init(){
		return this;
	}

}


Address
component accessors="true"{

	// Properties
	property name="line1" type="string";
	property name="line2" type="string";
	property name="city" type="string";
	property name="state" type="string";
	property name="zip" type="string";

	/**
	 * Constructor
	 */
	address function init(){
		return this;
	}
}

The UserService checks when asked to create or retrieve a User to see if they have an existing Address assigned if so it either creates a new address instance or retrieves and assigns it to the address property.

In the case of a new User:

oUser.address = wirebox.getInstance("Address");

Can I accees the address properties straight up like this?
prc.oUser.address.city
or
prc.oUser.address.getCity()

In my web page I would have something like this:

<td valign="top" class="basicText">
	#html.inputField( type="text", name="address.city", bind="prc.oUser.address", bindProperty="city", maxlength="50" )# *
</td>

In my controller then would I just do this to populate both the User and Address properties that make up the oUser object?

var oUser = populateModel( model=userService.new(), memento=getRequestCollection(), composeRelationships=true );

How does Coldbox know about the relationship, is it all in the default Metadata of the object, are there certain situations in which I have to be extra careful?

How deep can I take this?

Is the performance good on a complex object or should I manually handle these kinds of relationships?

I do not want to have to reinvent functionality that already exists in a performant way, but all of the sample code and even the tests that I have looked at all use ORM, which I cannot use for other reasons.

Thank you

Ok, so I actually just tried to implement this.
The address structure exists in the rc

address	
Struct (ordered)
line1	string	Main Street
line2	string	
city	string	City
state	string	ST
zip	    string	90210

When I execute the populateModel() call I get this error:

BeanPopulator.PopulateBeanException
Message	Error populating bean models.user with argument address of type class lucee.runtime.type.CastableStruct.
Detail	the function is located at [/app/models/user.cfc]<br>Invalid call of the function [setAddress], first Argument [address] is of invalid type, Cannot cast Object type [Struct] to a value of type [Address]<br>[{Raw_Trace={system.core.dynamic.beanpopulator_cfc$cf.udfCall2(/coldbox/system/core/dynamic/BeanPopulator.cfc:501)}, codePrintPlain={499: // Populate the property as the value obtained whether simple or related

It is very clear what is happening here, the default setter for address is being called and being passed a struct rather than an instance of address.
Obviously I can override the setter with an explicit one but I assumed that populateModel() would handle this for me. Do I not understand “composeRelationships=true”?

Unfortunately, relationship composition does not work in a non-ORM context, because the BeanPopulator does not know how to compose - and falls back to the setter.

Your best bet is to manually create the Address object (you can populate it from that struct key) and then assign it as the Address of the struct.