Datamoil blog. Undocumented solutions.

I write solutions to the problems I can't find much about elsewhere on the Web, also some code/script snippets that are absolutely awesome and make my life easier. Will be glad if someone finds these posts interesting and helpful!

Monday, May 3, 2010

Accumulative sorting in ADF 10g tables

Just what the title says.

In an application there were a few tables filled with results of some queries. I haven’t yet figured out why, but it was of a high importance to the client that all the tables had accumulative sorting (like the order by clause in SQL). This requirement took me a while to figure out how to implement, whilst the solution was quite elegant and pretty small to write it here.

So, there’s a table with results of a search (the query really doesn't matter as the entire sorting solution will be implemented in the view layer)


The whole trick is to set sortListener=”#{CustomersBean.onSort}” for the table. The backing code for this sortListener is found in the backing bean named CustomerBean.

And that’s pretty much it. The table is now sortable accumulatively: you can hit customerid first, then name, then surname etc. the resulting table will look similarly to what produces SQL clause order by customerid, name, surname, etc.
Hope this helps.

How to dispose a body

Just don’t tell me you never thought about it!

First, be smart from the very beginning. Pulverize all teeth, burn off fingerprints, and disfigure the face. Forcing a DNA test to establish identity (if it ever comes to that) might introduce the legal/forensic hurdle that saves your ass down the line. An unidentifiable body can, in a pinch, be dressed in thrift store clothes and dropped in a bad part of town where the police are less likely to question it. I don’t recommend that disposal method, I’m just saying an easily identifiable body is an even bigger threat than the opposite.

Assuming you have it inside a house where you can work on it a bit, the first thing you want to do is drain it of fluids. This will make it easier to cut up, and slow decomposition a little bit. The best way to do this quick and dirty is to perforate the body with a pointed knife, and then perform CPR on it. Cut the fronts of the thighs deep, diagonally, to slit the femoral arteries. Then pump the chest. The valves in the heart will still work when dead, and the springback of the ribcage can put apply a fair amount of suction to the artria. Do this in a tub. Plug the drain, and mingle lots of bleach with the bodily fluids before unplugging the drain to empty the tub. This should help control the stench of death, which would otherwise reek from your gutter gratings. Do everything you can to control odors. Plug in an ionizer, burn candles, leave bowls of baking soda everywhere. Ventilate the room in the middle of the night, but otherwise keep it closed. Keep the body under a plastic sheet while it’s in the tub.

If you want to bury, I recommend separating the body into several parts, and burying them separately. For one thing, it’s easier to dig a deep enough hole for a head than for an entire body. this reduces your chances of being discovered while you are actually outside and digging the grave.
That is the one thing you can’t do inside the doors of your house, and represents a vulnerable moment you want to keep brief, under 2 hours. Do it between 3 and 5 am. It’s also less likely for someone to call the police if their dog digs up some chunk of meat, than if they dig up an enitre body. They may assume it’s an animal carcass disfigured by decomposition, and leave it alone or dispose of it. It’s also more likely that the dog will consume all of it before anyone knows the difference. A whole skeleton is another story. You can cut a body into 6 pieces faster than you think. It’s not much different than boning a chicken, but it takes more work, a big knife, and time. A hammer will be useful for pulverizing joints or driving the knife deep where it doesn’t want to go. Anyway it’s wise to crush as much of the skeleton as you can along the way. It will aid in making the body less identifiable for what it is as it decomposes.

Don’t return to the same site 6 times for 6 burials.You’ll attract suspicion from anyone nearby, and you’ll wind up placing the body parts close enough together to be found by any serious investigation. Put them in plastic bags with lots of bleach, and store in a freezer until you have enough time to bury them all.

Depending on what tools you have available, you may find that you’re get really good at deconstructing the body. You might prefer to slowly sprinkle it down a drain without leaving your house. This avoids the long-term risk of discovery associated with burial, and the overwhelming supply of bacteria in a sewer accellerates deconomposition, whil e providing a convenient cover smell.

Truly grinding down a body takes a lot more work, and you run the risk of fouling your plumbing and calling in a plumber. So don’t try it unless you know how to clear bones and meat out of a drainpipe. A good food processor can be useful. But don’t over-use it, or power drills or saws. They’re noisy and they attract attention. And forget the kitchen sink. It’s better if you actually remove one of the toilets in your house from its base, which will give you direct access to one of the largest sewer pipes that enters your house. Follow any disposals with lots of bleach and then run the water for 5 or 10 minutes on top of that. And plug that pipe when you’re not using it, to prevent any sewer gasses from backing up into your house. Usually, a U-trap inside the toilet does that for you.

Full discussion can be found here. Hope it helps

“javax.faces.convert.ConverterException: Unsupported Model Type” in ADF 10g for selectManyCheckbox

There’s a mess with the selectManyCheckbox bindings: both for initial list items and selected items. ADF itself doesn’t support direct binding to a ViewObject, and that’s why, as Frank Nimphius said,
…you would need to use a managed bean to dispatch between the ADF binding layer and the multi select component.
Maybe it’s just me, but it took me a while to figure out how exactly to do it.

First off, the managed bean. It should contain fields with accessors for two lists: the initial options and the selected items.

The initialListItems will be bound to the multi-selection items element. Whilst the selectedItems list will contain the selected items from the initial list. The important thing is the datatype for the latter – a java.util.List! In fact it’s what provokes the “Unsupported Model Type” exception. This datatype hassle was actually the part that took me a real while to get it, I tried primitive array, ArrayList of String’s, Object’s and what not!
Now the only thing left is to bind both lists to the multi-selection component.

No more exceptions. That's it, hope it helps!

How to add showPopupBehavior to an ADF Rich Faces table column

I didn’t see the answer to that anywhere in the manual, so I had to experiment myself. Ofc I sort of figured out how to do it pretty easily. Still this tutorial can save someone’s time, I hope.
So, basically, what one can do to pop a dialog with ADF Rich Faces, is 2 simple steps:
1. Define a popup with a dialog in it
2. Set showPopupBehavior of the link or button to point to that popup.


Pretty simple, isn’t it? Now the question is how to achieve the same behavior per row in a table. If we set the same showPopupBehavior popupId to a command object found in a column, it won’t work and JDeveloper will mark it as an erroneous syntax (“Reference Id confirmDelete not found”). Well, the trick is that the popup should be defined inside the column, and that’s actually it. Here’s a code snippet.

The method in the backing bean looks like:

The navigation part is intended to refresh the page (there’s a global rule in the faces-config.xml for outcome “scheduler” to navigate to this page), because dialog handler doesn’t do it automatically with JSF controller.
Hope this helps!

How to make the Oracle Application Server 10g run as a Windows service

A problem that recently has been bugging the project I’m currently working on, was to make the Oracle Application Server 10g run as a service, so that it would be available without a user logging in and starting it up manually. We solved it with the use of an open source middleware project called JavaService, a pretty neat tool. Find below how.

Requirements:
Windows machine (the guide was tested with a vanilla Windows 2003 server installation)
Oracle Application Server 10g
The latest version (today 2.0.10) of JavaService

Actions:

Let’s say JavaService is unzipped to C:\JavaService-2.0.10

Type in a cmd prompt:
cd \JavaService-2.0.10
To install the service with name OAS:
set ORACLE_HOME=C:\product\10.1.3.1\OracleAS_1
set CP=%ORACLE_HOME%\j2ee\home\oc4j.jar;%ORACLE_HOME%\jlib\startupconsole.jar;%ORACLE_HOME%\opmn\lib\optic.jar;%ORACLE_HOME%\lib\xmlparserv2.jar
javaservice -install OAS %ORACLE_HOME%\jdk\jre\bin\client\jvm.dll -Djava.class.path=%CP% -DORACLE_HOME=%ORACLE_HOME% -start oracle.appserver.startupconsole.view.Runner -params start -stop oracle.appserver.startupconsole.view.Runner -params stop -current %ORACLE_HOME%\j2ee\home\ -description "Oracle Application Server Service"
(in case the memory settings are not met (they are supposed to be taken from %ORACLE_HOME%\opmn\config\opmn.xml) add these 2 parameters
-XX:MaxPermSize=256m -Xmx256m right after the Java dll path)
To uninstall the service with name OAS:
javaservice -uninstall OAS
To view the configuration for installed Java service with name OAS:
javaservice -queryconfig OAS
Now the service OAS can be found among other services.

Should be also mentioned, that the Application Server better be stopped by the time you attempt to start the service.

Hope this helps.

Clear an iterator in ADF 10g

The mission is to empty out an iterator without setting its Refresh attribute to “never” and consequentially executing it manually. What I ended up doing, when I needed this once, was adding a parameter to the query WHERE clause (something like “and 1 = nvl(:param, 1)”) and invoking it with a zero when I needed it empty. Apparently there is an easier way.
Say the iterator to clear is defined in the pageDef as:


Then the code in the backing bean would look like:

javax.faces.context.FacesContext ctx = javax.faces.context.FacesContext.getCurrentInstance();
javax.faces.el.ValueBinding bind = ctx.getApplication().createValueBinding("#{data}");
oracle.adf.model.BindingContext bindingContext = (oracle.adf.model.BindingContext) bind.getValue(ctx); //resolve binding context
oracle.adf.model.binding.DCDataControl dataControl = bindingContext.findDataControl("AppModuleDataControl");//find data control by name (defined in DataBindings.cpx) from BindingContext
/*
* finally get the View Object instance which the iterator is bound to (see the attribute Binds in the iterator definition in the pageDef)
* then invoke the magic method executeEmptyRowSet on it
*/
((AppModuleImpl) dataControl.getDataProvider()).getCity1().executeEmptyRowSet();
That’s it. Hope this helps!

Global validation for a Date input field in ADF 10

Say you have a table with a date column and you have created a view accessing it. Now try to insert an abnormal date into the dateInput field on the page (something like 1/1/111111111), commit the changes, check the value in the DB and you’ll get what I’m talking about here. I had queried a question on the OTN forum regarding this and the only answer I got was from Frank Nimphius to

configure a value change listener on the date field and verify that the provided value is valid, If not call FacesContext.renderResponse to ignore the request

this is a solution, but well, it requires more or less to apply it to each dateInput field on every single page. The other way around that I finally used, was to override the EntityImpl setAttributeInternal method like the following:

protected void setAttributeInternal(int attributeNumber, Object attributeValue) {
if (attributeValue instanceof oracle.jbo.domain. Date) {
java.util.Date value = ((oracle.jbo.domain.Date)attributeValue).getValue();
GregorianCalendar gc = new GregorianCalendar();
java.util.Date inAHundreedYears = new java.util.Date(new GregorianCalendar(gc.get(Calendar.YEAR) + 100, gc.get(Calendar.MONTH),
gc.get(Calendar.DAY_OF_MONTH)).getTimeInMillis());
if (value.after(inAHundreedYears)) {
System.err.println("Invalid date provided (" + value + ")");
}
else {
super.setAttributeInternal(attributeNumber, attributeValue);
System.out.println("Set date " + value);
}
}
else {
super.setAttributeInternal(attributeNumber, attributeValue);
}
}
which actually just checks that the Date attribute provided is of a logical range.

This method has to be part of a class extending oracle.jbo.server.EntityImpl and obviously the entity implementation for that table with a date column must extend the new EntityImpl class.

That was it. Hope this helps!