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.

A few thoughts on AppFuse

I've been thinking about how to structure AppFuse for the upcoming Spring and iBatis enhancements. These enhancements shouldn't require any directory structure changes. However, I've received some suggestions to change the common, ejb and web directory structure to be a little more inline with the tiers. So it would become something more like database, business and web (or dao, service and web). After thinking about this for the last couple of days, it seems to make sense. I picked up the notion of common from Erik Hatcher's JavaDevWithAnt, which I borrowed heavily from when creating AppFuse. Erik used common because this represented classes that would be included in both the web tier and the EJB tier. But since I (currently) don't plan on every adding EJBs to AppFuse, does it make sense? Even if I did, I'd probably only use SessionBeans, and those could easily fit into the service layer. The nice thing about moving the business layer (currently in web/**/services) to it's own directory is that it will get it's own JAR (with hardly any modifications to build.xml) and can be used outside of the webapp.

The nice thing about isolating the web directory to web-only classes is I can use Ant to replace any Struts-specific classes with WebWork or Tapestry. To prevent AppFuse from being cluttered with too many options, it'll ship with Struts out-of-the-box. If users want WebWork for their framework, they can download a WebWork version of the web-tier and run an Ant target that will replace all the Struts stuff with WebWorks stuff. It seems like the cleanest way to do web framework switching.

Another thing that might happen to AppFuse, caused by my enthusiasm to try out everything, is that it will contain too much stuff for a basic web application. It currently has security and user management built in, which is what most webapps need. I recently added in OSCache and Clickstream. OSCache is not enabled, but most webapps can probably use it somewhere. Clickstream is a different story. For most of the webapps I've built, this is not needed at all. Most of the apps are no more than 20 screens, and it's unlikely the client will care where people go the most. Another option that deserves ripping out is the idea of Struts' submodules. I tend to rip this out as the first thing when starting a new project. File Upload is something I've used rarely, so I should probably lose that feature too.

There are also other technologies that I've thought of adding to AppFuse, namely Quartz and Lucene. However, I've only used Quartz on 1 of my last 5 projects and Lucene on 2 - so obviously these might be considered bloat for a basic webapp. I think the best thing would be to implement these in AppFuse, on my own, and then document how I did it on the wiki (for an example, see diagramming build.xml with Vizant). If folks need to use it they can add it on their own. Documentation is always good, and if I can just document how to add stuff, I can certainly reduce the bloat.

Whaddya think - is it better to include options out-of-the-box or simply document them? Should I restructure the directories to match the tiers more?

Posted in Java at Jan 23 2004, 06:58:11 AM MST 9 Comments
Comments:

Don't underestimate the use of a logger such as clickstream - even if you don't care about pages popularity it can provide great trace information which can help with debugging. EJB support is overkill - as you said if you have Spring to help implement a DAO (or Gateway + Data Mapper pattern depedning on who you talk to) then its an easy matter to use EJB's etc later. If you do feel the need to add it, then do it as an add-on build task within your ant script. Quartz? Fairly specialized uses I'd expect, as with Lucene. Both good products, don't get me wrong, but neither require a huge amount of configuration if a developer wants to drop them in.

Posted by Sam Newman on January 23, 2004 at 09:13 AM MST #

The day has finally come! Whoohoo, I am so excited. One of the reasons I choose to modify AppFuse when building my own application was to organize the directories a bit more intutively. Now that you are going to do some reworking, I think I can go back to starting with the vanilla AppFuse to make my app. Matt, you rock!

Posted by Dan Allen on January 23, 2004 at 09:27 AM MST #

It's my intention to migrate my app to AppFuse in the coming months. What I would like to see, and what has been suggested in a comment to an older post, is that classes like User and Role move to a 'domain' package. IMHO such classes (and other that are part of my own app like Album, BlogEntry, etc.) represent domain entities and will be used by the business/service layer. The fact that these classes are also made persitend using DOA's & Hibernate is just one (although important) feature of those classes. But they generally serve purposes that go beyond data storage.

Posted by Jaap on January 23, 2004 at 01:36 PM MST #

Good point Jaap - I've been thinking about this but forgot to mention it. For frameworks like Spring and WebWork where I can reuse my POJO in the webapp - this makes perfect sense. So there question is - where should I put it? I'm thinking a package named "org.appfuse.model" will work - but which folder does it belong in? Should it go in the <em>services</em> directory or in the <em>database</em> (or <em>dao</em>) directory? The latter probably makes the most sense - whaddya think?

Posted by Matt Raible on January 23, 2004 at 01:47 PM MST #

Matt, as a side note (and thought for future J2EE 1.4 support) I think you should also make a subdirectory for Web Service Endpoints (wse) and Web Service Clients (wsc).
With J2EE 1.4 allowing for POJOs and Session Beans to be treated as Web Service Endpoints you might think carefully about naming a 'services' subdirectory since services will take on two meanings (business services or web services) as J2EE 1.4 apps become the norm.
Just a thought.

Posted by dsuspense on January 23, 2004 at 02:10 PM MST #

Some would consider the core "domain model" (User, Role, ...) classes to be part of the business model, so placing the "model" package under that could make sense.

OTOH,If you plan on reusing the same set of domain model classes in a number of applications , each with somewhat different business logic, they shoud be separated in to their owne source directory. This is a little esoteric, you have to be planning on a lot of reuse in a number od different applications. Plus you still need to re-process these POJO's using XDoclt to build parts of your presentation (struts, web descriptor, etc.) and persitence logic.

I think the first approach, keeping them in whatever source tree your business logic is in makes the most sense.

Posted by Richard Mixon on January 26, 2004 at 01:21 AM MST #

Matt,

Here's my two cents on Architecture, AppFuse, i18n, etc. Note, I am not an active user of AppFuse yet, only looked at the code. This is partly inspired by your latest post on Java Open Source Programming.

  • Million-$ question: what do you want to do with AppFuse? Do you want to keep it 'An application for starting your web applications' or will it gradually move to 'Matt's private laboratory'. In the latter case, hey, it's your free time and I'll be watching what you come up with! In the first case, I think you should be carefull what you want to offer and how that reflects on AppFuse's architecture. If you want to appeal to the largest possible audience, then this has implications on the layers you use. See below.
  • I strongly feel that Services are the way to go. If you stick business logic in autonomous service classes that are responsible for all manipulations of the model, then a switch to whatever presentation framework, or using multiple views simultanously should be a breeze. The only thing that you have to replicate are the Form - Value Object transformations and Service calls. This is currently *very* relevant, given your urges to try out and provide support for different web frameworks like WebWork and Faces. The one thing you will loose are the Struts-actions. Anything in there will be lost or must be wrapped, adjusted or otherwise butchered (ughh!).
  • Keep the Service layer simple. Interface, implementation and factory should do the trick. Spring can be of help because it's offers great factory functionality. Keeping the layer simple allows anyone to tailor it to their own needs. Using EJB's? Wanna do a WebService? It doesn't really matter because the Service implementation can be wrapped any which way the user wants. Note: IMO the term 'business delegate' is something very much tied to J2EE patterns. From what I know, it is particularly relevant in that context because it hides calls to the Session facade and wrapps all those nasty EJB exceptions into something more meaningfull. I am very much in favour calling things by their real name...
  • I agree with Richard on where to put the model. The model and the services should be closely tied together. As I said, persistence is but one feature of the model classes. The Service layer will be the main actor on the model. In fact, why have a separate section for persistence anyway? Why not stick the DAO's in <code>org.appfuse.model.user.dao</code> or something?
  • Please, please, please don't loose the i18n. You might not believe it, but there are actually people use it (I will!). Remember, on the other side of the Atlantic, language-support will make or break a website. In IT, English is the lingua franca and conveniently so. But in many, many, many other areas it is not.

Quote: To be honest, in AppFuse, all the Managers (a.k.a. business layer) do is transfer POJOs to ActionForms, and then back again. The Managers are were my business logic should go, but I often find it easier to put it in my actions.

So, as you feel that not much is going on in your service classes, perhaps it is time for a good review of what as ended up in the actions classes in all those months ;)

Regards, Jaap

Posted by Jaap on January 26, 2004 at 04:06 AM MST #

Dominic - you have a good point. However, I've never had the need for web services in my apps, and I don't see a need in the future. My clients may say something different, but to be honest - if they want to do web services, they'll probably already have an architecture in place, and I won't be able to use AppFuse. Since I haven't done any webapps with webservices, I won't be adding them to AppFuse - there's just no need. If I ever get on a project that has webservices, and I learn a bit more about them, and how I can use them - then I might integrate them.

Jaap - here's my answers to your bullet points.

<ul class="glassList">
  • <em>> What do you want to do with AppFuse?</em> I want it to be an application that I use to jump start web applications at my clients. I've released it as open source so others could use it and the source could improve. The reason I'm adding Spring, WebWork and Tapestry is because I want to learn those technologies. The WebWork and Tapestry pieces will be separate downloads because Struts is the most popular and most of my clients will likely want to use it. I'm not looking to make all AppFuse user's life's easier - I'm looking to make <em>my life</em> easier. So I don't want the largest possible audience - it's a pain in the ass to do all that support for free. ;-)
  • <em>> Services and simple service layer.</em> This is what my *Manager classes currently represent. However, they do currently cast to ActionForms, so that will have to change, or I'll have to implement different managers (this is probably easier).
  • <em>> Model package should be in services directory.</em> OK that makes sense. I like the persistence package because it makes it easier to test all the DAO's by looking in the "database" directory for *Test.java.
  • <em>> Don't lose the i18n.</em> I don't plan on losing it, but I don't think anyone is using AppFuse for non-English applications. I only say this because there are forwards that are hard-coded to be "action=Edit", which won't work if the there is a button.edit=Key where Key is in another language. I think this issue will go away as I examine other frameworks and bring my findings back into Struts.
  • I don't think there's too much logic in AppFuse's action classes, but implementing other frameworks will surely show me what I'm doing wrong.

    Thanks for all the comments, they're greatly appreciated.

    Posted by Matt Raible on January 27, 2004 at 07:55 PM MST #

    I am in the process right now of adding Quartz to my Struts-based app. It will be part of my service layer so that it can interact with the Session beans while doing some recurring 'batch' operations. I have learned quite a bit from your examples Matt and can't wait to see how you work with Quartz.

    Posted by Wiebe de Jong on January 31, 2004 at 01:52 PM MST #

    Post a Comment:
    Comments are closed for this entry.