Matt RaibleMatt Raible is a Java Champion and Developer Advocate at Okta. developer.okta.com

The JHipster Mini-Book The JHipster Mini-Book is a guide to getting started with hip technologies today: AngularJS, 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.

AppFuse Videos

I know I said I'd never do an AppFuse video, but after having many requests - I decided to go ahead and make a couple. The first one is a demo of creating a new project and then installing and browsing that project in your browser - to see all the out-of-the-box features.

The 2nd one basically all the stuff that's done in the tutorials - using Spring MVC for the web framework. I create a Person.java object and then use AppGen to generate all the code for it. In this one, I make a number of mistakes (but solve them all). I thought about going fully happy-path, but then decided it was important to show some gotchas that might occur.

I used the trial version of Camtasia Studio to create these videos. Thanks to Keith at KGB Internet for hosting the demo site for AppFuse. If you need Tomcat hosting, Keith offers an excellent service at a very good price.

Update: You can also download these videos for off-line use.

Update 2: I updated these videos for AppFuse 1.9.3.

Posted in Java at May 04 2005, 09:48:40 AM MDT 32 Comments
Comments:

Great work,
Here my cygwin tip:
on cygwin (or other unix term), to use color syntaxing on the console, do an:
export ANT_ARGS=-logger org.apache.tools.ant.listener.AnsiColorLogger
on your ~/.bashrc or ~/.antrc

Posted by nbarbosa on May 04, 2005 at 03:55 PM MDT #

Yeah, I know about that tip and use it on my OS X box. However, I'm not able to get it to work with Cygwin on Windows XP or 2000. When running "ant db-load" with that option, I get:

Buildfile: build.xml
?[2;32m
init:?[m
?[2;32m
prepare:?[m
?[2;35m     [echo] Preparing target directory 'C:\Temp\appfuse/build/appfuse'?[m

?[2;32m
db-load:?[m
?[2;36m   [dbunit] Executing operation: CLEAN_INSERT
   [dbunit]           on   file: C:\Temp\appfuse\metadata\sql\sample-data.xml
   [dbunit]           with format: xml?[m
?[2;32m
BUILD SUCCESSFUL
Total time: 3 seconds?[m

If you have any tips for getting this working on Windows - that'd be awesome. ;-)

Posted by Matt Raible on May 04, 2005 at 04:05 PM MDT #

I used appfuse for a while, but after working with Ruby on Rails, Appfuse's development cycle seems a bit tedious. I just feel like when I'm watching your movies, I'm always waiting on Ant or Tomcat, whereas with the Ruby on Rails movies, there's little waiting.

Posted by Matt Moriarity on May 04, 2005 at 04:19 PM MDT #

You have a valid point Matt. I wonder what the rates are for Rails developers these days? I plan on learning Rails sometime this year, but I doubt I'll have an opportunity to use it with corporate clients. Heck, they won't even let me use Tapestry or JSF over Struts! ;-)

Posted by Matt Raible on May 04, 2005 at 04:27 PM MDT #

Well the setting about ANT_ARGS worked for me, Matt, so it might be something with your TERM settings? mine is TERM=cygwin About the videos, are these downloadable?

Posted by Ernesto Echeverria on May 04, 2005 at 04:36 PM MDT #

Ernesto - my TERM *is* set to cygwin. Oh well, it's not a big deal so I'm not too worried about figuring it out. I agree it would be nice for the video, but so would a dual G5. ;-) I'll make sure and re-shoot the videos if I ever buy one.

As far as downloading the videos - I uploaded them to the 1.8 download area under the name "Video Demos" [direct link].

Posted by Matt Raible on May 04, 2005 at 04:41 PM MDT #

"...About the videos, are these downloadable?..." Well, you would probably need to do some hardcore cracking of the url... replacing .html with .swf or something like that... and then save the page ;-)

Posted by en on May 04, 2005 at 04:54 PM MDT #

Ruby on rails thoughts. One: I did a search on monster and found nothing. But that doesn't mean much. Second: Ruby on Rails, as great as it may be, is a hard sell to management. Java is easy to sell. It's proven technology.

Posted by Tom on May 05, 2005 at 07:31 AM MDT #

Matt, I can recognize Eclipse, Firefox, Idea, maybe wincvs icons on your windows launchbar. What are the other applications? Do you mind sharing? Thanks for the cool videos. Prashant Rane

Posted by Prashant Rane on May 05, 2005 at 11:51 AM MDT #

Prashant,

From left to right: Desktop, Firefox, Explorer (that opens to source folder), Eclipse, IDEA, HomeSite, SmartCVS, Cygwin, Word and TopStyle. There's also a bunch more that are hidden - but I don't use them much.

Posted by Matt Raible on May 05, 2005 at 12:58 PM MDT #

Matt, great video, is it possible to include audio too?

Posted by Navier on May 06, 2005 at 11:13 AM MDT #

Navier - I didn't include any audio in these videos, but I'll keep that in mind for the next ones.

Posted by Matt Raible on May 06, 2005 at 01:25 PM MDT #

On the sound comment - I've had trouble getting Camtasia studio to produce sound for the flash based movies (had to revert to the much larger quicktime format to get the sound to work correctly). Apparently the sound with SWF files problem is due to a codec issue, here's a thread from their knoweledge base : http://techsmith.custhelp.com/cgi-bin/techsmith.cfg/php/enduser/std_adp.php?p_faqid=102

Posted by Lance Hankins on May 07, 2005 at 09:42 AM MDT #

[Trackback]

  • AppFuse replaces Container Managed Authentication (CMA) with Acegi Security.
  • Refactoring of build.xml to use Ant 1.6 features.
  • Numerous bug fixes to AppGen.
  • All-in-one installer was also added.
...

Posted by mornlee's blog on May 09, 2005 at 08:43 AM MDT #

Hi Matt, is there a possibility to download the videos? Some developers (like me) have no Internet connection on their develop computers).

Posted by Frank Steinhauer on May 09, 2005 at 09:59 AM MDT #

Cut that Question, just saw the videos in the download section. Maybe you should write that in the text on this page.

Posted by Frank Steinhauer on May 09, 2005 at 10:09 AM MDT #

Frank, there is a link to download the videos buried in the comments of this post. ;-) I've updated this post with a direct link.

Posted by Matt Raible on May 09, 2005 at 10:40 AM MDT #

These videos are great, and can make a more compelling case for customer solutions than straight HTML docs. But please please please, focus on the end solution first by going to the web page as fast as possible to show the direct link between what has to be coded and what it produces. Think with the mind of a "customer" of your framework, as that is your target audience. Remember - unit tests don't matter for those generating code, until they a) first see that everything works by visiting the web interface and b) want to make changes to the code that would then require running the tests.

I think that if you were to cut down this video to only the first 2-4 min of setup and the last 2 min, you would have a compelling video. You can then show other things in subsequent videos, like maintaining the code after it is generated (tests pass/make change/tests fail/fix/tests pass/view web site), and other features. Just be careful not to get bogged down in cmd line too much.

Also, consider having the ant scripts precompile the JSPs, as that time it takes to compile can discourage the customers viewing the videos and provide an improper perception of performance issues within your generated code.

HTH,
James

Posted by James Higginbotham on May 29, 2005 at 04:36 PM MDT #

James - I agree that these videos should be re-done so they're more "to the point" with less mistakes. I did run the "ant test-canoo" to pre-compile the JSPs, but I could have done that as part of the build process as well (since AppFuse supports this). I think it might be a good idea to use something like Viewlets because the length is shortened since it's not a *true* movie - rather it just records screenshots when you click on the mouse. Hopefully I'll have time to re-shoot these sometime this summer.

Posted by Matt Raible on June 06, 2005 at 04:00 PM MDT #

Hey Matt, Did you find out the solution for the ant coloring problem in cygwin? I have the same problem. Thanks. regards, Ivan

Posted by Ivan C. on July 19, 2005 at 11:23 AM MDT #

Ivan - unfortunately I never figured out how to get Ant coloring to work with Cygwin.

Posted by Matt Raible on July 19, 2005 at 11:29 AM MDT #

Hi Matt, your video is cool. Can you tell me what's the plugin you used in IDEA to generate the model object? it seems that it can read the database structure and do the getter/setter with hibernate xdoclet and struts xdoclet as well. Do you know if there is one for eclipse too? I m so interested in your quick code writing with the plugin. Do drop me a line if possible =P. tks!

Posted by Erik Ng on August 08, 2005 at 03:06 AM MDT #

Erik - unfortunately, there is no plugin. I was simply using IDEA's "Live Templates" feature to quickly paste in pre-recorded code.

Posted by Matt Raible on August 08, 2005 at 09:38 AM MDT #

Hi, I am a Chinese, I am studing appfuse, thanks for your videos.

Posted by chenyang on August 23, 2005 at 08:59 PM MDT #

https://appfuse.dev.java.net/servlets/ProjectForumMessageView?messageID=10546&forumID=566 I have built an optimized WSAD 5.1.1 workspace containing the equinox (Appfuse) application. The app is running on a WAS 5.1 Server. The view layer is Struts. The DAO layer is Hibernate. The workspace contains a minimal amount of libraries to make the application run. Happy Appfusing, Joel Cohen

Posted by Joel Cohen on December 12, 2005 at 09:13 AM MST #

Ivan - I did find a solution. However, when I built a new machine last week (and installed the latest version of Cygwin), I didn't have to do anything fancy - the Ant color logger <em>just works</em>. Strange...

Posted by Matt Raible on December 29, 2005 at 11:11 PM MST #

Matt, I followed the steps in the tutorial to create a new domain object and let appgen to create all the necessary classes. When I pull up the "siteForm" page and try to save the record as it is, everything goes well. When I update a field and then I try to save the record, this is what happens. java.lang.NullPointerException at org.hibernate.type.IntegerType.next(IntegerType.java:57) at org.hibernate.engine.Versioning.increment(Versioning.java:25) at org.hibernate.event.def.DefaultFlushEntityEventListener.getNextVersion(DefaultFlushEntityEventListener.java:262) at org.hibernate.event.def.DefaultFlushEntityEventListener.onFlushEntity(DefaultFlushEntityEventListener.java:140) at org.hibernate.event.def.AbstractFlushingEventListener.flushEntities(AbstractFlushingEventListener.java:190) at org.hibernate.event.def.AbstractFlushingEventListener.flushEverythingToExecutions(AbstractFlushingEventListener.java:70) at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:26) at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:730) at org.hibernate.impl.SessionImpl.managedFlush(SessionImpl.java:324) at org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:86) at org.springframework.orm.hibernate3.HibernateTransactionManager.doCommit(HibernateTransactionManager.java:490) at org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:495) at org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:468) at org.springframework.transaction.interceptor.TransactionAspectSupport.doCommitTransactionAfterReturning(TransactionAspectSupport.java:258) at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:106) at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:144) at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:174) at $Proxy4.saveSite(Unknown Source) at hqda.acsim.sv.webapp.action.SiteFormController.onSubmit(SiteFormController.java:63) at org.springframework.web.servlet.mvc.SimpleFormController.processFormSubmission(SimpleFormController.java:258) at hqda.acsim.sv.webapp.action.BaseFormController.processFormSubmission(BaseFormController.java:174) at org.springframework.web.servlet.mvc.AbstractFormController.handleRequestInternal(AbstractFormController.java:245) at org.springframework.web.servlet.mvc.AbstractController.handleRequest(AbstractController.java:139) at org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter.handle(SimpleControllerHandlerAdapter.java:44) at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:684) at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:625) at org.springframework.web.servlet.FrameworkServlet.serviceWrapper(FrameworkServlet.java:386) at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:355) at javax.servlet.http.HttpServlet.service(HttpServlet.java:709) at javax.servlet.http.HttpServlet.service(HttpServlet.java:802) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:252) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:173) at com.opensymphony.module.sitemesh.filter.PageFilter.parsePage(PageFilter.java:118) at com.opensymphony.module.sitemesh.filter.PageFilter.doFilter(PageFilter.java:52) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:202) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:173) at hqda.acsim.sv.webapp.filter.GZIPFilter.doFilter(GZIPFilter.java:51) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:202) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:173) at org.displaytag.filter.ResponseOverrideFilter.doFilter(ResponseOverrideFilter.java:125) at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:202) at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:173) at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:75) at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:76) any ideas, Thanks Fadi

Posted by Fadi Samara on March 30, 2006 at 11:06 AM MST #

Fadi - can you post your domain object and the steps you went through to the mailing list. That's a better support forum. Send a blank e-mail to users-subscribe + appfuse.dev.java.net to subscribe.

Posted by Matt Raible on March 30, 2006 at 12:01 PM MST #

quisiera saber si con este programa puedo bajar films. reel to reel de 10 segundos aprox. gracias julio

Posted by julio BRADFORD on July 21, 2006 at 11:17 AM MDT #

//-------------------------- //Hi,I am a Chinese -!- //thanks for your videos. //You are great //Thank you very much? //-------------------------

Posted by ALX on February 03, 2007 at 01:30 AM MST #

Help me, somebody have solutions about this problems. my domain is the seams oject user appfuse.

  [java] java.lang.NullPointerException
     [java] at org.hibernate.type.IntegerType.next(IntegerType.java:59)
     [java] at org.hibernate.engine.Versioning.increment(Versioning.java:25)
     [java] at org.hibernate.event.def.DefaultFlushEntityEventListener.getNextVersion(DefaultFlushEntityEventListener.java:360)
     [java] at org.hibernate.event.def.DefaultFlushEntityEventListener.scheduleUpdate(DefaultFlushEntityEventListener.java:250)
     [java] at org.hibernate.event.def.DefaultFlushEntityEventListener.onFlushEntity(DefaultFlushEntityEventListener.java:121)
     [java] at org.hibernate.event.def.AbstractFlushingEventListener.flushEntities(AbstractFlushingEventListener.java:196)
     [java] at org.hibernate.event.def.AbstractFlushingEventListener.flushEverythingToExecutions(AbstractFlushingEventListener.java:76)
     [java] at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:26)
     [java] at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:1000)
     [java] at com.mundial.core.webapp.filter.FlushingSpringSessionInViewFilter.closeSession(FlushingSpringSessionInViewFilter.java:33)
     [java] at org.springframework.orm.hibernate3.support.OpenSessionInViewFilter.doFilterInternal(OpenSessionInViewFilter.java:183)
     [java] at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:77)
     [java] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:202)
     [java] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:173)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:264)
     [java] at org.acegisecurity.intercept.web.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:107)
     [java] at org.acegisecurity.intercept.web.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:72)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:274)
     [java] at org.acegisecurity.ui.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:110)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:274)
     [java] at org.acegisecurity.providers.anonymous.AnonymousProcessingFilter.doFilter(AnonymousProcessingFilter.java:125)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:274)
     [java] at org.acegisecurity.ui.rememberme.RememberMeProcessingFilter.doFilter(RememberMeProcessingFilter.java:142)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:274)
     [java] at org.acegisecurity.wrapper.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:81)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:274)
     [java] at org.acegisecurity.ui.AbstractProcessingFilter.doFilter(AbstractProcessingFilter.java:217)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:274)
     [java] at org.acegisecurity.ui.logout.LogoutFilter.doFilter(LogoutFilter.java:108)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:274)
     [java] at org.acegisecurity.context.HttpSessionContextIntegrationFilter.doFilter(HttpSessionContextIntegrationFilter.java:193)
     [java] at org.acegisecurity.util.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:274)
     [java] at org.acegisecurity.util.FilterChainProxy.doFilter(FilterChainProxy.java:148)
     [java] at org.acegisecurity.util.FilterToBeanProxy.doFilter(FilterToBeanProxy.java:98)
     [java] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:202)
     [java] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:173)
     [java] at com.mundial.core.webapp.filter.StrutsAjaxFilter.doFilterInternal(StrutsAjaxFilter.java:33)
     [java] at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:77)
     [java] at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:202)
     [java] at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:173)
     [java] at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:213)
     [java] at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:178)
     [java] at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:126)
     [java] at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:105)
     [java] at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:107)
     [java] at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:148)
     [java] at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:869)
     [java] at org.apache.coyote.http11.Http11BaseProtocol$Http11ConnectionHandler.processConnection(Http11BaseProtocol.java:664)
     [java] at org.apache.tomcat.util.net.PoolTcpEndpoint.processSocket(PoolTcpEndpoint.java:527)
     [java] at org.apache.tomcat.util.net.LeaderFollowerWorkerThread.runIt(LeaderFollowerWorkerThread.java:80)
     [java] at org.apache.tomcat.util.threads.ThreadPool$ControlRunnable.run(ThreadPool.java:684)
     [java] at java.lang.Thread.run(Thread.java:595)

Posted by Leandro Tapia on March 08, 2007 at 06:59 PM MST #

Leandro, please post any issues you run into to the AppFuse mailing list. Thanks.

Posted by Matt Raible on April 09, 2007 at 09:44 PM MDT #

Post a Comment:
  • HTML Syntax: Allowed