I've experimented with WrapFactory. I understand how/when a Java object gets
wrapped into a Scriptable object. When I access my domain object I get a
wrapped object. The problem is when I go to set a value of the domain object
with another domain object. The new value will be a wrapped object. It's a
headache but not unmanageable to unwrap the new value. The big problem is
when dealing with collections. Consider this Java:
public class DomainEntity {
private DomainEntity parent;
private List<DomainEntity> children;
...getters/setters for parent and children
}
public class WrapperEntity {
private DomainEntity delegate;
// getter/setter for delegate
public void setParent(WrapperEntity wrappedParent) {
delegate.setParent(wrappedParent.getDelegate()); // bearable
}
public List<DomainEntity> getChildren() {
return delegate.getChildren();
}
}
and this JavaScript:
var domain = new DomainEntity(); // wrapped to WrapperEntity
domain.getChildren().add(new DomainEntity()); // fails because new object is
really a WrapperEntity (ok, it doesn't actually crash but it does add a
WrapperEntity to a List of <DomainEntity>.
Is there any way to automatically unwrap the object being added to the
collection? Do I need to wrap all collections and implement add(), put(),
etc. in order to unwrap it as it's being added?
Has anyone run into this?
--
Daryl Stultz
_____________________________________
6 Degrees Software and Consulting, Inc.
http://www.6degrees.com
mailto:da...@6degrees.com
I'm currently experimenting with WrapFactory and
substituting NativeJavaObjectExt for NativeJavaObject and overriding unwrap:
public class NativeJavaObjectExt extends NativeJavaObject {
// constructors...
public Object unwrap() {
Object wrapped = super.unwrap();
if (wrapped == null) return wrapped;
if (wrapped instanceof Wrapper) wrapped = ((Wrapper) wrapped).unwrap();
return wrapped;
}
}
So the idea is to go from NativeJavaObject (Scriptable) -> DomainEntity
skipping the wrapper. This leads to this error when domain.getChildren() is
called.
org.mozilla.javascript.EvaluatorException: Java method "getChildren" was
invoked with WrapperEntity@df1651 as "this" value that can not be converted
to Java type WrapperEntity. (<test>#38)
Hmm, can't be converted to same type?
> Is there any way to automatically unwrap the object being added to the
> collection? Do I need to wrap all collections and implement add(), put(),
> etc. in order to unwrap it as it's being added?
>
> Between a WrapFactory and collection wrappers, I think I've finally settled
on a solution that will work. My wrapper classes will be pretty
straightforward overriding add/put, etc. to unwrap the JS classes and put
the domain delegate into the collection. The proof of concept with an
"AutoUnwrappingList" appears to be working.