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.

The AppFuse Generator

I found the AppFuse Generator project in my comments last night. Richard So seems to have created a nice code-generation tool for AppFuse. It looks like it can create/modify all the files you need to CRUD a database table. I took a brief look at the code and it's all based on Velocity templates, so you should be able to easily tweak things.

This tool does seem to generate the DAOs/Managers - which can lead to more code to maintain. It would be nice if it could be modified to be similar to AppGen where there's a "detailed" version (that generates everything) and a "default" version (which only generates the web tier classes). The default version could use the generic "dao" and "manager" beans. I wonder if this tool supports running/installing the same table more than once? This currently doesn't work too well with AppGen, but shouldn't be too hard to fix.

In reality, I'm pumped that Richard has created this, as well as a project to back it up. I especially like that he's going to try and create an Eclipse Plug-in as part of this project. Nice work Richard!

Posted in Java at Nov 22 2004, 04:39:35 AM MST 8 Comments

Studying vs. Doing

My parents are in town for this next week and I expect to relax most of the week, but also squeeze a few hours in each day for Java. I'll probably do a bit of work for clients, but I expect to spend most of my time with Tapestry and JSF. I have to write a chapter that includes these frameworks in 3 weeks and I hope to integrate them into AppFuse by the end of the year.

Last night, I started thinking - I can use this week for 2 things: reading or doing. I could finish reading Tapestry In Action and get a good start on Core JSF. Or I could make the leap and begin implementing them in AppFuse. The latter sounds like more fun. Of course, the books should serve as good reference guides when I need help.

Posted in Java at Nov 20 2004, 02:14:21 PM MST 1 Comment

[ANN] DisplayTag 1.0 RC2 Released

Fabrizio, the main man behind the Display Tag, has been fixing bugs and adding features at breakneck speed. Early this morning, he released the final 1.0 candidate for the Display Tag. Good stuff - thanks Fabrizio!

Posted in Java at Nov 20 2004, 09:53:59 AM MST 5 Comments

Tuesday at ApacheCon

Tuesday at ApacheConIt's now Tuesday morning at ApacheCon and I'm proud to admit I've been pretty lame on the party front so far. It feels great though, I went to bed at 10:30 last night and slept until 9:30 this morning. I pretty much crashed after having such a hectic schedule the last couple of day.

On Saturday night, I was up until 4:00 a.m. cranking out Chapter 10 of Spring Live. I got back up at 7:30 and almost finished it by noon. At 1:00, I arrived at Denver's No Fluff Just Stuff, and moderated a BOF on Comparing Web Frameworks. Then at 2:00, I did a session on AppFuse. Following that, I spent 2 hours finishing up Chapter 10 and sent it off to for editing. 18 pages in 18 hours - oof.

After sending off my chapter, I headed home and had dinner with the family before heading to the airport at 7:00. We arrived in Vegas at 10:30 and went to the Hard Rock for beers. I didn't have any cash so I borrowed some from Jim. After 10 minutes of Blackjack, I was up $120, so I paid Jim back and called it a night. I got heckled as I left the Hard Rock at 3:00 a.m.

Yesterday (Monday), I woke up at 8:30 with a raging hangover. Damn wine chasers - don't seem to work for beer. Bruce didn't take any, got 3 hours of sleep and felt fine. My talk was at 11:00 and I managed to stifle the hangover about 5 minutes before it. The talk went well and the room was packed (approx. 100 folks). After the talk, I grabbed some lunch with Scott, Jim, Jonathan, Howard and his wife.

At 2:00, Dion interviewed me for TheServerSide. At 3:00, I had a meeting with the SourceBeat guys, and had some beers with Michael Koziarski around happy hour. Then I hit an ApacheCon sponsored free-beer thing and later headed to the "Pink Taco" with Jonathan and Dave. I could barely stay awake after dinner, so headed to bed early.

Today, I plan on attending a few sessions and possibly doing some gambling this evening. Sure is nice not having any commitments for the rest of the week. I have a few meetups with folks, but nothing that requires preparation.

Posted in Java at Nov 16 2004, 12:42:29 PM MST

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

Facets of Ruby by Dave Thomas

You can learn Ruby in 4 hours. This talks isn't to learn Ruby, but rather to show facets of Ruby. Ruby has made programming fun again for Dave. It's also made him more productive.

Languages and tools make a difference

Ruby has variables, methods, but no types in methods. When Dave first started using Ruby, he had a strong typing background - and was terrified of Ruby's un-typed feature. He first thought Ruby was a toy language for hobbyists because of the lack of typing. Now, many years later, he really likes the lack of typing and hardly even has bugs relating to typing. He notes that with Java we store most of our data in Collections - and those are all Objects - so Java is essentially un-typed as well. How often do you get ClassCastExceptions? The rooms concensus is not not a whole lot. To make up for the lack of typing, Ruby developers tend to write a lot more unit tests.

ActiveRecord - Ruby O/R Mapping Library

Ruby on Rails - not a single line of XML. Uses intelligent defaults and allows you to override them. The following creates a wrapper around the "ranks" table.

class Rank < ActiveRecord::Base
end

The original author of RoR thinks that every database table should be plural, so singular class names map to plural table names. It's even smart enough to change Person to a "people" database table. Apparently it has a bunch of the singular-to-plural mappings for the English language built-in. The key to Rails is clever defaulting - allow you to write a lot less code, but override if you really need to.

ActiveRecord has many lifecyle hooks (17) that you can override. For example, before_save, before_destroy, validate. For example

def before_save
  self.when_added ||= Time.now
end

I wonder if Rails has any support for transactions and specifying propagation behavior on transactions? I asked Dave this question and it sounds like ActiveRecord has a rich support for transactions - and even wraps the "save" method with a transaction by default.

"Ruby is pretty damn good at web applications"

Simple CGI is a common choice. FastCGI and mod_ruby in Apache are other common choices. There are also a number of different web frameworks for Ruby:

  1. Roll-your-own
  2. Templating systems
    1. erb
    2. Amarita
    3. RDoc templates
  3. Iowa - similar to WebObjects
  4. Ruby on Rails

Ruby on Rails - MVC Framework

Contoller - one method per view. Setup context (a.k.a. the model) for views. Views contain "rhtml" - HTML with embedded Ruby. Lots of helper functions. Can access model data (context) setup by Controller. The name of the method in the Controller determines the name of the view file. A "select" method will dispatch to a "select.rhtml" file. The method name to call in a Controller is determined by the URI - for example, /ranks/view calls the "view" method in the RanksController class. Pretty slick! I like the idea of smart defaults - IMO this should be used a lot more in webapps. I'd love to get away from mapping URLs in Struts, Spring and WebWork.

Rails has built-in support for configurable URLs - so you can change query strings to more slash-type URLs. What about things like client-side validation, success messages and sortable/pageable tables? Do those exist in Rails? I asked Dave and he said said they have good support for success messages with a "flash" concept and the post-to-redirect problem is almost non-existant because most controller invocations are redirects. Client-side validation and sortable/pageable tables don't exist in Rails.

Rails has Needles - and IoC framework similar to Pico. However, there's a fair amount of traffic on the mailing list and a lot of Ruby developers think they just don't need IoC. Dave's suggestion is to use Class Injection.

The largest Ruby application is probably Daves - 55,000 lines or code, couple hundred thousand users. There are entire companies who write all all their applications in Ruby. The founder of Rails wrote it so he could write Basecamp - which is only 4500 lines of code.

Good stuff Dave - and definitely a nice overview of Rails. Will I be digging in an using Rails anytime soon? Not this year, I'm going to have some fun with Tapestry and JSF first. Maybe next year.

Posted in NFJS at Nov 12 2004, 06:39:59 PM MST

Design Patterns Revisited: Taking Advantage of Dynamic Reflective Languages by Stuart Halloway

SmartFactory - one factory for all factories. Allows developers to handle failures rather depending on various factories. Unfortunately, you will have to do Casts. Stuart things that Generics should've never been added and instead we should just have no casts. Instead, the compiler should inject the cast implicitly.

Document d = SmartFactory.getInstance();

Java might be a lot more powerful if we could return a different type from constructors - like Class Clusters in Objective-C. You can get a lot of dynamic features in Java using AspectJ. Java Developers have a lot of responsibility when they start using aspects.

Stuarts talk was 3 hours and I only attended the first half. He's a very good speaker and I enjoyed listening to him more a lot. The basic gist of his talk seemed to be that Java should be more dynamic, and using AspectJ, it can be. I thought he was going to recommend we switch languages - so I was surprised to here him recommend AOP. The last example he gave was how to interrupt a FileInputStream so you could test the condition in a unit test. I can see how this could be quite useful for causing network or database failures and seeing how your application behaves.

Posted in NFJS at Nov 12 2004, 06:38:07 PM MST

Ant Hacks by Erik Hatcher

The first session I attended was Erik Hatcher's Ant Hacks talk. The first half of his talk was about Ant in general and was most of the stuff covered in Java Development with Ant. The good stuff was the 2nd half when he covered all the new stuff in Ant 1.6. Steve is working on an update to Java Development with Ant - shoujld will be a lot thinner. Below are some notes I took on what's new in 1.6.

  • <image> task. Requires Java Advanced Imaging API
    • Performs image manipulation
  • <import> task
    • No more entity ref includes needed - can use Ant properties for file reference now.
    • OO Nature
      • mix in imported build files - call super on imported file by specifying depends="${ant.project.name}.target" where the project.name is specified in the imported build file. Only targets that are overridden will get prefixed with namespace.
      • target overriding - main build file takes precedence
      • "abstract" targets - requires main build file implementation
  • <subant> task - Recurses tree
    • Two modes: 1) same build file in each sub directory 2) crawl a tree and run same build file on all subdirectories
  • Can have targetless build files. Everything outside a target gets executed before any targets
  • <presetdef> - Use the same task and optionally repeat. Define the options once, give it a name and refer to it later. Can override attributes later in the build.xml file. Only works for one task at a time.
  • <macrodef> - bye bye antcall. Much faster than antcall - does all the same things
    • You can specify attributes and elements as part of the definition. Tasks are wrapped in a <sequential> tag.
      • attributes are referred to in tasks using @{attribute}
      • elements are simple placeholders using XML <element/>
    • I could really use this stuff in AppFuse to replace the compile-module and test-module targets
    • "spawn" a new attribute on <java> - allows process to live past when Ant dies
  • <scriptdef> - allows you to use all kinds of scripting languages - i.e. Groovy, JavaScript, etc.
    • the project, attributes and elements are given to you - so you can easily grab them in the scripts
    • helpful to know Ant's API when writing
  • <antlib> - componentizes definition of types and tasks
    • anything that defines stuff - put in antlib.xml (i.e. <taskdef>)
    • mostly designed for Ant task distributors because they can package an antlib.xml with a namespace
    • has root element of <antlib> instead of XML
      • xmlns:antcontrib="antlib:net.sf.antcontrib" - brings in all tasks into your project

I really liked Erik's talk because AppFuse was inspired by his Java Development with Ant book. Its build.xml file was intially based on Erik's sample app and therefore, the first half of his talk pretty much pointed out tips and tricks that I'm currently using. The 2nd half of his talk was highlighting the new features of 1.6 - which he's suggested I adopt in the past. I've never had much desire (or time) to dig in and update AppFuse's build.xml file to 1.6. However, after attending his talk - it seems like it should be pretty easy to do. Good bye <antcall>, hello <macrodef>.

Later: One of the coolest things I saw in Erik's talk was how his Ant logging was color coded. I asked him about it and all your need to do is specify "-logger org.apache.tools.ant.listener.AnsiColorLogger" in an ANT_ARGS environment variable. Good stuff!

Posted in NFJS at Nov 12 2004, 05:12:12 PM MST 1 Comment

Denver's No Fluff Just Stuff starts today

It's time for another NFJS conference. I attended the one in June and had an awesome experience. I doubt I'll cover it as much as I did last time, that's just a lot of work - not to mention my cell phone's data bill was $300! As I look through the sessions, I'm noticing that it's a great thing to attend 2 of these conferences - b/c you can skip all the sessions you saw the first time. Since there's usually 2-3 good ones per time slot, reducing that down to 1-2 is nice.

This afternoon, I'm planning to attend sessions by Erik Hatcher and Stuart Halloway. Erik for Ant 1.6 and Subversion (maybe even Lucene) and Stuart for "dynamic, reflective languages". Since much of AppFuse's build.xml is based on Erik's Java Dev with Ant sample app, it'd be nice to figure out how to take advantage of 1.6 features (especially since 1.6.2 is required). I've never seen Stuart speak before, but I've heard he's excellent.

Saturday I plan on learning more about Tapestry from Erik (in a 3-hour session!). Since adding Tapestry to AppFuse is my next open-source development effort, this weekend and ApacheCon are good opportunities to learn more about it. I know, I should just buck up and read the book (I made it to page 100 a couple of weeks ago, nothing since), but it's tough to find the time.

I'll probably skip out tomorrow afternoon and work on Spring Live since Chapter 10 is due by Monday and I'm not done yet. Sunday, I'll be talking about AppFuse making open-source easier. "Brain, get ready to be stuffed."

Posted in NFJS at Nov 12 2004, 09:11:55 AM MST Add a Comment