Friday, December 18, 2009

Spring RMI callback

One open issue of Spring remoting via RMI is that it hasn't supported RMI callback as discussed in here.The conventional RMI callback requires the interface implements Remote and the methods throw RemoteException. Hereby it is not very nice.

WlcfgRmiCallbackProxyFactory is implemented to provide such support by customizing Spring remoting code. It provides a remote proxy which intercepts method invocation on callback interface (non-RMI). It uses wlcfgRmiCallbackExporter which wraps a non-RMI service into remote object via RmiInvocationHandler and export it. Note that it doesn't bind to RMI registry.


public class WlcfgRmiCallbackProxyFactory extends RemoteInvocationBasedAccessor
implements MethodInterceptor, Serializable {

private static final long serialVersionUID = 5685339356048366732L;

private Class callbackInterface;
private RmiInvocationHandler invocationHandler;

public WlcfgRmiCallbackProxyFactory(Object callback, Class callbackInterface) {
this.callbackInterface = callbackInterface;

WlcfgRmiCallbackExporter exporter = new WlcfgRmiCallbackExporter();
this.invocationHandler = exporter.getRmiInvocationHandler(callback,
callbackInterface);
}

public Proxy getProxy() {
Proxy proxy = (Proxy) ProxyFactory.getProxy(callbackInterface, this);
return proxy;
}

@Override
public Object invoke(MethodInvocation invocation) throws Throwable {
try {
return invocationHandler.invoke(createRemoteInvocation(invocation));
} catch (RemoteException re) {
throw RmiClientInterceptorUtils.convertRmiAccessException(
invocation.getMethod(), re, RmiClientInterceptorUtils.isConnectFailure(re), ClassUtils.getShortName(callbackInterface));
} catch (InvocationTargetException ex) {
Throwable targetEx = ex.getTargetException();
RemoteInvocationUtils.fillInClientStackTraceIfPossible(targetEx);
throw targetEx;
}
}
}

public class WlcfgRmiCallbackExporter extends RmiBasedExporter {

private static Log log = LogFactory.getLog(WlcfgRmiCallbackExporter.class);

public RmiInvocationHandler getRmiInvocationHandler(Object callback, Class callbackInterface) {
this.setService(callback);
this.setServiceInterface(callbackInterface);
this.setRegisterTraceInterceptor(false);

// wrap non-RMI service into a remote object
Remote exportedObject = getObjectToExport();

try {
UnicastRemoteObject.exportObject(exportedObject, 0);
} catch(RemoteException e) {
log.error("Failed to export " + getServiceInterface().getName(), e);
}

log.info("Export object " + getServiceInterface().getName());
return (RmiInvocationHandler)exportedObject;
}
}


There are two types of proxy: JDK dynamic proxies or CGLIB. Spring can use both for creating proxies at runtime. One is based on interface, the other for concrete class as discussed in here. With the invocation of ProxyFactory.getProxy(), a Proxy class is generated at runtime which implements all of the supplied interfaces. It is fancy that the returned proxy is an instance of the interface and can be casted as:

WlcfgRmiCallbackProxyFactory proxyFactory = new WlcfgRmiCallbackProxyFactory(this, IHostSessionListener.class);
hostService.registerForNofitications((IHostSessionListener)proxyFactory.getProxy());

Two common usages of proxies are demonstrated above:
- Line 18, add interceptor so that a normal method call becomes remote call.
- Line 47, limit method access to target source object - only methods defined in serviceInterface are exposed. Otherwise, with reflection method call, all methods would be exposed.

Thursday, November 19, 2009

Join (association) Table

one-to-many can be mapped with join table as many-to-many (unique="true"), it gives some flexibility that many side doesn't need to have FK to one side, hence they are more loosely coupled. The relation is kept in a separated table. E.g., both Template and Task have one-to-many relationship with DeployWlc. Then we can keep DeployWlc table intact and have separated join tables ce_template_deployWlc, and ce_task_deployWlc.


<class name="Person">
<set name="addresses">
<key column="personId" not-null="true"/>
<one-to-many class="Address"/>
</set>
</class>

<class name="Person">
<set name="addresses" table="PersonAddress">
<key column="personId"/>
<many-to-many column="addressId"
unique="true"
class="Address"/>
</set>
</class>

For many-to-one, we can also have join table, so that on database table, many side doesn't have FK column, but on java object, it has the reference. If both side defines the join table, it creates a bidirectional one-to-many/many-to-one association using a join table.

<many-to-one name="person" class="Person" column="personId"/>


<key column="addressId" unique="true"/>
<many-to-one name="person" class="Person" column="personId"/>


A cascade myth: the CASCADE on collection is not for join(association) table, but for the base table on the other side. The data entries on association table are updated without cascade setting.

The association could be strong or weak. For strong association, define Hibernate cascade "all, delete-orphan" will do it; For weak association, we may run into some issues. For example, the bidirectional association table, the *inverse* side may have FK constraint violation issue. E.g., ApGroup(inverse) <--> Ap, the deletion of ApGroup will fail since it is referenced by association table. It is OK for Ap deletion which is taken care of by Hibernate. So the solution is add database level "on delete cascade" for FK constraint tbl_apGroup_ap -> apGroup.

alter table tbl_apGroup_ap add index FK4F9906CCF1F23ED3 (apGroupId), add constraint FK4F9906CCF1F23ED3 foreign key (apGroupId) references tbl_apGroup (id) on delete cascade;

It means the deletion on parent table (pointed) tbl_apGroup will cascade the deletion on child table tbl_apGroup_ap.

one-to-one is mapped with many-to-one (unique="true") with foreign key association. If using one-to-one, it is using primary key association.

Friday, September 4, 2009

AOP & OOP

OOP inheritance is good for behavior along vertical relationships;
AOP is good for behavior that applies cross horizontal layers (cross-cutting concern)

AOP works with OOP, doesn't replace OOP.

See here.

Tuesday, June 2, 2009

Add Tooltip on disabled button


<div style="position:relative;text-align:right;">
<span id="Configure_overlay" style="z-index:2; position:absolute; background-color:white; opacity:0.60; filter:alpha(opacity=60); width:125px; height:20px; display:none;"></span>
<input type="button" name="Configure" id="configure" value="Configure" onclick="clickMe()"style="font-size: 7pt;width:125px">
</div>

The overlay must be absolute positioned to be placed right on top of the button. Because the default position is static which means overlay will occupy space in document flow. For postion:absolute, the element is removed from the document. The surrounding relative div is required to deal with scroll case. Without it, the overlay is relative to the body and is fixed whereas the button may move in a scrolling area.

function disableCustomConfig(rId, msg) {
var customConfigOverlay = document.getElementById("Configure_overlay");
var customConfigTooltip = new YAHOO.widget.Tooltip("customConfigTooltip", {
context:"Configure_overlay", text:msg, showDelay:0, hideDelay:0, disabled: false
});

customConfigOverlay.style.display = "";
customConfigTooltip.cfg.setProperty("text",msg);
}

Wednesday, May 6, 2009

Javascript Closures

A re-introduction to JavaScript and Simplify Scope with Javascript Closures have a good introduction on the concept of javascript closures. A closure is the combination of a function and the scope object in which it was created. Closures let you save state. The memory of a closure can be freed only when the returned callMe is no longer accessible.

function createClosure(scope_) {
    var origScope = scope_;

    var callMe = function() {   // inner private function
        origScope.somefunc();
    }
    return callMe;    // inner function returned
}

// preserve 'this'
someobject.someproperty = createClosure(this);

function makeAdder(a) {
    return function(b) {
        return a + b;
    }
}

x = makeAdder(5);  // each call to the outer function create a closure
y = makeAdder(20);

x(6)    // return 11, with scope object a=5, 
        // a closure preserves the arguments and variables in all scopes it contains. 
y(7)    // return 27, with scope object a=20

Any nested function forms closure. It doesn't have to be returned, it can be an anonymous inner function as below. We should try to avoid closure whenever possible, it may potentially cause memory leak if there exists circular reference between JS object and DOM object.
function assignOnclick(element) {
   element.onclick = function() {
      this.style.backgroundColor = 'blue';
   };
}

See: Functions and function scope

Tuesday, May 5, 2009

Rounded Box



<div class="boxcontainer">
<div class="t"><div class="b"><div class="l"><div class="r">
<div class="bl"><div class="br"><div class="tl"><div class="tr">
<div class="boxlabel">{LABEL}</div>
<div class="boxcontent">{CONTENT}</div>
</div></div></div></div>
</div></div></div></div>
</div>


.t {background: url(/images/dot.jpg) 0 0 repeat-x;}
.b {background: url(/images/dot.jpg) 0 100% repeat-x;}
.l {background: url(/images/dot.jpg) 0 0 repeat-y;}
.r {background: url(/images/dot.jpg) 100% 0 repeat-y;}
.bl {background: url(/images/bl.jpg) 0 100% no-repeat;}
.br {background: url(/images/br.jpg) 100% 100% no-repeat;}
.tl {background: url(/images/tl.jpg) 0 0 no-repeat;}
.tr {background: url(/images/tr.jpg) 100% 0 no-repeat; padding: 5px;}

.boxlabel {
float:left;
display:inline;
position:relative;
top:-5px;
left:5px;
padding: 0px 2px 0px 2px;
background-color:#FFFFFF;
color:#1E90FF;
font-size:10;
font-family: Arial;
}

.boxcontent {
position:relative;
top:-5px;
text-align: left;
}

.boxcontainer {
margin: 5px;
}

The boxlabel float left with relative/top/left position to adjust its position. And its background-color is set to make the background opaque, otherwise, it is transparent and the below border line is shown.

Also, note that we have a padding on the last img div, to avoid text inside the box overlap with image.

See: CSS and Round Corners: Build Boxes with Curves

Tuesday, April 28, 2009

object references an unsaved transient instance

    Match m = new Match();
    m.setPlayDate(playDate);

    for (int playerId : playerIds) {
        Player p = playerDao.read(playerId);
     
        // update player's stat
        PlayerStats ps = playerStatsDao.findByPlayerAndYear(playerId, year);
        ps.increment();
        playerStatsDao.saveOrUpdate(ps);
   
        m.addParticipant(p);
    }
  
    matchDao.persist(m);

org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: poker.db.model.Match.

On 2nd iteration of the loop, in line 8, while querying playerstats, it threw the above exception. It was doing a *flush* before the query since playerstats was dirty atm.

I really made an effort to dig into it. It turns out that it was caused by the *inverse* setting of a many-to-many relationship. I used to think it doesn't matter as long as you set either side of it.

In Class Match:
public void addParticipant(Player p) {
    getParticipants().add(p);
    p.getMatches().add(this);
}

PlayStats * <---> 1 Player * <---> * Match
All relationships are bi-directional. PlayStats is owner side by default for the many-to-one. And I set (inverse=true) on Player side by rolling a dice. I thought when I called match.addPaticipant(), both collections are updated and the relation is built. It shouldn't make any difference by setting inverse.

I imagine that the reference link is uni-directional for underlying presistence with the inverse setting. When Player is the owner of this many-to-many, the link is PlayerStats ->Player->Match, since Match object is a transient object (not saved yet) when we tried to save/update PlayerStats, it threw the above exception. However, if we change the owner side to Match, the reference link is broken, PlayerStats->Player, Match->Player, save/update PlayerStats has nothing to do with the state of Match object anymore. Thus it runs perfectly!

* Inverse=true means relationship owner to avoid unnecessary update. Basically on many side, insert a new record already with FK value, you don't need another update statement to set it.
http://www.mkyong.com/hibernate/inverse-true-example-and-explanation/

Alternatively, the second solution is to set FlushMode of query in playerStatsDao.findByPlayerAndYear().

public PlayerStats findByPlayerAndYear(int playerId, int year) {
    String queryString = "from PlayerStats ps where ps.player.id = :playerId "
                          + "and ps.year = :year";
    Query query = getSession().createQuery(queryString)
                .setInteger("playerId", playerId)
                .setInteger("year", year)
                .setFlushMode(FlushMode.COMMIT);
    return (PlayerStats) query.uniqueResult();
}

By default, FlushMode is AUTO, flush synchronize the in-memory persistent object with underlying database store by running the SQLs, the changes not visible to others until tx.commit() though.

Note that flush occurs in three cases: transcation commit, session.flush() invoked or before the query. By changing flush to tx commit time, we avoid the "object references an unsaved transient instance" issue. It is also good for performance.

Cascade

We may get FK constraint exception when we try to delete the parent record (e.g., Player table). We can define database level cascade such as "on delete cascade|set null".


create table player_stats (
`id` integer unsigned not null auto_increment,
`player_id` integer unsigned not null,
primary key (`id`),
foreign key (`player_id`) references player (`id`) on delete cascade
)
engine = InnoDB;

Note that it is uni-directional. Only works for parent -> child cascade.

With Hibernate cascade, we don't need to define this on DDL. And the cascade is more flexible - bi-directional. We can cascade change from any side following the association link (one-to-many, many-to-one, many-to-many etc). It handles cascade on higher level, i.e., entity to entity. On example is tbl_apGroup, tbl_apGroup_ap, tbl_ap. The database cascade would be defined on FK tbl_apGroup_ap referencing to tbl_apGroup. But Hibernate cascade is from domain object ApGroup to Ap.

Friday, April 24, 2009

ConcurrentModificationException

If you try to modify a list while iterating through it, then you will encounter the ConcurrentModificationException.

The foreach loop is *is* syntactic sugar for iterating. However, you need to call remove on the iterator - which foreach doesn't give you access to.


for (SgeApAdapter apAdapter : apsToUpdate) {
if (...) {
apsToUpdate.remove(apAdapter);
}
}


It throws ConcurrentModificationException. We have to use iterator explcitly to remove item in collection.

Wednesday, April 8, 2009

Process.getInputStream()

The concept of an InputStream always refers to data coming IN to the thread which is invoking the InputStream method. Similarly, an OutputStream always refers to data pushed OUT by the thread which is invoking the OutputStream method.

The only place where this is really tricky is when you are working with Process objects. The getInputStream() method of Process returns a Java InputStream that reads from the standard output stream of the running Process.

The key thing to remember when using Runtime.exec() is you must consume everything from the child process' input stream. Otherwise, the child process may hang due to the buffer filling up.


Process proc = Runtime.getRuntime().exec(cmd);

StreamGobbler errorGobbler = new StreamGobbler(proc.getErrorStream());
StreamGobbler outputGobbler = new StreamGobbler(proc.getInputStream());
errorGobbler.start();
outputGobbler.start();

if (proc.waitFor() != 0) {
System.out.println("RestoreMain: Migration failed.");
result = false;
}


StreamGobbler

public void run() {
try {
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line = null;
while ((line = br.readLine()) != null) {
// ------------------------------------------------------------
// Exhaust Stream
// ------------------------------------------------------------
log.debug("StreamGobbler: " + line);
}
} catch (Exception e) {
log.debug("Failed to exhaust stream.");
}
}

Friday, March 20, 2009

Inner Classes

Inner Classes gives us a good introductions. Inner classes come in four flavors:: Static member class, Member class, Local class, Anonymous class. And the advantages of inner classes can be divided into three categories: an object-oriented advantage, an organizational advantage, and a call-back advantage.

The OO advantage is not well known for me compared with call-back advantage. One good example is to separate search algorithm as inner class in Tree class. Another is to nest MuListElement class inside BeastGetActiveMuRespMsg - composition relationship in UML.


public class BeastGetActiveMuRespMsg {
private int retCode;
private MuListElement[] muList;
....
public static class MuListElement {
private String macAddress;
private String ipAddress;
...
}
}

A static member class is a static member of a class. Like any other static method, a static member class has access to all static methods of the parent, or top-level, class.

Like a static member class, a member class is also defined as a member of a class. Unlike the static variety, the member class is instance specific and has access to any and all methods and members, even the parent's this reference.

Tuesday, March 17, 2009

Javascript/css/image loading

In Q&A-Javascript Execution & Onload Techniques in Web Browsers, It states that "Inline and external scripts are executed in the order in which they appear in an (x)HTML document…It should be noted that the loading of an (x)HTML page is halted while loading external JavaScript files."

In 14 Rules for Faster-Loading Web Sites, Rule 6 “Put script at the bottom” is used to avoid such halting. See Example.

Other resources (css/images) are loaded asynchronously and you cannot be certain when they will complete.

onload vs onDomReady
The onload event fires when the document and it's script/style/image resources are loaded, but you probably don't want to wait for images if you are doing any javascript when the page is loaded. Also, it may cause UI errors if the user tries to interact with the page before the JavaScript event handlers have been applied to the DOM via the onload event - a limitation of onload event. Instead, use something like jQuery's "ready" event or fire your own "DOMReady" event by placing a script tag at the end of the body:


<body>
<!-- your page contents here -->
<script type="text/javascript">
// DOM is ready, do scripty stuff now
DOMReady();
</script>
</body>

Single threaded script processing
The client-side javascript is single threaded. This means that the parsing of (x)HTML documents stops while scripts are loaded and executed, and that web browsers stop responding to user input while event handlers are being executed.

This is a good thing, and a bad thing. It's good because you can rest comfortable knowing that two event handlers will never run at the same time. Also, you can manipulate document content knowing that no other thread is attempting to modify the same piece of content.

It's bad in that intensive scripts can hold up the user experience by causing periods of unresponsiveness from a JavaScript driven UI.

Wednesday, January 21, 2009

Hibernate in Action (notes)

- Two paradigms: SQL/JDBC relational model vs. object-oriented domain model
SQL operations such as projection and join always result in a tabular representation
of the resulting data. This is quite different than the graph of interconnected
objects used to execute the business logic in a Java application.

  • Granularity
  • Subtype
  • Identity
  • Associations
  • Object graph navigation

* PK update issue: not only update PK, but also FK in reference tables if using a column like USERNAME as PK. It is recommended to use surrogate keys (with no meaning to the user) as PK wherever possible.

Tuesday, January 20, 2009

JTA - Java Transaction API


The numbered boxes around the transaction manager correspond to the three interface portions of JTA:

1—UserTransaction—The javax.transaction.UserTransaction interface provides the application the ability to control transaction boundaries programmatically. The javax.transaction.UserTransaction method starts a global transaction and associates the transaction with the calling thread.

2—Transaction Manager—The javax.transaction.TransactionManager interface allows the application server to control transaction boundaries on behalf of the application being managed.

3—XAResource—The javax.transaction.xa.XAResource interface is a Java mapping of the industry standard XA interface based on the X/Open CAE Specification

Notice that a critical link is support of the XAResource interface by the JDBC driver. The JDBC driver must support both normal JDBC interactions, through the application and/or the application server, as well as the XAResource portion of JTA.(So called XP compliant resource manager)

See: Understanding JTA—the Java Transaction API

Friday, January 16, 2009

ThreadLocal

The ThreadLocal class behaves much like the various Reference classes in java.lang.ref; it acts as an indirect handle for storing or retrieving a value. Listing 1 shows the ThreadLocal interface.


public class ThreadLocal {
public Object get();
public void set(Object newValue);
public Object initialValue();
}

See: Exploiting ThreadLocal to enhance scalability


public class EntityChangeTracker {

private static ThreadLocal<List<EntityChange>> entityChangeThreadLocal = new ThreadLocal<List<EntityChange>>() {
protected List<EntityChange> initialValue() {
return new ArrayList<EntityChange>();
}
};

public static List<EntityChange> getEntityChanges() {
return entityChangeThreadLocal.get();
}

public static void addEntityChange(Entity<?> e, AuditOperation opr) {
List<EntityChange> list = entityChangeThreadLocal.get();
list.add(new EntityChange(e, opr));
}

public static void clear() {
entityChangeThreadLocal.get().clear();
}
}

volatile keyword

Lock free, an alternative to synchronization and lock. A volatile variable is one whose value is always written to and read from "main memory" and not cached by register or thread. That means that different threads can access the variable.

A typical example of a "stop request" flag allowing one thread to signal to another to finish:


public class StoppableTask extends Thread {
private volatile boolean pleaseStop;
public void run() {
while (!pleaseStop) {
// do some stuff...
}

public void tellMeToStop() {
pleaseStop = true;
}
}

If the variable were not declared volatile (and without other synchronization), then it would be legal for the thread running the loop to cache the value of the variable at the start of the loop and never read it again.

See: The volatile keyword in Java 5

Tuesday, January 13, 2009

JVM GC



-Xloggc:[filename] is used to log GC. verbose:gc output to stdout.
-XX:+PrintGCDetails is to display more GC details on stdout.

There are two primary measures of garbage collection performance. Throughput is the percentage of total time not spent in garbage collection, considered over long periods of time. Throughput includes time spent in allocation (but tuning for speed of allocation is generally not needed.) Pauses are the times when an application appears unresponsive because garbage collection is occurring.

Reference:
[1] Java theory and practice: A brief history of garbage collection
[2] Java theory and practice: Garbage collection in the HotSpot JVM
[3] Tuning Garbage Collection with the 5.0 Java[tm] Virtual Machine

Friday, January 2, 2009

Mutablity


private MutableLocation loc = new MutableLocation();
public Location getLocation() {
return loc;
}

Internally, you store a mutable object, but return it typed as a simple interface when you want to allow only read-only access.This is done to preserve encapsulation and prevents the location fields from being modified by external code.