Matt RaibleMatt Raible is a Web Developer and Java Champion. Connect with him on LinkedIn.

The Angular Mini-Book The Angular Mini-Book is a guide to getting started with Angular. You'll learn how to develop a bare-bones application, test it, and deploy it. Then you'll move on to adding Bootstrap, Angular Material, continuous integration, and authentication.

Spring Boot is a popular framework for building REST APIs. You'll learn how to integrate Angular with Spring Boot and use security best practices like HTTPS and a content security policy.

For book updates, follow @angular_book on Twitter.

The JHipster Mini-Book The JHipster Mini-Book is a guide to getting started with hip technologies today: Angular, Bootstrap, and Spring Boot. All of these frameworks are wrapped up in an easy-to-use project called JHipster.

This book shows you how to build an app with JHipster, and guides you through the plethora of tools, techniques and options you can use. Furthermore, it explains the UI and API building blocks so you understand the underpinnings of your great application.

For book updates, follow @jhipster-book on Twitter.

10+ YEARS


Over 10 years ago, I wrote my first blog post. Since then, I've authored books, had kids, traveled the world, found Trish and blogged about it all.

Tapestry by Example with Erik Hatcher

It's Saturday morning and I plan on learning more about Tapestry this morning. There's pretty light attendence in the room. Too bad - I bet if it was a JSF talk, the room would be packed. In this talk, we're actually going to build a real application on-the-fly.

Why another web framework?

  • HTML should be HTML
  • JavaScript Embraced
  • Reusable components
  • Free developer from dealing with plumbing
    • Request/Response
    • Session/Application Scope
    • URL Mappings (nice, but leads to ugly URLs)
  • Event handler driven
  • Asset handling
  • Line-precise error reporting

Erik says its one of the few frameworks that embraces JavaScript so much. I dig this b/c I think JavaScript is important for web development. Look at what the GMail guys have done with JavaScript. It'd be wicked cool to have this sort of thing open-sourced so we could all create GMail-type interfaces.

Dirty Laundry

  • Heavy Duty - can be overkill for small/simple app
  • Potentially steep learning curve. More of an un-learning curve. The Servlet API isn't in your face - so all that knowledge is useless.
  • Not widely accepted - managers haven't heard of it
  • Some awkward conventions (i.e. abstract classes)
    • and some non-intuitive necessary tricks
  • Unit testing tough - do you unit test your swing app's listener methods?
    • Tapestry Test Assist should solve this problem
    • Howard's caught the TDD bug, so this should get better
  • Lousy URLs - there's a patch on the wiki to fix this
    • Tough to do hit/stat tracking
    J2EE declarative security
  • Example applications

Workbench Demo - DatePicker component does do i18n (very cool!). Client-side validation does one-field at a time, like WebWork does. I prefer the "all messages in one pop-up" approach that Commons Validator has. Pallete component looks very cool - you can move and re-order items from a multi-select on the left to a multi-select on the right. Chart component looks pretty cool - you can generate graphs very easily. Unfortunately, it's not part of Tapestry, but you can see how to do it in the Workbench app. If you want to see an online version of the workbench, I have it setup on my server.

Repositories for components: Tacos, Tassel, T-Deli and a few mentioned on the wiki.

To bring a component to life, you simply add a "jwcid" to an HTML tag. You can specify initial values for page properties using <property-specification initial-value=""> tag in your template's .page file. The value is implicitly an OGNL expression, and you can define lists using "{'value1', 'value2', 'value3'}". This is great for prototyping before you have a backend or even a page class. To remove elements in a page, specify jwcid="$remove$" on an HTML element and it'll be removed at render time. The restriction is you can't have Tapestry components inside a $remove$ component.

If you don't want to use abstract methods (and hence classes) in your page class, you can use getProperty()/setProperty() methods. However, the recommended way is to use abstract methods.

Templates - two different types. You can put the @component stuff directly into your page - or you can use jwcid's and refer to a name that's defined as a <component> in your page-specification XML file. The Border component can be used to do page decoration like SiteMesh. You can use the Shell component to declare stylesheets/scripts on a per-page basis. This is something I do a fair amount, so it's nice to see it's built into Tapestry.

Internationalization - Resource bundles are component specific (one .properties per page). In a .page, you use <message-binding>. In a template (.html), you use attribute="message:key" or <span key="">. The "key" attribute can't be used on any ol' HTML element, only on the <span> tag. In .java, you use getMessage() and format(). You can also define a custom message source (i.e. read messages from a database). I'm impressed with how easy it is to do i18n in Tapestry. It's also cool that i18n is built-in for templates. Just include a locale extension on your page and it'll be rendered for users with that locale. For example, home_fr.html will show up for users with the French Locale.

Engine - gets all requests. Visit class - POJO that acts as like an HttpSession. You can configure it in the .application file. You can talk to your "Visit" class in a template using "ognl:visit". To call methods on it, just use "ognl:visit.method". Majority of services originate in the Engine. Generally override createXXX methods. Engines can be pooled or created on a per-session basis.

If you override the createXXX methods in Engine, you change the behavior for:

  • message source
  • global and visit
  • property configuration
  • template and component sources

contrib:Table - to override use <tr jwcid="columnColumnValue@Block"> - where "column" is the name of the column. Using this, you can easily put links and such into a table cell. Built-in TableModel can be used to talk directly to a JDBC DataSource. The TableModel is smart in that it only brings back the rows it needs to display. Add an exclamation point to the beginning of a column name to turn off sorting for that column. i18n is built-in for headers - the name of the column is simply looked up as a key in the page's .properties file.

Exception handling - Bail out by throwing an ApplicationRuntimeException. This tosses you to the default exception page, which you can override and "pretty up".

Validation - it's robust, but it can only validate <input type="text">. Erik thinks that Tapestry's validation framework could be much simpler and easier to use.

Dynamic Templates - can implement a IDelegateSourceTemplate and pull templates from a database or content-management system. To register your new TemplateDelegate, you can just register an <extension> in the .application file and point it to your class.

Page Lifecycle - initialize(), PageRenderListener(), PageValidateListener(), PageDetachListener(). Can use an ExternalCallback and ICallback to set properties on one page from another. Callbacks look very cool and there's a lot of discussions about them on the mailing list. The VLib app has a fair amount of callback examples.

This was definitely a good Tapestry session - thanks Erik.

Posted in Java at Nov 13 2004, 12:53:59 PM MST 4 Comments

XDoclet and JDK 5.0

One of the major issues in XDoclet's JIRA has been the fact that XDoclet doesn't work with JDK 5.0 syntax. After many comments and lots of debate, Anton Adamansky has submitted a patch. If you want to use XDoclet with JDK 5.0 - you might want to give this patch a run for its money. Hopefully we can get it included in XDoclet in the near future.

Posted in Java at Nov 13 2004, 08:22:24 AM MST Add a Comment