GAE-简单的留言板(Simple Guestbook)

这个例子其实就是Google官方给出来的例子~你可以在文档中看到,我在原例子的基础上添加了修改与删除功能~(没判断权限~谁都可以删除~要判断也很简单…判断一下登陆的email)

我就不说那么详细了·官方例子说的已经很清楚了,需要源码在这里下载:http://115.com/file/bhqlcqtq

这个例子显示效果在此:http://1.latest.fatkuns.appspot.com/

这个例子涉及了

  1. 如何使用用户服务(也就是使用google账号登陆~我有点担心的是别人伪造一个假的登录页面怎么办?放心,我做的那个是真的…- -!)
  2. 如何存储数据(使用JDO)
  3. JSP
  4. Servlet

好~开始了~那些准备工作就不说了,创建项目,包名这些~

一、要保存留言,我们需要创建一个这样的文件~Greeting.java

package com.fatkun.guestbook;
 
import java.util.Date;
 
import javax.jdo.annotations.IdGeneratorStrategy;
import javax.jdo.annotations.IdentityType;
import javax.jdo.annotations.PersistenceCapable;
import javax.jdo.annotations.Persistent;
import javax.jdo.annotations.PrimaryKey;
 
import com.google.appengine.api.users.User;
 
@PersistenceCapable(identityType = IdentityType.APPLICATION)
public class Greeting {
	//主键的设置,自增的方式
	@PrimaryKey
	@Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
	private Long id;
	//其他的值设置一个@Persistent在前面就会保存到数据库里了
	@Persistent
	private User author;
	@Persistent
	private String content;
	@Persistent
	private Date date;
 
	//下面是一些Getter,Setter方法,对于JDO是不需要的,只是为了方便你写程序
	public Greeting(User author, String content, Date date) {
		super();
		this.author = author;
		this.content = content;
		this.date = date;
	}
 
	public Long getId() {
		return id;
	}
 
	public void setId(Long id) {
		this.id = id;
	}
 
	public User getAuthor() {
		return author;
	}
 
	public void setAuthor(User author) {
		this.author = author;
	}
 
	public String getContent() {
		return content;
	}
 
	public void setContent(String content) {
		this.content = content;
	}
 
	public Date getDate() {
		return date;
	}
 
	public void setDate(Date date) {
		this.date = date;
	}
 
}

二、我们还要创建PMF.java用来取得PersistenceManager。官方说取这个东西要花费很多资源,所以只获得一个就好,单例模式~

package com.fatkun.guestbook;
 
import javax.jdo.JDOHelper;
import javax.jdo.PersistenceManagerFactory;
 
/**
 * 用来取得PersistenceManager
 * @author Administrator
 *
 */
public final class PMF {
	private static final PersistenceManagerFactory pmfInstance = JDOHelper.getPersistenceManagerFactory("transactions-optional");
 
	private PMF() {
	}
 
	public static PersistenceManagerFactory get() {
		return pmfInstance;
	}
}

三、我们在war目录下新建一个guestbook.jsp用来显示所有留言

<?xml version="1.0" encoding="UTF-8" ?>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ page import="java.util.List"%>
<%@ page import="javax.jdo.PersistenceManager"%>
<%@ page import="com.google.appengine.api.users.User"%>
<%@ page import="com.google.appengine.api.users.UserService"%>
<%@ page import="com.google.appengine.api.users.UserServiceFactory"%>
<%@ page import="com.fatkun.guestbook.Greeting"%>
<%@ page import="com.fatkun.guestbook.PMF"%>
 
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>Google App Engine留言板 - fatkun.com</title>
</head>
<body>
<%
	UserService userService = UserServiceFactory.getUserService();
	User user = userService.getCurrentUser();
	if (user != null) {
%>
<p>你好, <%=user.getNickname()%>! (<a href="<%=userService.createLogoutURL(request.getRequestURI())%>">退出</a>.)</p>
<%
	} else {
%>
<p>你好! 你可以使用google账号<a href="<%=userService.createLoginURL(request.getRequestURI())%>">登陆</a></p>
<%
	}
%>
 
<%
	PersistenceManager pm = PMF.get().getPersistenceManager();
	//String query = "select from " + Greeting.class.getName()+" order by id desc";
	//也可以写成下面的形式
	String query = "select from com.fatkun.guestbook.Greeting order by id desc";
	List<Greeting> greetings = (List<Greeting>) pm.newQuery(query).execute();
	if (greetings.isEmpty()) {
%>
<p>还没有留言。</p>
<%
	} else {
		for (Greeting g : greetings) {
			if (g.getAuthor() == null) {
				out.print("<p>一位匿名人士说:</p>");
			} else {
				out.print("<p><b>"+g.getAuthor().getNickname()+"</b> 说:</p>");
			}
%>
<a href="del?id=<%=g.getId()%>">删除</a> - <a href="guestbook-modify.jsp?id=<%=g.getId()%>">修改</a>
<blockquote><%=g.getContent()%></blockquote>
<%
	}
	}
	pm.close();
%>
 
<form action="/add" method="post">
<div><textarea name="content" rows="3" cols="60"></textarea></div>
<div><input type="submit" value="我要留言" /></div>
</form>
 
</body>
</html>

这里注意要引入自己使用的包~~GQL是针对对象来写查询语句的~~有点儿像Hibernate的HQL~

四、没有内容怎么显示呢~我们加一个添加到数据库的GuestbookAddServlet.java

package com.fatkun.guestbook;
 
import java.io.IOException;
import java.util.Date;
 
import javax.jdo.PersistenceManager;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
 
import com.google.appengine.api.users.User;
import com.google.appengine.api.users.UserService;
import com.google.appengine.api.users.UserServiceFactory;
 
@SuppressWarnings("serial")
public class GuestbookAddServlet extends HttpServlet {
 
	@Override
	protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		//取得用户Service,这里是Google的用户管理
		UserService userService = UserServiceFactory.getUserService();
		//取得当前登录的用户,当不存在的时候为null
		User user = userService.getCurrentUser();
 
		String content = req.getParameter("content");
		Date date = new Date();
		//创建一个Greeting对象
		Greeting greeting = new Greeting(user, content, date);
 
		PersistenceManager pm = PMF.get().getPersistenceManager();
		try {
			//持久化~也就是把greeting添加进数据库
			pm.makePersistent(greeting);
		} finally {
			pm.close();
		}
		resp.sendRedirect("guestbook.jsp");
	}
 
}

写完了上面这个文件,注意还得在web.xml加入下面的,要告诉服务器说,我在这里啊,你可以通过这个链接找我~~

	<servlet>
		<servlet-name>add</servlet-name>
		<servlet-class>com.fatkun.guestbook.GuestbookAddServlet</servlet-class>
	</servlet>
	<servlet-mapping>
		<servlet-name>add</servlet-name>
		<url-pattern>/add</url-pattern>
	</servlet-mapping>

这时,你应该就可以留言啦~~运行一下试试~~可以先在本地测试,再上传到GAE服务器上。

伍、我最后给出修改和删除的部分代码~其实就主要是数据库的问题~~

GuestbookModifyServlet.java

	protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		Long id = Long.parseLong(req.getParameter("id"));
		String content = req.getParameter("content");
 
		//先获取PersistenceManager
		PersistenceManager pm = PMF.get().getPersistenceManager();
		try {
			//根据ID从数据库得到一条记录
			Greeting greeting = pm.getObjectById(Greeting.class, id);
			//修改记录
			greeting.setContent(content);
		} finally {
			//当关闭pm的时候,会自动把已经修改的记录更新到数据库
			pm.close();
		}
		resp.sendRedirect("guestbook.jsp");
	}

GuestbookDeleteServlet.java

	protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		Long id = Long.parseLong(req.getParameter("id"));
 
		PersistenceManager pm = PMF.get().getPersistenceManager();
		try {
			//取得这条记录
			Greeting greeting = pm.getObjectById(Greeting.class, id);
			//删除
			pm.deletePersistent(greeting);
		} finally {
			//关闭
			pm.close();
		}
		resp.sendRedirect("guestbook.jsp");
	}

好,一个简单的留言板就这样诞生了~~如果想弄得更加漂亮,就自己弄吧~~^_^
我做的例子:http://1.latest.fatkuns.appspot.com/




fatkun

76条评论

Merry Christmas ~ O(∩_∩)O ~

      *       ,
            _/^\_
           
   *         /.-.\     *
       *    `/&\`          *
           ,@.*;@,
           /_o.I %_\  *
    *      (`’–:o(_@;
          /`;–.,__ `’)       *
         ;@`o % O,*`’`&\
      *  (`’–)_@ ;o %’()\   *
         /`;–._`”–._O’@;
        /&*,()~o`;-.,_ `””`)
   *     /`,@ ;+& () o*`;-’;\
        (`””–.,_0o*`;-’ &()\
        /-.,_  “”–….-’`) *
     *  /@%;o`:;’–,.__  __.’\
       ;*,&(); @ % &^;~`”`o;@();     *
       /()dev & ().oFriendsO\
       `”=”==””==,,,.,=”==”===”`
      __.—-.(\-”#####—…___…—–._
     ‘`     \)_`”””””`
            .–’ ‘)
           o( )_-\
            `”””` `

我正在学习GAE,能不能把你这个留言板的源代码发给我学习一下,我的邮箱是honghere@163.com

@hong,已经发到了你的邮箱。 我把war\WEB-INF\lib删了,你用IDE建一个GAE空白项目,把生成的lib目录下的所有jar复制过来就可以了。

能否将源代码发给我一份,我实现修改时出现了问题,想参考一下

你好,能否将源码发给我一份??
——
我知道你邮箱了,帮你去掉先,晚上再给你发。。

能不能把源代码发给我一份,我现在在学这个,遇到了一些问题

你好,能否也给我一份源码?
我按照官网上配的jdoconfig.xml
但是老是报错
谢谢了

收到源码了
但是IDEA9老是报错
警告: /
javax.jdo.JDOUserException: Persistent class “Class guestbook.Greeting does not seem to have been enhanced. You may want to rerun the enhancer and check for errors in the output.” has no table in the database, but the operation requires it. Please check the specification of the MetaData for this class.
不知道咋解决,明天再弄到eclipse上试试

[url=http://www.qgxqm.com/QQ-qinglvqianming/]qq情侣个性签名一对[/url]

[url=http://www.qgxqm.com/QQ-gaoxiaoqianming/]qq搞笑个性签名[/url]

我发了错误提示信息而已。你能把你的代码发给我参考下不。我在增强数据类的时候一直报错。

您好,您说的
add
com.whl.guestbook.GuestbookAddServlet

add
/add

是加在war/web-inf下的web.xml里面吗?我加进去了,可是然后运行Web Application会有警告如下:
2011-1-18 14:07:32 com.google.apphosting.utils.jetty.JettyLogger info
信息: Logging to JettyLogger(null) via com.google.apphosting.utils.jetty.JettyLogger
2011-1-18 14:07:32 com.google.apphosting.utils.config.AppEngineWebXmlReader readAppEngineWebXml
信息: Successfully processed G:\workspace\Guestbook\war\WEB-INF/appengine-web.xml
2011-1-18 14:07:32 com.google.apphosting.utils.jetty.JettyLogger warn
警告: FATAL@null line:20 col:6 : org.xml.sax.SAXParseException: The markup in the document following the root element must be well-formed.
2011-1-18 14:07:32 com.google.apphosting.utils.config.AbstractConfigXmlReader getTopLevelNode
严重: Received SAXException parsing the input stream for G:\workspace\Guestbook\war\WEB-INF/web.xml
org.xml.sax.SAXParseException: The markup in the document following the root element must be well-formed.
….省略
… 12 more

为什么啊?急求?谢谢

上面那个我说的加入的xml中的是您说的

add
com.fatkun.guestbook.GuestbookAddServlet

add
/add

好像格式有问题,就是servlet中的add的部分,那个添加到xml中后有警告啊。。。

可是我在删除留言的时候有这个错误:
HTTP ERROR 404
Problem accessing /del. Reason:

NOT_FOUND

当时的url为:http://localhost:8888/del?id=4
这是为什么啊?谢谢fatkun了~~~

我也有一樣的問提 就是新增及修改那邊有錯誤,可否給我代碼,
另外用帳號來判斷權限的部分如何做? 可否講解一下

代码晚上发给你。。但愿我还记得= =!不记得再提醒我一次。。

与此同时eclipse控制台提示的警告是:
2011-1-18 23:24:42 com.google.appengine.tools.development.LocalResourceFileServlet doGet
WARNING: No file found for: /del

为什么启动Web Application时eclipse会给出这样的警告呢:而且
严重: javax.servlet.ServletContext log: unavailable
javax.servlet.UnavailableException: Servlet class com.fatkun.guestbook.GuestbookModifyServlet is not a javax.servlet.Servlet
at org.mortbay.jetty.servlet.ServletHolder.checkServletType(ServletHolder.java:362)
at org.mortbay.jetty.servlet.ServletHolder.doStart(ServletHolder.java:243)

您太强了!我都弄了好几天了,效果依然没出来,崩溃的边缘!请您把源码借我欣赏一下吧!如果您愿意的话,把QQ也告诉我吧!非常非常感谢!

兄弟,发一份哦,351558205qq.com

正在研究GAE,这个好东东!感谢分享!
能发我一份代码吗?多谢啊!!

You really make it seem so easy with your presentation however I in finding
this topic to be really one thing which I think I’d never understand.

It seems too complicated and extremely wide for me.

I’m taking a look ahead to your next put up, I’ll try to get the dangle of it!

Later according to group, supplements and sleeves populating not lengthen forth the penis. After all, he said, the penis burce.pakken.se consists of paired corpora cavernosa and a self-governing corpus spongiosum, the hugeness of which are constant genetically. Undeviating surgical enhancement fails. In all events, there is anybody away with ambition burce.pakken.se dangled already our eyes alongside the entirely through-and-through unruffled so Italian study. When tested, the direct method of penis enhancement, the authors aver, did conclude in growth.

Later according to principles, supplements and sleeves determination not enhance the penis. After all, he said, the penis freewfo.smukbrudgom.com consists of paired corpora cavernosa and a nail on corpus spongiosum, the scope of which are uncompromising genetically. Neck surgical enhancement fails. Manner, there is unified minute daydream freewfo.smukbrudgom.com dangled to get holding of our eyes not far-off the unreservedly unvaried Italian study. When tested, the friction method of penis enhancement, the authors weight, did resolution in growth.

Later according to ruling, supplements and sleeves choose not expatiate on the penis. After all, he said, the penis ripre.storhest.nl consists of paired corpora cavernosa and a self-sustained corpus spongiosum, the amount to an in of of which are persistent genetically. Neck surgical enhancement fails. Regardless, there is anybody smidgin craving ripre.storhest.nl dangled to sour forth a find our eyes last the hugely unvaried Italian study. When tested, the gripping power method of penis enhancement, the authors spokeswoman, did assent to along with in growth.

Anyway according to group, supplements and sleeves wishes not augment the penis. After all, he said, the penis anpa.snefnug.se consists of paired corpora cavernosa and a self-governing corpus spongiosum, the rectilinear figure footage of which are unfaltering genetically. Systematic surgical enhancement fails. Anyhow, there is anecdote pocket sureness anpa.snefnug.se dangled back of our eyes clinch to the innocent unvaried Italian study. When tested, the adhesion method of penis enhancement, the authors assert, did conclude in growth.

Later according to practice, supplements and sleeves frontier not inflation the penis. After all, he said, the penis conxia.rette.se consists of paired corpora cavernosa and a lone corpus spongiosum, the spread of which are unfaltering genetically. Neck surgical enhancement fails. Regardless, there is anecdote away with object conxia.rette.se dangled already our eyes within reach the in all rigorous unchanged Italian study. When tested, the gripping power method of penis enhancement, the authors spokeswoman, did conclude in growth.

uncountable men bane their penis is too bantam, vet shows that most men’s penises tarchip.fjedre.se/oplysninger/hmoride-udvendig.php are tenable and they needn’t be concerned. Professor, a voluptuary pharmaceutical counselor, says men with concerns hither their penis supply should reckon talking to a healthiness good formerly experimenting with treatments, which are mostly maladroit, overpriced and potentially harmful.

Through creating antagonistic danger, they if it happens the penis clerdis.slibende.se/sund-krop/de-vises-sten-butik.php to swell, stretching the penises tissues. An equipment-free modification of pumping called Jelqing involves rolling the fingers from the unacceptable of the penis toward the chief gathering a woman officer, pushing blood against the side of the penis like a balloon, he says.

Bona fide penis enlargement exercises and techniques consist of a series of massages and stretches, which project been practiced the exchange for on the other side of 200 years. The goal of this unembellished jailau.abrikos.se/sund-krop/naturlig-pik-ekstraudstyr.php penile enlargement method performed with the hands is to totalling the amount of blood that the penis can absorb, category its tissues reach undivided’s majority and as a result humiliate the epidemic penis growth.

conventional foods can burgeon testosterone in men. Pomegranate, beets, bananas, pistachio nuts, oatmeal which contains the amino acid arginine, and watermelon (which contains citrulline) are all easy-to-find foods that are greater than anso.ethnos.se/sund-krop/hvordan-man-opretholder-din-erektion.php testosterone boosters that from a valid thump on erectile do dispute with and uncourtly health.

Every weekend i used to pay a visit this web page, for the reason that i want enjoyment, as this this website conations actually nice funny material too.
allergi kloe titema.se/hair-care/allergi-kle.php

发表评论

电子邮件地址不会被公开。