开发liferay的小例子

    技术2025-05-28  16

     

     

    一、实例

    这里我们采用portal里面代码规范生成机制。对于持久化层和服务层的类都可以自动产生。

    我们的portlet功能很简单就是从数据库里面一个表中获取数据,并在页面上显示。

    建立业务数据表

    在数据库里面新建一个表users,字段userid(varcher),username(varcher),password(varcher).并往表中插入几个条数据。

    建立代码模板配置文件

    (1)建立service.xml文件

    在ext/ext-impl/src/com/ext/portlet 新建一个目录users,在目录下建立一个service.xml文件

    文件内容为:

    <?xml version="1.0"?>

    <!DOCTYPE service-builder PUBLIC "-//Liferay//DTD Service Builder 5.1.0//EN" "http://www.liferay.com/dtd/liferay-service-

    builder_5_1_0.dtd">

    <service-builder package-path="com.ext.portlet.users">

    <namespace>Users</namespace>

    <entity name="UsersEntry" local-service="false" remote-service="true" persistence-

    class="com.ext.portlet.users.service.persistence.UsersEntryPersistenceImpl">

    <!-- PK fields -->

    <column name="userid" type="String" primary="true" />

    <!-- Audit fields -->

    <column name="username" type="String" />

    <column name="password" type="String" />

    <!-- Order -->

    <order by="asc">

    <order-column name="username" case-sensitive="false" />

    </order>

    </entity>

    <exceptions>

    <exception>UsersEntry</exception>

    </exceptions>

    </service-builder>

    <!--package-path是指我们即将建立portlet的上级目录-->

    <!-- portlet name就是我们新建文件夹名称users,short-name没有作研究不太清楚使用途径-->

    <!--entity name 是和我们即将建立的和数据库表a_user一一对应实体的类名,可以和数据库表名不同, 

    <!--但为方便起见一般和表名保持一致-->

    (2)修改ant文件,增加ant任务

    建好service.xml文件后,我们在ext-impl目录下打开build-perent.xml 在

    <target name="build-service">

    ……. 

    </target>

    下面添加任务

    <target name="build-service-portlet-users">

    <antcall target="build-service">

    <param name="service.file" value="src/com/ext/portlet/users/service.xml" />

    </antcall>

    </target>

     

     

     

     

    然后在myexlipse的ant视图里面打开ext-impl目录下的build.xml执行build-service-portlet-user任务。

    我们发现在ext-impl/src/com/ext/portlet/users , ext-service/src/com/ext/portlet/users

    下面多了几个目录和文件。这是都是系统自动产生的hibernate的实体类和持久化类。

    如果我们再细心些也可发现在ext-impl/src/META-INF目录下配置文件都多些内容。

    系统已经自动将对应的实体类、持久化类、工具类等配置为相应的javabean、util、service等。

    无疑节省了很多时间,而且减少我们人工配置的错误。

    打开ext-impl/src/META-INF/ext-hbm.xml,把<class name="com.ext.portlet.users.model.impl.UsersEntryImpl"table="UsersEntry">改为<class name="com.ext.portlet.users.model.impl.UsersEntryImpl" table="Users">

    业务实现编码

    现在我们要实现一个查询功能,将数据库中表名users中所有记录的username查询出来,并显示在前台。

    打开/ext-service/src/com/ext/portlet/users/service下UsersEntryService文件,建立一个名为getAllUsers的抽象方法;

    public List getAllUsers() throws SystemException;

    在/ext-impl/src/com/ext/portlet/users/service/impl/UsersEntryServiceImpl.java中实现它.

    public List getAllUsers() throws SystemException {

    return UsersEntryUtil.findAll();

    }

    同样spring的service层 也是通过辅助类作为对外唯一入口,所以在UsersEntryServiceUtil里面增加一

    个方法getAllUsers作为service层的方法getAllUsers的入口。

    public static List getAllUsers() throws SystemException{

    return _service.getAllUsers();

    }

    需要注意的是service层接口对应具体实现是由工厂类指定。他们捆绑关系可以查看spring配置文件信息。

    在执行ant 的build-service-portlet-usertest任务已经完成了。

    在/src/com/ext/portlet/users/action目录下建立一个ViewUserAction.java文件,完成响应客户端请求。

    package com.ext.portlet.users.action;

    import com.ext.portlet.users.model.UsersEntryModel;

    import com.ext.portlet.users.service.UsersEntryServiceUtil;

    import com.liferay.portal.struts.PortletAction;

    import java.util.ArrayList;

    import java.util.List;

    import javax.portlet.PortletConfig;

    import javax.portlet.RenderRequest;

    import javax.portlet.RenderResponse;

    import javax.portlet.WindowState;

    import org.apache.struts.action.ActionForm;

    import org.apache.struts.action.ActionForward;

    import org.apache.struts.action.ActionMapping;

    public class ViewUsersAction extends PortletAction {

    public ActionForward render(ActionMapping mapping, ActionForm form, PortletConfig config, RenderRequest req, RenderResponse res)throws Exception {

    if (req.getWindowState().equals(WindowState.NORMAL)) {

    return mapping.findForward("portlet.ext.users.view");

    } else {

    List users = UsersEntryServiceUtil.getAllUsers();

    List usernames = new ArrayList();

    for (int i = 0; i < users.size(); i++) {

    usernames.add(((UsersEntryModel) users.get(i)).getUsername());

    }

    req.setAttribute("users", usernames);

    req.setAttribute("count", ""+users.size());

    return mapping.findForward("portlet.ext.users.view_users");

    }

    }

    }

     

    里面大概功能是如果porlet的窗口状态时普通,则定向到一个叫portlet.ext.myuser.view的目标上。

    如果窗口状态是最大化,那么就从调用userLocalServiceUtil,从数据库里面获取所有人员信息。

    Portlet的生成

    建立自己的portlet。在/ext-impl/src/com/ext/portlet/users下面新建文件UsersPortlet.java

    package com.ext.portlet.users;

    import com.liferay.portlet.StrutsPortlet;

    import java.io.IOException;

    import javax.portlet.PortletException;

    import javax.portlet.PortletPreferences;

    import javax.portlet.RenderRequest;

    import javax.portlet.RenderResponse;

    public class UsersPortlet extends StrutsPortlet {

    public void doView( RenderRequest renderRequest, RenderResponse renderResponse)throws IOException, PortletException {

    PortletPreferences prefs = renderRequest.getPreferences();

    System.out.println(prefs.getValue("test", ""));

    super.doView(renderRequest, renderResponse);

    }

    }

    该portlet重载了doview方法。如果自己portlet对view和edit有自己特性,那么只要重载doview和doedit就可以了。

    现在portlet的内容是空的,我们用jsp页面来展示用户名称方式来填充portlet里面内容。

    在 /ext-web/docroot/html/portlet/ext目录下建立目录users,并在users目录下建立init.jsp文件

     

    init.jsp代码

    <%@ include file="/html/common/init.jsp" %>

    <portlet:defineObjects />

    <% PortletPreferences prefs = renderRequest.getPreferences(); %>

     

    建立view.jsp文件:

    <%@ include file="/html/portlet/ext/users/init.jsp" %>

    <a href="<portlet:renderURL windowState="<%= WindowState.MAXIMIZED.toString() %>" />">

    MyUser 

    <%= prefs.getValue("user", "") %>

    </a>

    该jsp内容是显示默认的初始用户名。具体值从初始化配置参数里获取。

    建立view_users.jsp

    <%@ include file="/html/portlet/ext/users/init.jsp" %>

    <% List reports = (List)request.getAttribute("users");%>

    <% String count = (String)request.getAttribute("count");%>

    size : <%=count %>.<br/>

    <% 

    for (int i = 0; i < reports.size(); i++) {

    String reportName = (String)reports.get(i);

    %>

    <%= reportName %><br>

    <% 

    }

    %>

     

     

    该jsp页面目的是展示所有从数据库里面取出来的用户名。

    Ok,完成以上工作后,我们整个portlet编码工作已经宣告结束,接下来的是配置portlet参数工作。

    Portlet的配置:

    是portlet配置信息文件存放/ext-web/docroot/WEB-INF目录下,在portlet-ext.xml文件里面添加

    <portlet>

    <portlet-name>EXT_Users</portlet-name>

    <display-name>Users</display-name>

    <portlet-class>com.ext.portlet.users.UsersPortlet</portlet-class>

    <init-param>

    <name>view-action</name>

    <value>/ext/users/view_users</value>

    </init-param>

    <expiration-cache>0</expiration-cache>

    <supports>

    <mime-type>text/html</mime-type>

    </supports>

    <resource-bundle>com.liferay.portlet.StrutsResourceBundle</resource-bundle>

    <portlet-preferences>

    <preference>

    <name>test</name>

    <value></value>

    </preference>

    </portlet-preferences>

    <security-role-ref>

    <role-name>power-user</role-name>

    </security-role-ref>

    <security-role-ref>

    <role-name>user</role-name>

    </security-role-ref>

    </portlet>

    <portlet-name>必须唯一,不得已有portlet名字冲突。<display-name>也必须唯一。

    <portlet-class>指向我们的建立portlet类。

    <name>view-action</name>里面值是指view这个action对应的actionurl。

    <portlet-preferences>

    里面参数值是提供给这个portlet使用的参数初始值。这里配置是指portlet里面使用到参数名user的值是jack。

    如portlet不需要初始值参数,则该项不需要配置。

    在liferay-portlet-ext.xml文件里面添加

    <portlet>

    <portlet-name>EXT_Users</portlet-name>

    <struts-path>ext/users</struts-path>

    <use-default-template>false</use-default-template>

    </portlet>

    <portlet-name>的值必须和portlet-ext.xml文件里面<portlet-name>值一致。

    在liferay-display。Xml文件节点<category name="category.test">

    下面添加

    <portlet id="EXT_Users" /> id必须和portlet-ext里面的<portlet-name>一致。

     

    在struts-config.xml文件里面添加内容:

    <action path="/ext/users/view_users" type="com.ext.portlet.users.action.ViewUsersAction">

    <forward name="portlet.ext.users.view" path="portlet.ext.users.view" />

    <forward name="portlet.ext.users.view_users" path="portlet.ext.users.view_users" />

    </action>

    就是说,当前台提交一个actionUrl为/ext/users/view_users请求的时候,由ViewUsersAction负责处理这个

    action操作。后面2个forward指的是在ViewUsersAction定向返回请求目标页面。

    …………

    return mapping.findForward("portlet.ext.users.view");

    ………

    return mapping.findForward("portlet.ext.users.view_users");

    findForward的值为避免与其他findForward值冲突,一般将包名也带上,保证不会重名。

    在tiles-defs.xml文件里面添加内容:

    <definition name="portlet.ext.users.view" extends="portlet">

    <put name="portlet_content" value="/portlet/ext/users/view.jsp" />

    </definition>

     

     

    <definition name="portlet.ext.users.view_users"

    extends="portlet">

    <put name="portlet_content"

    value="/portlet/ext/users/view_users.jsp" />

    </definition>

    该name的值即随同struct-config.xml配置信息里面forward参数path值对应的,指向真正的目标页面。

    最后我们在/ext-impl/src/content目录下Language-ext.properties文件里面增加内容:

    javax.portlet.title.EXT_Users=Users 

    view-users=View Users

    即portlet显示出来时候,在portlet上面标题信息。

    我所遇到的问题以及解决方式:

    1、报 字段 出错, password_ 应该在数据库中是 password

    修改配置文件ext-impl/src ? META-INF ? ext-hbm.xml

    Model不知道要不要改,我也改了一下。

     

    最新回复(0)