Login Logout in Flex
login & logout for flex web application sample code
//main Application file
<?xml version=”1.0″ encoding=”utf-8″?>
<mx:Application xmlns:mx=”http://www.adobe.com/2006/mxml” xmlns:lw=”components.LoginWindow”
layout=”absolute” width=”100%” height=”100%”
creationComplete=”initApplication()”
visible=”false” >
<mx:RemoteObject id=”userLoginRO”
destination=”UserSessionService”
fault=”faultHandler(event)”>
<mx:method name=”removeAttribute” result=”logoutHandler( event )”/>
</mx:RemoteObject>
<mx:Script>
<![CDATA[
import components.LoginWindow;
import mx.managers.PopUpManager;
import mx.events.MenuEvent;
import mx.controls.Menu;
import mx.controls.Alert;
import mx.events.ModuleEvent;
import mx.modules.ModuleManager;
import mx.modules.Module;
import mx.modules.IModuleInfo;
import mx.events.MenuEvent;
import mx.controls.menuClasses.MenuBarItem;
private var moduleToBeLoaded:Module;
private var moduleInfo:IModuleInfo;
private var moduleName:String;
private var module:Module;
import vo.LoginMaster;
import vo.user.LoggedInUserDetails;
import mx.rpc.events.FaultEvent;
import mx.rpc.events.ResultEvent;
public var loggedInUser:LoginMaster;
public var loggedInUserID:int;
public var loggedInUserDetails:LoggedInUserDetails;
public var loginUserStatus:SharedObject;
public var isUserLogged:Boolean;
/* Method used to get which menu item selected */
private function menuItemHandler(event:MenuEvent):void
{
moduleName=event.item.@modulename;
loadModule(event.item.@url);
}
/* Method determines modules to be loaded from given URL */
private function loadModule(moduleURL:String):void
{
moduleInfo=ModuleManager.getModule(moduleURL);
moduleInfo.addEventListener(ModuleEvent.READY, renderModule);
moduleInfo.addEventListener(ModuleEvent.ERROR, renderModuleError);
moduleInfo.load();
}
/* Loads module into Parent Container */
private function renderModule(event:ModuleEvent):void
{
if (applicationModuleCanvas.getChildren().length > 0)
{
applicationModuleCanvas.removeChild(moduleToBeLoaded);
}
if (moduleName == "FirstModule"){
moduleToBeLoaded=moduleInfo.factory.create() as FirstModule;
}else if (moduleName == "SecondModule"){
moduleToBeLoaded=moduleInfo.factory.create() as SecondModule;
}
applicationModuleCanvas.addChild(moduleToBeLoaded);
}
/* Error Display Wile loading Modules */
private function renderModuleError(event:ModuleEvent):void
{
if (event.errorText == "Error #2035")
{
Alert.show("Please Provide Module URL in MenuItem URl Property", "Module Not Found");
}
else
{
Alert.show(event.errorText, "Error");
}
}
/* Init Application with login window */
private function initApplication():void
{
loggedInUserID = 0;
loggedInUserDetails = new LoggedInUserDetails();
loggedInUser = new LoginMaster();
var loginWindow:components.LoginWindow ;
loginUserStatus = SharedObject.getLocal("loginUserStatus");
if (loginUserStatus.data.isUserLogged==null) {
loginWindow = new components.LoginWindow();
PopUpManager.addPopUp(loginWindow, this, true);
PopUpManager.centerPopUp(loginWindow);
} else {
Application.application.visible = true;
welcomeNoteTxt.text = "Welcome ....."+ loginUserStatus.data.userName ;
}
}
/* Method used to get which menu is selected */
private function menuHandler(event:MouseEvent):void
{
var selectedMenu:MenuBarItem=MenuBarItem(event.target)
if (XMLList(selectedMenu.data).*.length() == 0)
{
var moduleURL:String=MenuBarItem(event.target).data.@url;
if (moduleURL.length != 0)
{
moduleName=MenuBarItem(event.target).data.@modulename;
loadModule(moduleURL);
}
else
{
logOutUserFromApplication();
}
}
}
/* Method used to logout from the application */
private function logOutUserFromApplication():void{
loginUserStatus.clear();
//userLoginRO.removeAttribute(loggedInUserID);
Application.application.visible = false;
initApplication();
}
/* Method used to set LoggedIn UserDetails such as Welcome Note etc ..*/
public function setLoggedInUserDetails():void{
loggedInUser = loggedInUserDetails.login as LoginMaster;
loggedInUserID = loggedInUser.id;
loginUserStatus.data.isUserLogged = true;
loginUserStatus.data.userName = loggedInUser.firstName + " "+ loggedInUser.lastName;
loginUserStatus.flush();
welcomeNoteTxt.text = "Welcome ....."+ loginUserStatus.data.userName ;
}
/* Fault Handler */
private function faultHandler(event:FaultEvent):void{
Alert.show("There was a problem "+event, "Error..");
}
/* logout Handler */
private function logoutHandler(event:ResultEvent):void{
Alert.show("You Have Successfully Logged Out ","User LogOut ");
}
]]>
</mx:Script>
<mx:VBox width=”100%”
height=”100%”>
<mx:Canvas width=”100%”
height=”8%”>
<!–<mx:Image id=”companylogo”
source=”@Embed(source=’images/companylogo.jpg’)”
x=”10″
y=”4″/>–>
<mx:Text x=”809″ y=”33″ width=”349″ id=”welcomeNoteTxt” enabled=”false” fontWeight=”bold” textAlign=”left”/>
</mx:Canvas>
<mx:MenuBar id=”appMenuBar”
labelField=”@label”
width=”100%”
height=”25″
fontWeight=”bold”
fontSize=”12″
themeColor=”#ffcc00″
itemClick=”menuItemHandler(event)”
click=”menuHandler(event)”>
<mx:XMLList>
<menuitem label=”FirstModule”
url=”FirstModule.swf”
modulename=”FirstModule”/>
<menuitem label=”SecondModule”
url=”SecondModule.swf”
modulename=”SecondModule”/>
<menuitem label=”Logout”/>
</mx:XMLList>
</mx:MenuBar>
<!– modules//FirstModule.swf –>
<!– Selected Modules from menu will be displayed in this Canvas –>
<mx:Canvas id=”applicationModuleCanvas”
width=”100%”
height=”85%”
cornerRadius=”0″
backgroundColor=”#FDFDFD”
borderStyle=”inset”>
</mx:Canvas>
</mx:VBox>
</mx:Application>
// loginwindow file under src/components
<?xml version=”1.0″ encoding=”utf-8″?>
<mx:TitleWindow xmlns:mx=”http://www.adobe.com/2006/mxml” layout=”absolute” width=”461″ height=”202″
creationComplete=”initLoginWindow()” title=”Enter UserName and Password to continue …” fontSize=”12″>
<!– RemoteObject Used to Authenticate User–>
<mx:RemoteObject id=”userManagementRO”
destination=”userManagementService”
fault=”loginWindowfaultHandler(event)”>
<mx:method name=”validateUserNamePassword” result=”loginUserHandler(event)”/>
</mx:RemoteObject>
<mx:Script>
<![CDATA[
import vo.user.RoleMenuMapping;
import mx.core.Application;
import mx.controls.Alert;
import mx.rpc.events.FaultEvent;
import mx.rpc.events.ResultEvent;
import mx.managers.PopUpManager;
import mx.utils.StringUtil;
import mx.messaging.FlexClient;
import vo.LoginMaster;
import vo.user.LoggedInUserDetails;
import flash.net.SharedObject;
public var loggedInUser:LoginMaster;
public var loggedInUserDetails:LoggedInUserDetails;
/* Check User Name, Password were EMPTY */
private function loginUser():void{
var isUserNamePasswordNotNull:Boolean=true;
var userName:String=StringUtil.trim(userName.text);
var password:String=StringUtil.trim(password.text);
if(userName.length==0 && password.length==0){
loginStatusLbl.text="Please Enter UserName and Password ","User Login";
isUserNamePasswordNotNull=false;
}else if(userName.length==0){
loginStatusLbl.text="Please Enter User Name","User Login";
isUserNamePasswordNotNull=false;
}else if(password.length==0){
loginStatusLbl.text="Please Enter Password","User Login";
isUserNamePasswordNotNull=false;
}
if(isUserNamePasswordNotNull==true){
userManagementRO.validateUserNamePassword(userName,password);
}
}
/* RemoteObject Fault Handler */
private function loginWindowfaultHandler(event:FaultEvent):void{
Alert.show("There is a problem."+event, "Error..");
}
/* RemoteObject Login User Handler */
private function loginUserHandler(event:ResultEvent):void{
loggedInUserDetails= event.result as vo.user.LoggedInUserDetails;
if(loggedInUserDetails==null){
loginStatusLbl.text="Invalid UserName or Password";
password.text="";
loggedInUserDetails = new LoggedInUserDetails();
}else{
loggedInUser = loggedInUserDetails.login as LoginMaster;
Application.application.loggedInUserDetails = loggedInUserDetails ;
PopUpManager.removePopUp(this);
Application.application.visible=true;
Application.application.setLoggedInUserDetails();
}
}
/* LoginWindow.mxml InitApplication Function */
private function initLoginWindow():void{
loggedInUserDetails = new LoggedInUserDetails();
loggedInUser = new LoginMaster();
}
private function goToApp():void{
PopUpManager.removePopUp(this);
Application.application.visible = true;
Application.application.welcomeNoteTxt.text = "Using Goo App ";
}
]]>
</mx:Script>
<mx:HBox height=”100%” width=”100%”>
<mx:Canvas height=”100%” width=”100%”>
<mx:FormItem label=”User Name ” height=”24″ x=”10″ y=”48″ fontSize=”12″ fontWeight=”bold”>
</mx:FormItem>
<mx:FormItem label=”Password ” height=”24″ x=”10″ y=”80″ fontSize=”12″ fontWeight=”bold”>
</mx:FormItem>
<mx:Button id=”loginUserLoginBtn” label=”Login” click=”loginUser()”
cornerRadius=”0″ y=”126″ x=”363″ width=”68″ height=”28″ fontSize=”12″ tabIndex=”3″/>
<mx:TextInput id=”password” width=”321″ height=”28″ x=”110″ y=”80″ fontSize=”12″ displayAsPassword=”true” styleName=”CTextInput” tabIndex=”2″ text=”admin”/>
<mx:TextInput id=”userName” width=”321″ height=”24″ x=”110″ y=”48″ fontSize=”12″ styleName=”CTextInput” tabIndex=”1″ text=”admin”/>
<mx:Label id=”loginStatusLbl” height=”30″ x=”10″ y=”10″ width=”418″ fontWeight=”bold” color=”#F71E0E”
fontSize=”12″ fontStyle=”normal” enabled=”true” textDecoration=”normal” textAlign=”center” />
<mx:Button x=”266″ y=”126″ label=”GoTo App” click=”goToApp()”/>
</mx:Canvas>
</mx:HBox>
</mx:TitleWindow>
//First Module
<?xml version=”1.0″ encoding=”utf-8″?>
<mx:Module xmlns:mx=”http://www.adobe.com/2006/mxml” layout=”absolute” width=”400″ height=”300″>
<mx:Label x=”126″ y=”123″ text=”First Module” width=”194″/>
</mx:Module>
// Second Module
<?xml version=”1.0″ encoding=”utf-8″?>
<mx:Module xmlns:mx=”http://www.adobe.com/2006/mxml” layout=”absolute” width=”400″ height=”300″>
<mx:Label x=”129″ y=”127″ text=”Second Module”/>
</mx:Module>
//remoting-config.xml entries
<destination id=”userManagementService” channels=”my-amf”>
<properties>
<source>com.loginlogout.UserMgmService</source>
</properties>
<adapter ref=”java-object” />
</destination>
<destination id=”UserSessionService” channels = “my-amf”>
<properties>
<source>com.loginlogout.FlexSessionUtil</source>
</properties>
<adapter ref=”java-object” />
</destination>
//FlexSessionUtil to manage Flex Server Session for logged in user – will be removed when user log out.
import flex.messaging.FlexContext;
import flex.messaging.FlexSession;
public class FlexSessionUtil {
/**
* Set the given object in the session with an attribute name
*
* @param attributeName
* the string name for the attribute
* @param sessionObject
* Object value for the attribute name.
* @return void
*/
public static void setAttribute(String attributeName, Object sessionObject) {
FlexSession flexSession = FlexContext.getFlexSession();
flexSession.setAttribute(attributeName, sessionObject);
}
/**
* Get the given object in the session with an attribute name
*
* @param attributeName
* the string name for the attribute
* @return Object
*/
public static Object getAttribute(String attributeName) {
FlexSession flexSession = FlexContext.getFlexSession();
return flexSession.getAttribute(attributeName);
}
/**
* Remove the given object in the session with an attribute name
*
* @param attributeName
* the string name for the attribute
* @return void
*/
public static void removeAttribute(String attributeName) {
FlexSession flexSession = FlexContext.getFlexSession();
if (flexSession.getAttribute(attributeName) != null)
flexSession.removeAttribute(attributeName);
}
}
// write your server side code to check user authentication
inside your serverside java file import this class FlexSessionUtil to maintain loggedin user session
import com.spm.utils.FlexSessionUtil;
FlexSessionUtil.setAttribute(login.getId().toString(), login);
How To Create PDF in Flex 3
1. Creating PDF in Flex 3, Here is the Application code
Pre Requeste:# AlivePdf.swc [ include in ur Flex Project By dropping into libs folder ] Download AlivePDF
You can find answer in this post, for the question ” How to create PDF from Flex 3″ or “By Capturing Screen How to create PDF from Flex 3″
<?xml version=”1.0″ encoding=”utf-8″?>
<mx:Application xmlns:mx=”http://www.adobe.com/2006/mxml” layout=”absolute”>
<mx:Script>
<![CDATA[
import org.alivepdf.saving.Download;
import org.alivepdf.saving.Method;
import org.alivepdf.layout.Size;
import org.alivepdf.layout.Unit;
import org.alivepdf.layout.Orientation;
import org.alivepdf.pdf.PDF;
import org.alivepdf.pages.Page;
import org.alivepdf.images.ResizeMode;
import org.alivepdf.images.ImageFormat;
private var myPDF:PDF ;
private function GeneratePDF(event:MouseEvent):void{
myPDF = new PDF(Orientation.PORTRAIT, Unit.MM, Size.A4);
var newPage:Page=new Page(Orientation.PORTRAIT, Unit.MM, Size.A4);
myPDF.addPage(newPage);
myPDF.addImage(testPanel, 5 ,5, testPanel.width,testPanel.height, ImageFormat.PNG, 0, 1, ResizeMode.FIT_TO_PAGE);
myPDF.save(Method.REMOTE, "http://localhost:8080/FlexPDF/servlet/ScreenShotPDFServlet", Download.INLINE, "myPDF.pdf");
// You can modify the code to position the captured image in generated PDF
}
]]>
</mx:Script>
<mx:Panel x=”20″ y=”10″ width=”250″ height=”200″ layout=”absolute” id=”testPanel” title=”testPanel”>
<mx:Button x=”84″ y=”128″ label=”Generate PDF” click=”GeneratePDF(event);”/>
</mx:Panel>
</mx:Application>
****************
2. Here is Java Servlet Code, which generates PDF …
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.ServletInputStream;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class ScreenShotPDFServlet extends HttpServlet {
public ScreenShotPDFServlet() {
super();
}
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doPost(request, response);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
response.setContentType(“application/pdf”);
response.setHeader(“Content-disposition”,”inline; filename=myPDF.pdf” );
int contentLength = request.getContentLength();
byte[] byteArray = new byte[contentLength];
ServletOutputStream sos = response.getOutputStream();
ServletInputStream sis = request.getInputStream();
response.setContentLength(contentLength);
sis.read(byteArray,0,contentLength-1);
sos.write(byteArray);
}
}
3. web.xml entry of the servlet
<servlet>
<servlet-name>ScreenShotPDFServlet</servlet-name>
<servlet-class>com.spm.servlets.ScreenShotPDFServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>ScreenShotPDFServlet</servlet-name>
<url-pattern>/servlet/ScreenShotPDFServlet</url-pattern>
</servlet-mapping>
Note..
1. This servlet generates PDF from flex client with the captured ScreenShot ..
2. GET method called From Flex Client
How to Use Custom Styles to Flex Components
1. Create Style for Your Component ..
Use this URL to simplify the StyleExplorer for Flex Components ..
2. Create a style css file eg. CustomStyle.css
inside your project src .. eg: Project\src\assets\styles\CustomStyle.css
Create Styles for the components, You can do this by Creating Styles from Style Explorer and copy the text [ css style ].. from RIGHT MOST PANEL… Named CSS
Eg. CustomStyle.css
/* CSS file */
.TabNavigator {
tabHeight: 30;
horizontalGap: 1;
borderThickness: 1;
tabStyleName: “myTabs”;
firstTabStyleName: “myTabs”;
lastTabStyleName: “myTabs”;
selectedTabTextStyleName: “mySelectedTabs”;
}
.myTabs {
cornerRadius: 0;
}
.mySelectedTabs {
color: #000066;
}
.disabledBGColor {
disabledColor:#000000;
backgroundDisabledColor:#FFFFFF;
borderColor: #cccccc;
}
2. Include this file in your mxml file
<mx:Style source=”/assets/styles/CustomStyle.css” />
3. Apply the custom style to your component .. by using “styleName” property of the Component
<mx:TabNavigator width=”99%” height=”99%” styleName=”TabNavigator”>
// Your Code Here
</mx:TabNavigator>
Make Your Application More Look …
Loading And Unloading Modules in Flex
Here is sample code to load & unload modules in Flex
import mx.managers.PopUpManager;
import mx.events.MenuEvent;
import mx.controls.Menu;
import mx.controls.Alert;
import mx.events.ModuleEvent;
import mx.modules.ModuleManager;
import mx.modules.Module;
import mx.modules.IModuleInfo;
import mx.core.IUIComponent;
private var moduleToBeLoaded:Module;
private var moduleInfo:IModuleInfo;
private var moduleName:String;
private var module:Module;
private function menuItemHandler(event:MenuEvent):void
{
moduleName=event.item.@modulename;
//Alert.show(“Menu:\t”+event.item.@label +” url:\t”+event.item.@url+” modulename:\t”+event.item.@modulename);
moduleInfo = ModuleManager.getModule(event.item.@url);
moduleInfo.addEventListener(ModuleEvent.READY, renderModule);
moduleInfo.addEventListener(ModuleEvent.ERROR, handleError);
moduleInfo.load();
}
private function renderModule(event:ModuleEvent):void
{
applicationModuleCanvas.removeAllChildren();
if(moduleName == “M1″)
moduleToBeLoaded = moduleInfo.factory.create() as M1; // M1 is mxml file contains <mx:Module> ….</mx:Module>
else if(moduleName == “M2″)
moduleToBeLoaded = moduleInfo.factory.create() as M2;
else if(moduleName == “M3″)
moduleToBeLoaded = moduleInfo.factory.create() as M3;
applicationModuleCanvas.addChild(moduleToBeLoaded);
}
private function handleError(event:ModuleEvent):void
{
Alert.show(event.errorText,”Error”);
}
—————
<mx:ApplicationControlBar id=”AppControlBar” paddingTop=”0″ paddingBottom=”0″ width=”100%” height=”55″
styleName=”MyApplicationControlBar” >
<mx:MenuBar id=”appMenuBar” labelField=”@label” width=”100%” height=”41″ fontWeight=”bold” fontSize=”12″
themeColor=”#E7790D” alpha=”1.0″ itemClick=”menuItemHandler(event)”>
<mx:XMLList>
<menuitem label=”Loading And Unloading Modules” >
<menuitem label=”Module 1″ url=”M1.swf” modulename=”M1″ />
<menuitem label=”Module 2″ url=”M1.swf” modulename=”M2″/>
<menuitem label=”Module 3″ url=”M3.swf” modulename=”M3″/>
</menuitem>
</mx:XMLList>
</mx:MenuBar>
</mx:ApplicationControlBar>
<mx:Canvas id=”applicationModuleCanvas” width=”100%” height=”95%” cornerRadius=”0″ backgroundColor=”#FDFDFD” borderStyle=”inset”>
</mx:Canvas>
Liferay Portlet development
Just refer this url .. u will get some txt files to develope portlets …
http://liferay1.googlecode.com/svn/trunk/snippet/portal-devt/
JDK 7 Features
This is the list of features being developed by Sun, and others, for JDK 7.
When the Java SE 7 Platform JSR is submitted then these features will be proposed therein, except for those listed as either VM-level or implementation-specific.
Per the current draft of the development process we will shortly publish a Feature Proposal template. That will be the vehicle for proposing additional features for inclusion in the release. Smaller, non-feature changes will go through a lighter-weight process, soon to be defined.
Comments to: jdk7-dev at openjdk.java.net
Summary
Features are listed in order, more or less, from lowest to highest in the overall JDK software stack.
Liferay FusionCharts Integration
How to do ” Liferay FusionCharts Integration”
Its easy simple …
Problem:exists:
You might given the syntax to include flash chart swf, xml [say for eg ]
I pasted Only Snippets in the html/jsp file used to include fusion charts ……
1.
<script language=”JavaScript” src=”js/FusionCharts.js”></script>
<link rel=’stylesheet’ href=”Contents/Style.css” />
2. <script type=”text/javascript”>
var myChart = new FusionCharts(“Charts/StackedColumn3D.swf”, “chart1″, “580″, “300″, “0″, “0″);
myChart.setDataURL(“Data/Summary/Revenue2005.xml”);
myChart.render(“chart1″);
</script>
the problem
In portlet the location of swf, xml file cannot be known ..
Solution is to let portlet identify the location of swf/ xml file to display charts
Solution
1. Get the location of the portlet by
String pathPrefix=renderRequest.getContextPath(); //in jsp
1.<script language=”JavaScript” src=’<%=pathPrefix%>/js/FusionCharts.js’></script>
<link rel=’stylesheet’ href=’<%=pathPrefix%>/Contents/Style.css’ />
2. <script type=”text/javascript”>
var myChart = new FusionCharts(“<%=pathPrefix%> /Charts/StackedColumn3D.swf?registerWithJS=1″, “chart1″, “580″, “300″, “0″, “0″);
myChart.setDataURL(“<%=pathPrefix%>Data/Summary/Revenue2005.xml”);
myChart.render(“chart1″);
</script>
FOLLOW THE SAME WHERE EVER NEEDED …….
ENJOY ..
Liferay Portlet Developement
Liferay Portlet Developement
1. http://www.liferay.com/web/guest/community/wiki/-/wiki/Main/Development%20in%20the%20ext%20environment
2. http://www.liferay.com/web/guest/community/wiki/-/wiki/Main/Services,%20entities,%20and%20ServiceBuilder
3. http://www.liferay.com/web/guest/community/wiki/-/wiki/Main/Understanding%20ServiceBuilder%20and%20JavaScript%20for%20Liferay
Sun Identity Management
Sun Identity Management Suite
- Identity Management
- Access Control
- Single Sign On
For More Ifor refer ..
http://www.sun.com/software/identity/
http://www.sun.com/software/identity/for_development.jsp
http://www.sun.com/software/media/flash/demo_identity/netid.html?intcmp=27
http://link.brightcove.com/services/player/bcpid1640183659?&bctid=20284110001
http://wikis.sun.com/display/OpenSSO/Home
http://webcast-west.sun.com/interactive/08A01140/08A01140_06/index.html
http://webcast-west.sun.com/interactive/09B01894_01/index.html
Open-source Web applications, PHP vs. Java
Part 1:
It is common knowledge that PHP does well in the open-source Web applications space. PHP has numerous representatives for most application categories, and for some it provides a clear leader, like WordPress. On the other hand, most Java counterparts have apparently failed to reach the same popularity.
Below is an overview of the existing open-source PHP and Java implementations for the following categories of applications: forum, blog, wiki and content management systems (CMS). These are among the most commonly used types of on-line software.
Forum Engines
There are lots of PHP forum engines in the open-source software arena, including:
- phpBB which has 700+ mods and is the winner of the SourceForge.net 2007 Community Choice Awards for the Best Project for Communications category,
- vBulletin with 1000+ mods,
- punBB having 300+ projects and 150+ styles.
Notice the large amount of plugins for each of these projects. This denotes a large and healthy user base, devoted to both using and extending the core application.
Java has the JForum and JavaBB projects, but they seem to have very few users by comparison, not to mention plugin contributors.
Blog Engines
In the area of blogging, the PHP based WordPress is extremely well spread. Chances are that virtually any blog you read is powered by WordPress. The project has 2000+ plugins and at least 5 dedicated printed books. No other PHP blog engine comes close to the popularity of WordPress.
For Java, there are two relevant open-source blog applications: Apache Roller and Pebble. Roller is more feature-rich, but that comes at a considerable price: large footprint and difficult configuration. It is an enterprise application focused on very large blogging sites (e.g. the Sun blogs), but it seemingly fails to satisfy small-scale needs. I have yet to find a plugin developer community around it.
Pebble on the other hand is focused on the other end of the spectrum, providing a much simpler configuration and lower footprint. But I still couldn’t find plugins.
Wiki Engines
In this category, PHP seems to have an overwhelming advantage. The MediaWiki project powers Wikipedia, the largest wiki by far. The project has lots of available extensions, of which 300+ are stable. There are lots of other PHP wiki engines one can choose from, but I just wanted to point out the most prominent one.
Java does not have too many production-ready wiki projects. In my opinion, JspWiki (with 50+ plugins) and XWiki are the most relevant. I wanted to mention SnipSnap as well, however it’s development is officially stopped.
Content Management Systems
Content management systems are a handy way of building dynamic sites instead of starting from scratch. PHP seems to provide everything one needs, including a healthy competition among its foremost projects. These are Joomla (2900+ extensions, 14+ books published) and Drupal (3600+ modules, 9+ books). There are also other CMS projects e.g. Mambo and the ancient PHP-Nuke.
Because in most cases CMSs are deployed on a dedicated server, Java should not be at a disadvantage in this category. There are several open-source Java CMSs to choose from: Apache Jackrabbit, Apache Lenya, Alfresco, Liferay, OpenCms, Nuxeo, Magnolia, Jahia etc. Among these, Alfresco (2 printed books and 20+ stable extensions) and Liferay (portlets based, 1 printed book, 25+ portlet plugins) seem the more popular.
A special note for the Java Content Repository API defined by JSR-170. Both Jackrabbit and Magnolia implement it. This means that third-party tools can access their repositories in a standardized way. It is a very good step towards ensuring that information stored inside a JCR compliant repository can outlive a particular JCR implementation.
For now, the JCR API does not seem enough however. The PHP CMS projects are continuously gaining ground, probably because PHP hosting is cheap and easy to set up, and because the projects themselves are highly usable. Take into account that DZone and implicitly JavaZone (the former JavaLobby) are running on Drupal. And I’m sure that Rick and Matt tried to choose the best option while not easily dismissing the Java CMSs.
In the second part of this post, I will try to explore the reasons for the current state and to figure out a way to change it. Meanwhile feel free to add your input to the above, the list of projects is far from exhaustive.
Part 2:
The first part of this article reviewed some relevant open-source Web applications in both the PHP and Java worlds. The conclusion was that there are massively popular PHP projects and somewhat popular if not obscure Java counterparts. I’m a Java fan and it pains me to discover this reality. The user comments also underlined this feeling.
Is it the technical merits of PHP?
In my experience, the technical merits of PHP are below those of Java as a language and as a runtime environment (standard API, virtual machine).
Compared to Java, the code quality of PHP projects has a faster decreasing rate as the codebase size grows. The root cause is that PHP was created to solve small size problems and this makes it difficult to manage larger projects.
PHP 3 and 4 had basic object-oriented features, while PHP 5 improved them considerably, both at the language and the runtime level. There are several PHP MVC frameworks to ease the structuring of larger projects, but these are most effective when running on PHP 5. Most popular open-source PHP projects still run on PHP 4 and tend not to use MVC frameworks at all.
Looking at the staggering number of plugins available for the popular PHP open-source projects, one could conclude that their code is easily understandable and that PHP has well-rounded application extension mechanisms. Well, not exactly true.
The typical PHP extension mechanism is procedural and works like this:
- list the subdirectories of the extensions directory,
- analyze the predefined directory structure for each extension,
- execute some predefined PHP files that should auto-register their resources and actions.
The greatest concern? no protection of the core code. All the important internal structures of the PHP runtime are map-like data structures to which the PHP code has full access: the global variables map, the functions map, the classes map etc.
As a long-time Java developer, I see these as drawbacks. But they don’t seem to reflect as such on these popular projects with very large user and developer communities. But if it’s not the language, what is it?
The execution models
Compared to Java, developing and hosting PHP projects is dead-simple because of the execution model.
In a typical setup, each request to a PHP application is handled by a separate Apache process that uses its own instance of the PHP interpreter. After handling the request, the process is killed with no garbage left behind. This sounds inefficient for high-concurrency usage, but works great in a shared hosting environment. If a hosted application has no active requests, it doesn’t use memory at all. Development-wise, each PHP script is written like every script instance (process) is the only one running.
The Java Web application model uses servlets and multiple threads to handle requests. It scales upwards very well, hence its success in the enterprise space. Problems arise if you want to host many smaller and less frequently used applications inside the same Web container, precisely because of the threads. Developers have to be careful about concurrency issues.
The process control mechanisms available at the OS level are vastly superior than those available for Java threads. The result is that a hosting provider has strict control over the resources used by each PHP request. On the other hand, a Java thread backing a request is an object that you cannot control once started: it stops when it wants to, it uses as much system resources as it pleases. The Web containers only have mechanisms for controlling the pool of threads.
The end result is that there are technical limitations in setting up a competitively priced reliable Java hosting solution. This brings us to two fundamental questions: do we need successful open-source Java Web projects suitable for non-enterprise use? Can Java survive without such projects?
Java can probably survive, but survival and flourishing are two different things. If the average present-day college student or hobbyist finds pleasure in using and extending open-source PHP (and generally non-Java) Web applications, I believe that it is only a matter of time until the effects are felt in the enterprise space: less enthusiastic Java specialists, less innovation, decreasing quality of products and so on. Some say that the effects are already present ? what do you think?
Instead, wouldn’t you like to run your blog on a Java-based highly extensible engine? Wouldn’t you like to build complex sites using a Java-based CMS with many high quality, readily available, easy to develop modules? Something that can be as small or as large as you want. I would.
Building successful open-source Java Web applications – your input is needed
In my opinion, there are three important premises for an open-source Web project to succeed:
- the intrinsic value of the project,
- the enthusiasm of its community (both developers and users),
- easy hosting.
If Java presence is to increase in the area of open-source Web applications, all three are needed. The first two items are crucial because valuable projects and enthusiastic communities can even help improve the existing entry-level hosting options.
The fastest way to obtain Java projects with the same functionality as PHP ones is by automated software translation. The company I co-founded has developed technology that allows translating PHP applications to Java. I have already talked about this while presenting the nBB2 project, the Java equivalent of phpBB 2. The migration algorithms can be customized to produce various output flavors, ranging from plain servlets and JSP pages to Web frameworks like Struts or Spring MVC.
We would like to translate more open-source PHP projects to Java, but this would be just a first step. The Java community would then have to step in by using and extending them.
In the comments following the first part of this article it has been suggested that Sun act and sponsor key open-source Java Web projects. I my opinion, Sun already provides the Java platform and an open-source stack to support such endeavors. It is up to the Java community to make proper use of the technologies at hand. I look forward to hearing your thoughts on this topic, both online and in person. Next week I’ll be at JavaOne, so if you are around feel free to pass by the Numiton booth 1224-8 in the startup row.
Courtesy:
http://www.numiton.com
JSP Video Tutorial – 1
Servlets Video Tutorials – 2
Java Servlets Video Tutorials
OpenXava Demo
QAManager – developed using OpenXava , can be deployed in liferay portal …
It guve us ease of development in terms of ports & views for user roles…
please visit this url ….
qamanager
OpenXava Sample Demo
OpenXava
A RAD [ rapid application development ] tool – for both – web & portal applications in the form of deployable war files
www.openxava.org
Liferay Creating your first Liferay Portlet