Tuesday, December 4, 2012

Liferay: beta languages

If you have used the internationalization built in in Liferay, you might have noticed if you hover over the flags, the name of the languages appears. You also might have noticed, the name indicates the language is 'in beta'. If you want to get rid of this, you can write a hook (or extend a hook you already have).

Of course, you need to know what page you have to adjust. The display of the language-portlet is located in $LIFERAY_HOME$/tomcat-version/webapps/ROOT/html/taglib/ui/language/page.jsp. Copy the page in your hook, and somewhere near the bottom, you'll find following code:

if (LanguageUtil.isBetaLocale(locales[i])) 
{
    message = message + " - Beta";
}

Remove it, and the beta indication is gone!

Monday, December 3, 2012

Special character encoding

If you have ever created a custom language bundle, you'll know special characters can be very annoying. When they're not displaying correctly, but instead showing a diamond with a question mark or a white rectangle, it's sometimes difficult and frustrating to find the origin of the problem.

When you're building a website that has to come with a language with a lot of special characters (French, German, ...), you can run these encoding problems. In fact, there only has to be one of those special characters anywhere in your site, and it'll be messed up. When working with resource bundles (.properties files),  I've found that these few steps often resolve a lot of issues, so try to follow these simple guidelines.

  • Make sure your general encoding is set to UTF-8. In Eclipse, you do this in Window -> Preferences -> General -> Workspace
  • Each file can have a seperate encoding as well. Check the properties of your .properties files. In Eclipse, you do this by right-clicking, then selecting Properties. Under Resource, you can set the encoding to UTF-8.
Redeploy your application with this correct settings, and your problems should dissolve! Bear in mind, though, that if you had an incorrect encoding first, switching to the correct encoding may break your file and replace the special characters by the 'not found' characters (diamond or rectangle). Check your file before deploying!

Thursday, October 25, 2012

Liferay: authorization of actions on dynamic data lists


Another feature you might want to include in your dynamic data list template, is that the edit button is only shown to users of a certain role. This, again, requires some thinking and trying, but I have done it for you. What I did, was get all the roles for the current user (through the user id in the request's theme display).
#set ($user_id = $request.theme-display.user-id)

#set ($roles = $serviceLocator.findService("com.liferay.portal.service.RoleLocalService").getUserRoles($getterUtil.getLong($user_id)))
Now, we can loop the roles, and set a variable if the user has a certain role.
#set ($can_edit = 'false')

#foreach ($role in $roles)
    #if ($role.name == 'Administrator')
        #set ($can_edit = 'true')
    #end
#end
Later in the template, we can than use the $can_edit variable to conditionally display the edit link.

Tuesday, October 23, 2012

Liferay: dynamic data lists record actions

I'm still working with Liferay 6.1, and more specific their dynamic data lists. A question I've encountered a lot, and just ran into, is how to display the action buttons of a record in a custom list template. I haven't found the answer online, so I started to try some things myself.

 I figured the solution would be a lot like in my previous post: using the generated URL. I again switched back to the default list view, and copied the URL for the 'Edit' action. Stripping it down, this is the result:
/your_page?p_p_id=169_INSTANCE_ToH96dipcgdr&struts_action=%2Fdynamic_data_list_display%2Fedit_record&cmd=update&redirect=%2Fyour_page&recordId=$record.getRecordId()
Notice the p_p_id is copied from the URL (you can also get it from the $request), while the record id is dynamically fetched from the resultset's current record. Another important parameter is redirect. Provide it with the URL of the page you're going to display your list on. It will make sure the user will return to that page after saving or canceling the edit action. If you forget this, the user is stuck on the edit page.

Wednesday, October 17, 2012

Liferay: dynamic data list detail

I've been working with Liferay 6.1's dynamic data lists for the last few days. I like how easy it is to create a CRUD system for data lists. The out-of-the-box functionality to display lists using the Liferay defaults and a custom VM-template is amazing.

To display a detail of a record, however, is a lot more painful. For some reason, there's no VM-template support there. So what I wanted to do, was the following:
  • Create a detail link in the list VM-template
  • Let the detail page display my own custom page
Not all that much asked, I'd think, yet this was NOT easy to achieve in Liferay. The documentation in this area is very limited, and basically only covers the creation of a list-template. So, first things first, I created my custom list-template using the Liferay documentation, and my dynamic data list looked good.

Of course, I wanted links in that list, to click through to the details of a record. This was the first difficulty I encountered. I couldn't find any clues or documentation on how to get the correct link. So what I did, was switching the list view back to 'default', and copied the link URL there. It looked really, really ugly.

I then started to dissect that URL. I concluded that there's lot of parameters I didn't need, so I stripped it down to the bare minimum: the portlet ID, a struts action and a record ID. The portlet ID and struts action can be copied from the URL the default list provides, the record ID is dynamic and can be fetched using $record.getRecordId(). My URL looked like this:

/your_page?p_p_id=169_INSTANCE_ToH96dipcgdr&struts_action=%2Fdynamic_data_list_display%2Fview_record&recordId=$record.getRecordId()
This of course redirects to the default detail page, which might be OK for adding and editing records, but not for displaying them in an enterprise application. I somehow had to either edit the detail page, or find a way to redirect the detail-link to another page.

That was the second obstacle. Editing the detail-page wasn't really an option, since it would then be altered for ALL detail pages of all records, not just the ones I wanted to display at that time. With that idea out of the way, I had to find a way to make the detail URL redirect to a custom JSP. Therefor, I had to create a new struts action, and map it to a new JSP I also had to create.

The easiest way to do that is using a hook. In that hook, we need to do 3 things:

  • Create an Action class (extending from BaseStrutsPortletAction)
  • Create a custom JSP
  • Map the Action class to a certain path
The last one is the easiest: simply add this to your liferay-hook.xml

  /dynamic_data_list_display/view_office
  be.c4j.hook.action.SomeAction
 
This means you have to change the struts-action parameter in your detail-url to %2Fdynamic_data_list_display%2Fview_office. Of course, we also need to define the SomeAction class.

import com.liferay.portal.kernel.struts.BaseStrutsPortletAction;
import com.liferay.portal.kernel.util.ParamUtil;

import javax.portlet.PortletConfig;
import javax.portlet.RenderRequest;
import javax.portlet.RenderResponse;

import com.liferay.portlet.dynamicdatalists.model.DDLRecord;
import com.liferay.portlet.dynamicdatalists.service.DDLRecordLocalServiceUtil;

public class SomeAction extends BaseStrutsPortletAction {

 @Override
 public String render(PortletConfig portletConfig, RenderRequest renderRequest,
   RenderResponse renderResponse) throws Exception {
  
  long recordId = ParamUtil.getLong(renderRequest, "recordId");
  
  DDLRecord record = DDLRecordLocalServiceUtil.getRecord(recordId);
  
  renderRequest.setAttribute("ddlRecord", record);
  
  return "/portlet/dynamic_data_lists/view_office.jsp";
 }
}

Now all you have to do is build the JSP. Make sure you place in the folder $customs_jsps$\html\portlet\dynamic_data_lists. In the JSP you can access the ddlRecord attribute.

<%
DDLRecord record = (DDLRecord)request.getAttribute("ddlRecord");

%>; 

This is a field of our record<%= record.getFieldValue("fieldName") %>;

If you know what to do, it isn't all that hard, but it took me a lot of time to figure this out. Liferay offers a lot of out-of-the-box functionality, but sometimes you have to go through a lot of trouble for adding just that little extra.

Thursday, October 4, 2012

Oracle Open World - thursday

Last day of the conference... Not a lot of sessions today (only 1 and the Java community keynote), but we've subscribed to a trip to Oracle HQ this afternoon. We're getting a tour in their usability labs.

But first things first. I started my day with the Java community keynote. It was mainly about innovation, and some cool demos of robots (by Perrone Robotics) were given. In the end, James Gosling entered the stage and showed us what he is currently doing: Liquid Robotics. Medium-sized robots that roam the seas and gather data.

Then I went to an ADF session by Eugene Fedorenko. He took us through the process of developing an ADF application. During his 'deep dive', he showed us how to programatically create entities and view objects, end display them on the screen. I found it a bit odd to do everything programatically, instead of using the declarative strength of the framework, but I'm sure that in some cases this will turn out to be the best way.

On to Redwood City then. Oracle took us on a tour in their usability labs. They showed us how their apps are tested and evaluated using some advanced eye-reading techniques. An interesting afternoon, as closure for a very interesting conference. I learned a lot, saw some very nice demos and met interesting people. All in the lovely setting of San Francisco.


Wednesday, October 3, 2012

Oracle Open World - wednesday

Another day in San Francisco! Today's sessions are mainly about deveoping apps in the cloud, but there's also some ADF and an ADF Meetup tonight. I saw my early morning session about Java Heap and memory usage cancelled, so I used the extra time to go running in a San Francisco where the sun was just coming up. Lovely!

Develop apps with Oracle database cloud services (Rick Greenwald)

This session was presented to us by Rick Greenwald, director of Projectmanagement at Oracle Cloud. It didn't really tell me anything new. It was more of an APEX session than a cloud DB session. Rick gave a demo of an APEX application, running in the cloud.

One thing I noticed, though, was that the Oracle cloud DB only supports 1 schema. And that it's expensive. Pricing is $175 a month (for 5GB storage, 50GB would be $2000 a month). If you consider it includes everything (license, server, support, ...), it's not all that much, but if you take into account you can get a 5 GB MySQL cloud database, $175 is quite a lot. There's also a data transfer limit of 6 times your storage. Rick however told us that they will be monitoring the traffic (to avoid DOS attacks), but won't undertake any immediate action upon exceeding.

Another issue is that when you want to access your database from outside Oracle cloud, you'll have to use RESTful services. SQLDeveloper has a cloud connector built in these days, so you can still easily connect to your database. But if you want to connect another application (not running in Oracle cloud) to your cloud database, you need to expose your queries to REST web services. We were shown this is quite an easy process, though, but you really don't want to do this for larger applications.

I think Oracle Cloud has a lot of potential, but also a lot of limitations. You'll be kinda forced to use a full Oracle stack if you want to have all the benefits. Of course, if you just intend to write an APEX application, one Oracle cloud database can work wonders.

Developing with cloud services (Chris Richardson)

Chris Richardson is the founder of Cloudfoundry. He presented a very nice session on using cloud services. He used an application he wrote as guidance through the session: VoteMeetEat.com. The concept is simple: you text the word 'register' to a certain number, you get a confirmation SMS with an URL, you subscribe to that URL and you're in the program. The idea is to find restaurants and friends nearby. Anyone can then vote on a restaurant of their choice, and a group of friends can meetup at the highest voted restaurant.

To vote, you have to call a certain number, and based on your location it reads you the available restaurants. You vote by using your keypad. All participants receive a text message with the results. If you have to all write this by yourself, it would take months to get it done. And it would be a huge headache. So Chris takes advantage of cloud services, in this case for location, data and telephony.

In the demo he gave, he showed the different services he used. As a database to store friends in, MongoDB was used. It has an integration with CloudFoundry, so it's easy to use. Then, to find the restaurants nearby, a 3rd party service named Factual was used. Based on the geolocation of your phone, the Factual API returns a list of restaurants, and their information.

The most difficult part to setup and maintain yourself, though, is telephony. Setting up a database isn't all that difficult, but setting up your own telephony provider and maintaining it, doesn't sound like something you'd want to do yourself. And then we didn't even mention the complex protocols. So Chris has Twilio to do that for him. You talk HTTP to Twilio, Twilio handles all the complexity of the telephony. It's on a pay per use basis, so if your app is rather small, it's not all that expensive.

The VoteMeetEat application is a very nice example of how cloud services can be used to make the life of the developer a lot easier. And to lower development , hardware and maintenance costs.

Tuesday, October 2, 2012

Oracle Open World - tuesday


This day, I have done a lot of sessions on something I've been waiting for for quite a while: ADF Mobile. I won't discuss each session seperately (since it's all on the same topic), but I'll just give my general view.

First, it's worth noting that ADF Mobile really looks promising. The idea that you develop 1 application and then deploy it to different platforms, is really good. You build an app, then deploy it to Apple's App Store or Google's Play. Or both. Without having to deal with either Android specific stuff or Objective C. Pretty neat. Also, ADF Mobile makes sure your app is future proof. If Windows 8 turns out to be a huge hit, or any other OS that might appear in the future, ADF Mobile will have support for it.

All of this is possible because of an HTML5-based user interface. Below that, ADF Mobile uses PhoneGap to acces the device specific services. Build once, deploy everywhere. I did an hands-on session today, where we built a simple ADF Mobile app and deployed it to both iOS and Android, and I must say it works pretty good. The look and feel is generally the same and all of the functionality you build in is available in both versions.

Apart from that, I've seen quite a few demos on ADF Mobile. Or rather: demo. All presentations use the same demo app. I must admit, it looks definitely great, but seeing the same stuff over and over again gets dull after a while. Therefore I was very happy to see a real-world application demo by Infosys. They have built a mobile app using ADF Mobile for one of their customers. It's good to see the theory also appears to work in a real business usescase. The app also looked good, so I'm even more eager to get started with ADF Mobile myself now!

Monday, October 1, 2012

Oracle Open World - monday

This year, I have the privilege of going to one of the biggest conferences in the world: Oracle Open World. If you look at the numbers... they're pretty huge! During this week, I'll try to keep you posted on the most interesting sessions I followed. There'll be a short summary, and my personal thoughts and views.

Why should you switch to Java 7 (David Keenan, Staffan Friberg)

Summary

The presentation was a summary of, as the title says, why you should switch to Java 7. I'll just sum them up again!

JCommands
Garbage First
Runtime compiler improvements
Sockets Direct Protocol
Performance benefits to
  •    Date
  •    BigDecimal
  •    Crypto
  •    String to byte conversion
  •    concurrency API
  •    Hotspot JVM
  •    PermGen
  •    Internal strings
  •    XML API
Backwards compatibility (source, binary, behavioural)
Heap retuning

My thoughts

Not really a very innovating session, just a sum up of what's new in Java 7 and what's to come in Java 8. A good review, though, and makes you think of upgrading.

Future of development for Oracle Fusion (Chris Tonas)

Summary

Chris gave a demo using ADF Faces. It was a  typical ADF application with fancy graphs and components. Then he showed us the same app, but on an iPad. It had the same functionality, but HTML5 instead of Flash. It also had a slightly different layout and supported gestures and touch. The pagination in tables we so liked in ADF 10g has returned (in an  im:proved way), to avoid scrollbars.

He then talked about the iOS and Android SDK support in JDeveloper, and the visual preview of the app you're building. Apparantly, you build an ADF app once, and then deploy it to Android and/or iOS (and any other vendor Oracle decides to support). Pretty convenient! Further, Chris discussed offline support and gave an ADF Mobile demo. This time, it was a native iOS app, which I thought was pretty impressive.

To end the Mobile part, Thomas Quilligan presented a real-life case. He is from Accenture, an ADF Mobile Beta Program Partner. It was nice to see the Oracle ADF Mobile technology being used in a real-life project.

After that, we moved on to the Cloud part of the talk., with a strong focus on Developer Cloud Service. These are some of the out of the box services that the Developer Cloud offers:
  • Source control
  • Maven support
  • Issue tracking
  • Continuous Integration (Hudson) 
  • Wiki




The demo of the Developer Cloud Service that followed, was very nice. It showed the full development lifecycle, all brought to the cloud, organized in neat dashboards.






My thoughts

This was a very nice presentation. The ADF Mobile still looks promising, and appears to be finally released soon. The cloud part really surprised me. I've been waiting for Oracle Cloud for quite a while now, but I didn't know they were going to offer something like the Developer Cloud. I really liked that. If it all integrates as well as in the demos, this will definitely be a product I'd want and like to use!

Oracle's public cloud strategy (Abhay Parasnis)

I'm writing an article about this session on Cloudspring. I'll update the link as soon as it gets published.

Classic mistakes with ADF (Frank Nimphius, Duncan Mills)

This was a nice light session about some of the most made errors with ADF. Driven by real examples and questions, Duncan and Frank guided us through. I'll add the slides as soon as they're available, since writing it all out seems a little pointless.

I'll just give a bit more details about one of the errors discussed. It's one we ran into as well, and Frank and Duncan categorized it as 'silent, but deadly' (as opposed to 'unforgiveable' and 'bear traps'). It's about using a bean that is not request scope, but that contains references to UI components. The problem here is that UI components only last as long as a request. They are therefore not serializable, and any bean with a scope higher than request, will want to serialize all it's variables.

Tuesday, September 25, 2012

Oracle ADF Essentials

Oracle has released ADF Essentials: a free to develop and deploy core version of their Application Development Framework.

What is included in Oracle ADF Essentials?

According to the documentation, Oracle ADF Essentials includes the following Oracle ADF components: Oracle ADF Faces Rich Client Components, Oracle ADF Controller, Oracle ADF Model and Oracle ADF Business Components.

The following functionality, however, is not included in Oracle ADF Essentials, and requires the full Oracle ADF version: Oracle ADF Mobile, Oracle ADF Desktop Integration, Oracle ADF Security, The Oracle ADF Web service data control, Oracle ADF remote taskflows, Oracle ADF Business Component’s Service Interfaces, Oracle ADF Data Controls for BI, Essbase and BAM, Integration with Oracle Fusion Middleware features such as MDS, OPSS, OWSM, Enterprise Manager and MBeans, High Availability and Clustering.

All in all a good base to start from! We now await their cloud solution, so we can develop and deploy our ADF applications in the cloud.

Using Cloudbees behind a proxy

At work, we are sitting behind a proxy. This can be pretty annoying if you have to use services that require the internet, but don't rely on your internet settings. For example Maven, which can be configured using it's settings.xml file, or the Cloudbees SDK.

That last one is a bit trickier to use behind a proxy. There is no obvious settings.xml or properties file where you can define your proxy server. The solution, however, is very simple. Go to your Cloudbees SDK root folder, and edit the bees.bat file. Change the JAVA_OPTS to the following:
JAVA_OPTS=-Dbees.home=%BEES_HOME% -Dhttp.proxyHost=<your proxy host> -Dhttp.proxyPort=<your proxy port> -Xmx256m
Save the changes, and when you run the bees command from the console now, it will use your proxy settings. Easy as that!

Wednesday, September 12, 2012

ADF analyzed by Gartner

Gartner has recently published their analysis of Oracle's Application Development Framework. And while the general feelings towards ADF are rather hesitating, the Gartner conclusion is overall very positive. Of course, ADF is tightly coupled with Oracle's Fusion Middleware stack and JDeveloper (although an Eclipse plugin is available). But just because of those reasons, you can count on Oracle to continue developing and supporting ADF in the future.

A special mention goes to the MetaData Services provided in Fusion Middleware. It's an engine that allows users to personalize their own web-experience. Much like portals intend to do, but then in 'a regular' web application. It allows runtime customization of the look-and-feel, per user, group of users or the entire application.

Further, Gartner looks forward to the much anticipated ADF Mobile. They expect it to ship with the 12c release of ADF. As you could see earlier on my blog, I'm attending OpenWorld this year, and I hope to see some more details about ADF Mobile there.

So all in all a positive review of ADF. Let's hope customers also see the added value of the framework, and at least consider adapting it. Especially when an Oracle stack is already present, the step to start using ADF is not very big.

Thursday, August 16, 2012

Free Advanced ADF course - part 2

As I mentioned earlier, Oracle provides a free advanced ADF course. Today, Jürgen Kress announced on his blog that part 2 is available! Here are the links to part one and part two.

Good luck.

Monday, July 23, 2012

Google DataStore with JPA and Spring

I like Google App Engine. It's fast, reliable and free. It also comes with Google DataStore, a NoSQL solution to store data. The only problem is that it isn't that easy to use with the technology you want. We, for instance, wanted to use JPA and Spring. We've been struggling for a little while, but in the end, we managed to get all the right libraries. To make our life easier, we poured all those libraries in a Maven POM file, and made an archetype out of it. That way, we can just generate a new project from that archetype, and we're good to go!

Follow these steps to get started (You need Maven 3 to sucessfully run the app!)
mvn archetype:generate -DarchetypeGroupId=be.c4j -DarchetypeArtifactId=gae-wicket-archetype -DarchetypeVersion=1.0 -DgroupId=be.c4j -DartifactId=gaeproject -DinteractiveMode=false
  • The parts in bold are what defines your projectname and default package
  • On the newly created project, do a mvn gae:unpack 
  • Now you can mvn gae:run your application
  • It's just a simple Wicket Hello World app, but it's a base to start from
This setup was made to prepare our Summer of Technology session. A lot of thanks go to Sebastian Van Sande for sorting out dependency issues and creating the archetype.






Wednesday, July 18, 2012

Cloud IDE

Today, I stumbled upon somtehing I've been searching for quite a while: an online IDE in the Cloud! No more need to install stuff on your PC, just develop anytime, anywhere you are. I discovered Cloud IDE, where you can sign up for a free account. Moments later, your personal domain has been created and you can start developing!

There are some very interesting options once you are logged in. You can link (a.o.) your Cloudbees and Google App Engine accounts. That way, you can easily create and deploy applications. There is a sample GWT project that you can import to Cloud IDE, and when your Google App Engine account has been linked, the new project is deployed within seconds. A lot of nice functionalities, all out of the box.

Of course, there are also drawbacks. You need a relatively fast internet connection, but I guess that's not really an issue anymore these days. Further, the IDE isn't nearly as extended as Eclipse or IntelliJ. The 'develop in the cloud' concept is obviously still in its childhood, but it looks promising. There's GIT support, you can use Maven, create applications directly in your Cloud platforms, ... You can even collaborate on the same project with up to 5 users in the same domain.

More features will be added, while gathering feedback from developers. I like the idea, but it's yet another IDE to get used to. I'm looking forward to playing around with it, and the ease of integration with PaaS providers is a big advantage for me. The Cloud is ever expanding!

Monday, July 16, 2012

ADF tip: RowIterator

An ADF tip I can give you is the following: if you need a RowIterator multiple times, store it into an object. We've had an issue with getting it 2 times. Our application didn't give an error, would would appear to be busy forever, while not returning any results.

This was our case:
SomeVORowImpl someRow= (SomeVORowImpl)baseRow.getSomeVO().createRow();
//Do something with row
baseRow.getSomeVO().insertRow(someRow);
It would execute correctly (without errors), but the application would then hang. We've replaced the duplicate call to baseRow.getSomeVO() and stored it into a RowIterator object:
RowIterator someVO = baseRow.getSomeVO();
SomeVORowImpl someRow = (SomeVORowImpl)someVO.createRow();
//Do something with row
someVO.insertRow(someRow);
This did the trick. We haven't dug to the bottom of why this happened, but if we can reproduce this in a small test application, we might file a bug.



Friday, July 13, 2012

ADF sessions at Oracle Open World

It's still more than 2 months away, but I'm already looking forward to Oracle Open World. I'm starting to look at the sessions that will be given, and I'm preparing my list. These sessions are must-see's for me!
My selection is based on both topic and speakers. For now, I've only looked into the ADF sessions. I'll look into other topics (Cloud, Java, ...) later on, and will continue to update this list.

Thursday, June 28, 2012

A European cloud strategy

Neelie Kroes, vice-president of the European Comission responsible for the digital agenda, spoke about a European cloud strategy at the Economic Council Symposium (Brussel, 25/06/2012). Read what she said here!

In short: they want to install a 'Single Market', and make the cloud accessible without the limits of national borders. Think big, embrace the benefits and cut the costs.

Wednesday, June 20, 2012

ADF in Eclipse

Oracle organizes a free virtual event, to show some best practices in building rich ADF applications, based on ADF Data Controls, using standard Java technologies (EJBs, JPA, ...).

There's also a live Q&A chat with Oracle technical staff. The event takes place on July 10. You can register here.

Wednesday, May 23, 2012

Random Hacks of Kindness

Random Hacks of Kindness (RHoK) is a an initiative originated by Microsoft, Google, Yahoo, NASA and the World Bank. The objective is to bring together experts around disaster management and crisis response with volunteer software developers and designers in order to create solutions that have an impact in the field.

RHoK has periodical events, known as hackathons. The next hackathon will be organized by Contribute, and will take place 2 - 3 June 2012. For more information and registration, go to http://www.rhok.be/.

Entry is free, food and drinks will be provided. This hackathon is in cooperation with the Open Knowledge Foundation, and you'll receive more information about Amnesty International through a video link with a hackathon event in Berlin.

Tuesday, May 15, 2012

The Story of Send


Ever wondered what happens to your email when you hit "send"? Now you can follow the journey of an email with Story of Send, a new website with a behind-the-scenes look at how your email journeys through the world, from your Internet service provider to Google's data centers and beyond.

Watch the cool animation here: http://www.google.com/green/storyofsend.

Thursday, May 10, 2012

Summer of Technology @Contribute

It's that time of the year again! Summer is coming, and with summer comes Contribute's Summer of Technology.

During the months of July, August and September, Contribute organizes 12 free workshops. I am proud to announce that I'll be co-presenting one of them. It will be about building a Wicket application on Google App Engine. Click here for more details! Of course, there's much more than just my session, an a lot more topics than web application development will be covered.

Choose the session(s) that interest you, and subscribe. If you're having troubles viewing the website or registering yourself for one of the events, contact info@contribute.be.

Hope to see you on one of the sessions!

Thursday, April 26, 2012

Google App Engine 1.6.5 released

Google has launched a new version of App Engine. Version 1.6.5 has some improvements on a.o. datastore,  Images API and Task Queues.

Read Google's blogpost here.

Thursday, April 19, 2012

Make the web faster using SPDY

Google Developers has announced they have launched a version of mod_spdy, an Apache mod that adds SPDY support to your Apache HTTPD server. To get started, download mod_spdy and follow the install guidelines.

By default, Chrome, Chrome for Android and the most recent versions of Firefox support the SPDY protocol. It's not likely Microsoft's Internet Explorer will support SPDY in the near future.

Tuesday, April 17, 2012

Google Drive to launch next week

According to The Next Web, Google will launch Google Drive somewhere in the next week. Basically, Google Drive is just another cloud storage solution, but then again, it's Google. I should integrate nicely with their already existing products, such as Google Docs, Google Apps, Picasa and Android. Every user is entitled to receive 5GB for free, with the option to pay for more. It's not as much as the 50GB I blogged about earlier, but that was a limited offer.

After Box, DropBox, SugarSync and many, many others, this seems to be like the thirteenth cloud storage provider in a dozen. Let's hope Google can really offer an added value. If you're a fan of Google and their products (like I am), this should be worth checking out. There aren't a lot of details known, but the launch is expected to be on Tuesday 24 or Wednsesday 25 April.

Monday, April 16, 2012

Find constraint in Oracle database

When you're developing web applications, you usually persist against a database. And sometimes, that database throws errors at you. One of them can be a foreign key or other constraint violation. If you manage the database yourself, the constraint names are of course very logical and tell you immediately where the problem is. But sometimes the DB management isn't in your hands, and then the constraint key can be some random combination of letters and numbers. Obviously, it's not easy to find the cause of the problem then... unless you know how to search!

You can query all constraints in an Oracle database. Usually, the error you get from the database will be somewhere in your logs, or even displayed on the screen, so you have the name of the constraint that is violated. Once you have that, you can just run this simple query:

select constraint_name, table_name
from all_constraints
WHERE constraint_name = 'Faulted_Constraint_Name';


Now you know which table causes the error, and you can start solving the problem.

Of course, the 'all_constraints' table has more fields than just constraint_name and table_name. To find out what more you can query, just use following command:

desc all_constraints

This will give you a list of all queryable fields.

Friday, April 13, 2012

ADF 11g: Using Application Module outside ADF Application context

Earlier this week, I had to refactor an existing project, and extract some functionality. The goal was that this code could run outside of our Weblogic server, in a crontab job. So I created a new project, containing a class with a main method. The original code was based on Business Components, so I wanted to use this Oracle ADF specific technology as well.

After all the extraction was done, I created a JAR file of my new project and tried to run my main class. The fist problem I encountered was not having all the necessary JARs on my classpath. Therefor, I created a batch-script (could be Unix as well, but I was working in a Windows environment), setting all necessary JARs on my classpath and launching my main method

set JAVA_HOME=C:\Oracle\Middleware\jdk160_18\jre

set PATH=%JAVA_HOME%\bin;%PATH%
set CLASSPATH= YOUR_CLASSPATH

java -classpath %CLASSPATH% my.MainClass


Where YOUR_CLASSPATH is a semicolon-seperated list of all JARs you need. Now the code would compile! But then I ran into the next issue: creating an application module.

I used the default way of creating an Application Module, ie. Configuration.createRootApplicationModule(). While this works inside an ADF application, running a JAR standalone does not provide you with enough context. So I tried a new approach, and manually initialized a context:

String jdbcURL = "jdbc:oracle:thin:@HOST:PORT:SID";

Hashtable env = new Hashtable();

env.put(Context.INITIAL_CONTEXT_FACTORY, JboContext.JBO_CONTEXT_FACTORY);
env.put(JboContext.DEPLOY_PLATFORM, JboContext.PLATFORM_LOCAL);

Context ic = new InitialContext(env);


But of course, creating a Context isn't enough to use the Application Module. We need to create that as well, and I did that in the following manner:

// 'defName' is the JNDI name for the application module
// definition from which the root application module is to
// be created
String defName = "my.AppModule";

ApplicationModuleHome home = (ApplicationModuleHome)ic.lookup(defName);
ApplicationModule = (ApplicationModule)home.create();
mbApplicationModule.getTransaction().connect(jdbcURL, dbUser, dbPassword);


DefName is the JNDI name of your application module. This can be found in bc4j.xcfg. Now we can use the ApplicationModule just like we would in an ADF Application context!

Wednesday, April 4, 2012

Test your PL/SQL skills!

The best way to deepen your knowledge of a certain topic is to practice it. Play with it, take quizzes about it, just be 'into it'. And when you can win prizes, that's always a nice extra.

Now there is a PL/SQL Challenge. It's completely free, and you can win (e-)books and Amazon gift cards. But apart from that, it's a great way to test, deepen and maintain your PL/SQL skills.

Find the PL/SQL Challenge at http://www.plsqlchallenge.com/ .


Wednesday, March 28, 2012

Kinect for Windows

According to this blog post, Kinect for Windows will be available in Belgium as of June 2012. While this has not much to do with web development itself, I do like the Kinect. I have one for my XBox, and it works pretty smoothly. Now that it becomes available on Windows as well, I think it offers a lot of possibilities.

Imagine a teacher in front of a whiteboard, being able to write on it without a marker, or giving a presentation without having to click through each slide. It also offers possibilities for games, and by extension even web developers. The world of IT and computers is constantly evolving, Microsoft's Kinect being just one example.

Friday, March 23, 2012

The Cloudbees cloud solution

A few weeks ago, I blogged about getting your app online with Google App Engine. While this is a very easy process, it is far from the only cloud solution available. I have tried another one, Cloudbees, and will tell you about my experience now.

Cloudbees offers more then just a deployment platform. It has Repositories, Continuous Itegration and an Application Server for you to play around with. It also offers database services, and has plugins for numerous other things (like Sonar, Sauce Labs and many others). For this next example, I used SVN as repository, Jenkins as CI and Tomcat as app server.

Signing up

Signing up for Cloudbees is easy. Fill in your name and e-mailaddress, and create an account. That's it! Now that your account has been created, you can select which services to use. There are both free and paying options. To get started, I added the following:
  • Repository
  • Jenkins
  • Applications
I chose the free version of each. The idea was to simulate a real world working environment. I know there are a SDK and plugins available to build and deploy from within Eclipse/STS, but I wanted to have a continuous integration build my SVN repository whenever I checked in changes.

Configuration

First, I created a new code repository (in the Repositories service). I named it 'blogtryouts'.

Then I created a new application, naming it, again, Blogtryouts.


You now can configure the application server, which is in fact a Tomcat instance. You can define JDBC-connections, or upload a WAR file to be deployed.

Continuous integration

But we don't just want to upload a WAR file. We want our newly created SVN repository to be checked out, the project to be built and the resulting WAR-file to be automatically deployed. Therefore, we'll create a Jenkins service in Cloudbees. I created a DEV@Cloud free instance.

The Jenkins instance is immediately available. I added a new job ('Blogtryouts', who'd have guessed?), and made it a Maven 2/3 project. Once created, we can start configuring our Jenkins build!

Checkout, build, deploy

The configuration is pretty easy as well. The first thing we want Jenkins to do, is checkout our SVN repository. Under Manage sourcecode, you can select Subversion and then specify a URL. That URL is the one Cloudbees gave you when you created your repository. You can find it by going to Services -> Repositories and selecting your repository.

Since we told Jenkins it's a Maven project, it'll automatically try to build the pom.xml. You can add parameters and specify when it should be built. Under Building Activators check Build when a change is pushed to CloudBees Forge. This will start a build when someone commits code to SVN.

Last but not least ,we want to deploy the built artifact. Therefore, check Deploy to CloudBees under Actions after build. You can now specify the site and application ID to deploy to. The site is normally your username, application ID is the name you gave your application, prefixed with yoursite/. Cloudbees helps a lot by providing a dropdown with sites, and by telling you an application ID can't be found. They can even tell you which application IDs are valid.

If you now click 'build now', There will be a warning that your account hasn't been validated. This is an extra step required. Just click the link and enter your phone number (make sure you're near the phone with that number!). Seconds later, you'll receive a phone call with a computer voice telling you a PIN code. Enter the pin code, and you're good to go.

The webapp

So, now that our cloud is fully setup, we of course need a webapp to deploy. For demonstration purposes, we'll just use a general Maven archetype. As in some of my prvious blogposts, we'll create a Wicket project. We can do this quickly by executing this Maven command:

mvn archetype:generate -DarchetypeGroupId=org.apache.wicket -DarchetypeArtifactId=wicket-archetype-quickstart -DarchetypeVersion=1.5.5 -DgroupId=com.mycompany -DartifactId=myproject -DarchetypeRepository=https://repository.apache.org/ -DinteractiveMode=false

The magic

Now that our application has been created, we just have to import it into our SVN repository. I used TortoiseSVN to do an Import to my Cloudbees repository. It doesn't matter how you do it, but once the import's been done, you can watch the magic happen.

Jenkins will notice a new commit and will start a new build. When that's done, it'll deploy the generated WAR-file. When you now go to Services -> Applications, and click your application, you'll notice a new deploy has been done, with a Jenkins build message. This means your app is up and running! The URL is found on top of this page as well. Mine is available here.

Wednesday, March 21, 2012

Google Wave Sunsetting

Google has just sent reminders to all Wave-users: Google Wave is EOL. The shutting down will happen in phases, you can find the exact dates here. All services will be stopped by the end of April 2012.

Tuesday, March 20, 2012

Wicket 1.5 in Google App Engine

In a previous post, I explained how to quickly setup a Wicket application using Maven and Google App Engine. As you may have noticed, the default version of Wicket that is used, is 1.4. If you want to use Wicket 1.5, you have to replace Wicket dependence in your pom.xml.

This is what is there by default:

  <dependency>
      <groupId>org.apache.wicket</groupId>
      <artifactId>wicket</artifactId>
      <version>1.4.10</version>
    </dependency>


We'll replace it with:

  <dependency>
      <groupId>org.wicketstuff</groupId>
      <artifactId>wicketstuff-gae-initializer</artifactId>
      <version>1.5.5</version>
    </dependency>
>

Monday, March 19, 2012

Oracle Certified Professional (OCP), Java SE 7 Programmer

Oracle has announced a new certification, the Oracle Certified Professional, Java SE 7 Programmer. If you already are an Oracle Certified Professional (or a Sun Certified Java Programmer) for a previous version of Java, you can take an exam to upgrade your certification to the latest version.

If you're not yet certified, and want to become an OCP, you must first pass the Oracle Certified Associate (OCA) Java 7 Programmer exam.

Friday, March 16, 2012

Updated Java 6 EOL date

In its recently updated Java SE Support Roadmap, Oracle provides an updated date for Java 6 to go EOL (End Of Life). It used to be July 2012, but has now been postponed to November 2012.

Basically, it means that after November 201 Oracle will no longer post updates of Java SE 6 to its public download sites. Developers are encouraged to switch to the latest version.

Thursday, March 15, 2012

Oracle supports btrfs filesystem

Oracle has released the latest version of its Oracle Unbreakable Enterprise Kernel. You can find the release notes here. This release is based on Linux 3.0.16 and is a clone of the Red Hat Enterprise kernel.

With this release, Oracle is the 2nd vendor, after SUSE, to provide support for btrfs filesystems.

More information about btrfs can be found here.

Tuesday, March 13, 2012

JDeveloper: Code Template to show current class and method

For debugging purposes, I sometimes use a simple System.out.println statement to have some values displayed on the console. It's not the best or cleanest way, I know, but it works and is a lot faster than setting up a logging framework first. If you already have a logging framework configured, you might as well use that one, of course. Following method could also be used for quickly generating logging statements.

To keep an overview of the messages printed, I usually preceed every message with currentClass.currentMethod. In JDeveloper, there's an easy way to do this:

  • Open Tools -> Preferences...
  • Go to Code Editor -> Code Templates
  • Add a new one
  • Enter a shortcut (I use 'sopl'), and change the context to Java
  • In the code section, type System.out.println("$myCurClass$.$myCurMethod$(): $end$");
  • In the variables tab, map myCurClass to 'Class Name' and  myCurMethod to 'Method Name'
  • Leave end mapped to 'End Location'
Now you can use sopl in every Java class! Just type sopl and hit Ctrl+Enter.

Monday, March 12, 2012

ADF 11g: Tag Library

Wouldn't it be nice to have an overview of all Oracle ADF 11g components? Well, you can find them here:

http://jdevadf.oracle.com/adf-richclient-demo/faces/components/index.jspx

You can adjust parameters to see their effect and view the source code. There's also an option to change the skin, so you have an idea what skinning can do for you.

How to use Uploadify in Spring MVC

What is Uploadify?

www.uploadify.com
"Uploadify is a jQuery plugin that integrates a fully-customizable multiple file upload utility on your website. It uses a mixture of Javascript, ActionScript, and any server-side language to dynamically create an instance over any DOM element on a page."

So, Uploadify is a JQuery lib which allows you to upload multiple files at once onto your webpage. Uses flash for fancy animations!

Implementation

Integration

You start by downloading Uploadify and integrate it into your project. Put them in a folder and add thaty folder to mvc:resources in je servlet-context.xml.

<mvc:resources location="/resources/" mapping="/resources/**">

Further, you need to tell Spring thatMultiPartFiles are possible:

<bean class="org.springframework.web.multipart.commons.CommonsMultipartResolver" id="multipartResolver">
  <property name="maxUploadSize" value="500000"/>
</bean>


In a Maven project, get the required libraries by adding this to your POM:

<dependency>
 <groupid>commons-fileupload</groupid>
 <artifactid>commons-fileupload</artifactid>
 <version>1.2</version>
</dependency>


Upload page

Your upload page looks like this:

<link href="../resources/uploadify/uploadify.css" rel="stylesheet" type="text/css"></link>
<script src="../resources/js/jquery16.js"></script>
<script src="../resources/uploadify/jquery.uploadify.js"></script>
<script src="../resources/uploadify/swfobject.js"></script>

<script type="text/javascript">
$(document).ready(function() {
var myFiles = new Array();
var myFileCnt = 0;
$('#file-upload').uploadify({
'swf': '../resources/uploadify/uploadify.swf',
'cancelImage': '../resources/uploadify/cancel.png',
'multi' : true,
'auto' : true,
'fileObjName' : 'filedata',
'checkExisting' : false
});
});
</script>

<input id="file-upload" name="file-upload" type="file" />


Handling

If you set auto to true, an automatic POST-request will be executed. We need to catch and handle it!

@Controller public class FileUploadController {

 @RequestMapping(method=RequestMethod.POST)
 public String handleFile(MultipartHttpServletRequest request)
 {
  MultipartFile file = request.getFile("filedata");
  //some code here
  return "fileupload/success";
 }
}


Extra parameters in request

You can add extra parameters to your request. This is not as easy as it sounds, because Uploadify creates and manages its own form. This is how I did it:
Add function to your JSP page
In Uploadify, there are a few events available that are triggered throughout the process. onSelect is one of them. It gets called every time files are selected.

onSelect : function(){
$('#file-upload').uploadifySettings(
'postData',
{'season':$('#season').val()}
);
}


Your entire script now looks as follows:

$(document).ready(function() {
var myFiles = new Array();
var myFileCnt = 0;
$('#file-upload').uploadify({
'swf': '../resources/uploadify/uploadify.swf',
'uploader': '',
'cancelImage': '../resources/uploadify/cancel.png',
'multi' : true,
'auto' : true,
'fileObjName' : 'filedata',
'checkExisting' : false,
onSelect : function(){
$('#file-upload').uploadifySettings(
'postData',
{'myParamName':$('#myFieldId').val()}
);
}
});
});


Get parameter in Controller
When you've added the parameter to the postData, as described above, you can easily get it in your Controller. Its value is now in the parametermap of your request.

String s = request.getParameter("myParamName");

If you have followed this guide and stumbled upon problems, please let me know. I'll try to keep it as correct and up-to-date as possible!

Thursday, March 8, 2012

ADF Logging

Most people use Log4J for their logging. There are a few others, like Commons Logging, SLF4J, or the default Java Logging API. But if you're working with Oracle's Application Development Framework, there is another option as well: ADF Logging.

ADF Logging is a logging mechanism, embedded in the ADF framework. It wraps the Java Logging API, but throws in a few extra methods and some JDeveloper and (Weblogic) Enterprise Manager features.

A thorough guide on how to use it can be found on Duncan Mill's blog. A 15 minute introduction presentation is also available.

Wednesday, March 7, 2012

ADF 11g: Move Task Flow to another folder

Users of JDeveloper know it: on a lot of files, you can right click, choose the option "Refactor", and select "Move". But not so for task flows (at least not in JDev 11.1.1.5). If you want to move a task flow to another folder, you have to recreate it. For new flows, this isn't too hard, but for flows that have a lot of activities, actions and method calls, this can be a lot of work. To get the job done without having to recreate the entire task flow, follow these 2 easy steps:

  • Move the task flow definition XML file (under WEB-INF ) to the correct folder
  • Move the task flow diagram files (.adfc_diagram) to the correct folder. They can be found under the model/WEB-INF folder in your ViewConrtroller project
  • Change the DataBindings.cpx file to reflect the changes
That's it!

Free Cloud DB

I was looking for a free cloud database for my online applications, and to play around with a bit, and found a few solutions.

One was Oracle. My background is Oracle, and it's by far the best database there is. Unfortunately, their cloud solutions doesn't seem to be quite ready yet. You can register, but don't get a cloud database to play with. Yet... As soon as Oracle cloud is up and running, I'll check it out and make a post about it.

We continued our search then. I figured there wouldn't be any free Oracle cloud database, so I extended my reach to all databases. I stumbled upon Xeround. They seem to provide a free MySQL solution. Which basically is Oracle as well, since they acquired Sun. So I signed up, and created a DB instance. Apparantly, instances up to 10MB are free. There are payed solutions if you want more capacity. But for the stuff I'll be doing, 10MB of data will be more then enough.

The creation of an instance took a few minutes, but once finished, my database was up and running. It comes with a very convenient phpMyAdmin online console to manage the database and execute queries. So far, it looks like a very decent solution. Later on, I'll try to use the database in an application!

Tuesday, March 6, 2012

Scrum in 10 minutes

Scrum is a methodology to develop software or products. It is hot, these days, and widely used. There are expensive courses you can take to master the matter, but there are also some good online resource to consult.

One of them is this video: Scrum Master in Under 10 Minutes (HD) by @hamids

If you're interested in getting your Black Belt at KnowledgeBlackBelt, you can take an exam here after watching the video.

Good luck!

Saturday, March 3, 2012

Get your app online in 10 minutes with Google App Engine!

In this post I'll explain how to easily get an app online and running in under 10 minutes. There are a few thing we need before we can start, though:
The Google App Engine SDK can easily be installed from within STS itself.

So, once we have all these prerequisited, we can get started! First thing you have to do is tell Google you want to deploy a new application. To do this, go to the Google App Engine start page, and create an application.

I named my app blogtryouts.

Now we are ready to actually build an application. Springsource Toolsuite comes with Maven preconfigured, so we might as well use Maven and its rich collection of archetypes to get going. So, in STS, create a new Maven project (File -> New -> Other..., and then select Maven project)

A wizard starts to help you create a new Maven project. Make sure you leave the Create a simple project (skip archetype selection) UNCHECKED! We're going to select a Maven archetype to get started really fast. More information about Maven Archetypes can be found here. When you click next, you can select the maven archetype you want to use. Filter on gae, and select the archetype using the framework you desire. I chose Wicket, cause I like the way it works (and how you can have a web designer do the tedious HTML/CSS styling while you can focus on the real Java development). To use wicket, select gae-archetype-wicket.

Click Next. Now comes the screen where you enter your application information. Enter data concerning to your application in Group IdArtifact Id and package. In the gaeApplicationName field, you enter the name of the application you created on appengine.google.com. In our case, this was blogtryouts.

Also notice the gaeApplicationVersion field. It defaults to test. We'll change it to release, to deploy a release version of our app. Click Finish. Maven will now create an archetype!

Now, there are still some issues before you can deploy your application. You have to put the Google App Engine SDK to your buildpath. I have no idea why this isn't done by default, but it isn't, so we'll have to do it ourselves. Easiest way is by right clicking your project, and select Google -> App Engine Settings... Basically, you can just hit Ok, to accept all default values.

Now that the SDK has been added, there still is 1 problem to be addressed. I think it's a bug in either STS or the Maven Archetype, but the appengine-local-runtime artifact seems to be missing. You can just go to the pom, and delete the entry.

<dependency>
  <groupId>com.google.appengine</groupId>
  <artifactId>appengine-local-runtime</artifactId>
  <version>${gae.version}</version>
  <scope>test</scope>
</dependency>


Now, build the project by using the maven package command. The necessary files and folders will be created, and your application is ready to be deployed! When Maven has finished packaging, right click your application in STS, select Google -> Deploy to App Engine... and deployment will start. When it's finished, your application is available at yourAppname.appspot.com.

If you used test instead of release in the gaeApplicationVersion I mentioned earlier, it would deploy to test.yourAppname.appspot.com.

Good luck and have fun!


Friday, March 2, 2012

50GB of free cloud storage

Cloud storage service Box has a new Android app available. To celebrate its launch, Box now offers 50GB of free storage if you download the app before March 23rd. For the rest of your life! After that date, you can always sign up for a free 5GB account, or pay for more cloud diskspace.

So go to the Apps Marketplace on your android phone, search for 'box', and install the app.

Free Advanced ADF course

Great news! Oracle now provides free online training for ADF. According to Grant Ronald's blog, more parts of this course will be released in the coming weeks.

Get started, or sharpen your ADF skills...

ADF 11g: Select date and time

Today, I had to enable the users to not only select a date, but also a time. I remember this being a lot of work in 10g, but in 11g, it's apparantly out of the box functionality.

Thanks to Shay Shmeltzer for providing a solution!

https://blogs.oracle.com/shay/entry/a_timehour_selector_in_adf_fac

In short:
  • Make field in database of type TIMESTAMP
  • Make sure it's also a TIMESTAMP in your entity object
  • Provide a date format mask that includes hours and minutes


More information can also be found in this forum thread.

Java7 features

Java 7 has been released for a while now, but I thought I'd link to the most important new features, for future reference.

JDK7 Features

For us, developers, the most commonly used will be the ones made in Project Coin, I guess. Also take not of the features postponed to JDK 8 (at the bottom of the page)

Thursday, March 1, 2012

ADF 11g: Global date format

In ADF 11g, you can define a date format on many levels. On Entity Objects, View Objects, even on UI level in your JSF pages.

But wouldn't it be convenient to make 1 configuration and have all dates display the same? Well, this is possible. Just add this line of code to your trinidad-config.xml file (located in WEB-INF):


<formatting-locale>nl-BE</formatting-locale>


Of course, the locale you use determines the formatting. This particular example, nl-BE, will display all dates as dd/MM/yyyy.

ADF @ KnowledgeBlackBelt

Ever heard of KnowledgeBlackBelt? It used to be BlackBeltFactory. Doesn't sound familiar either? Perhaps JavaBlackBelt then? I'm sure that rings a bell to a lot of Java-oriented developers. Well, it's all the same site, it just has changed name (and layout) a few times over the years.

 In short, KnowledgeBlackBelt is a Java Learning & Certification community. Everyone can join and take free exams to gain grades. There are even courses (both free and paid) that handle certain topics and prepare you to take those exams. New users start out with a white belt, and eventually, after taking courses, exams and contributing to the community, they can become a Black Belt.

 I'm a contributor to the KnowledgeBlackBelt community. I have earned a brown belt over the years, and I'm the leader and moderator of the ADF Business Components exam. Check out the exam, and the entire concept that is KnowledgeBlackBelt. Learn, gain experience and get better at what you do.

ADF 11g: Get sequence in Groovy

A lot of people use sequences to generate an ID for their records. Since Oracle doesn't have an auto-increment, you need to manually get the next value and insert it into the ID field.


This can be done by triggers, but when you use Business Components, adding a one method and a single line of groovy code is enough. First, we need a method to get the next DB value:

  public Number seqNextVal(String seqName) {
 
    Number seqNextVal;
 
    if(seqName!=null && !seqName.equals("")) {
      SequenceImpl seq = new SequenceImpl(seqName, getDBTransaction());
      seqNextVal = seq.getSequenceNumber();
    }
    else {
      seqNextVal = new Number(0);
    }
 
    return seqNextVal;
  }


In the Id-attribute of your entity, you call this method by entering this expression in the value field:

adf.source.seqNextVal("SEQ_NAME")




Don't forget to check the Expression radio!

ADF 11g: Hide table column headers

Sometimes, you want to display a table, but hide the column headers. This can easily be done with ADF Skinning. First, we need to create a skin. This can be done by creating a trinidad-skins file in your META-INF folder. Since we only want to adjust our table in this simple example, we'll extend from the default Fusion desktop skin

<?xml version="1.0" encoding="UTF-8" ?>
<skins xmlns="http://myfaces.apache.org/trinidad/skin">
 <skin>
  <id>mySkin.desktop</id>
  <family>mySkin</family>
  <render-kit-id>org.apache.myfaces.trinidad.desktop</render-kit-id>
  <extends>fusion.desktop</extends>
  <style-sheet-name>/css/mySkin.css</style-sheet-name>
 </skin>
</skins>


As you can see, we refer to a css file there. Create it, and add this line to it:

.tableNoColumnHeaders af|column::column-header-cell {display: none}

Your skin has now been created, now we need to tell our application it has to use that skin. This is done in the trinidad-config.xml file, located in your WEB-INF folder. There, refer the skin-family to your own skin

<skin-family>mySkin</skin-family>

That's it. Your skin has been created. All that is left now is configure your table to use the style you just defined. Add following attribute to your <af:table> instance:

styleClass="tableNoColumnHeaders"

Wednesday, February 29, 2012

XLight FTP server

As a web developer, I sometimes get the task to communicate with an FTP server. Usually, that server is remote, and not under your own control. Therefore, it is often difficult to troubleshoot and pinpoint possible problems. For instance, last I wrote some code to transfer a file to an FTP-folder, where it was supposed to be picked up and printed. My code was executed without errors, but the document was never (or partially) printed.

The FTP server was actually a printer, and there was no way to view the actual folder. And even if that would have been possible, we could never be sure the file had been transferred, because the printer was constantly polling for new files.

So, to be sure our file transfer worked, we had to transfer the file to a 'regular' FTP-printer. While some people have an FTP-server running somewhere, I do not, so I had to download, install and configure one. That seemed like a tedious job, to just run a simple test. So I started looking for a simpler solution, and found one.

The answer was XLight FTP Server. This is a very lightweight FTP server, that does not require installation. You download the standalone FTP Server, unzip it, and run the .exe file included. You create a new virtual server, adjust some configurations, start said server and your own FTP server is up and running.

Tuesday, February 28, 2012

ADF 11g: SelectOneChoice not showing

Creating a dropdownlist with a List of Values for an attribute is easy in ADF 11g: create a ViewObject, link it with a List of Values through a View Accessor and add the List of Values to your attribute. That's basically it. If you now drag-and-drop said attribute on your page, JDeveloper will ask you if you want to drop it as a 'Single Selection'. There you select 'ADF Select One Choice', and voila, there you have a dropdownlist with your List of Values.

But sometimes, and it has happened to me before, the dropdownlist is not showing. Of course, you start to check and double check, even up to the point where you just delete everything you just did, and start over. To no avail.

If you ever face this issue, bear in mind that 1 simple configuration can mess up your result. In this particular case, I had the List of Values linked to a Transient Attribute. Of course, Transient Attributes are, by default, not editable. This is quickly fixed by changing the 'Updatable'-property to 'Always'.


If you now run your application again, the dropdownlist is showing correctly! This is one of those things you actually know, but run into every now and again. Especially if it's been a while since you linked a List of Values to a Transient Attribute...

Google App Engine

Recently, I started building my own website. Since I'm a Java developer, I wanted to build a website in Java. For work, I usually build web applications using Oracle's ADF, so for now, I wanted to use some other technology.

Of course, building a website in Java offers a lot of possibilities, but it also has its drawbacks. For example, most free webhosting solutions don't support Java applications. Therefore I had to either put up my own server, or find some cloud solution.

I opted for the latter, and quickly encountered Google as a provider for my needs. And more specifically: Google App Engine. After some quick research, I found that there are plugins for Eclipse (or STS, in my case) to get started easily. After installing the Google App Engine SDK Plugin for Eclipse, creating and deploying an application to the web is a matter of a few clicks!

More information on how to build applications for Google Apps Engine will follow shortly, in upcoming posts.

Stay tuned!