有了以上三个javabean,只是==有了三个数据表(事实上,如果要保存聊天信息在数据库中,建立表进行插入删除更新即可),还要有掌控全局的ChatroomManager类。下面先给出完整代码。
package
org.jvk.chatroom.service;
import
java.io.File;
import
java.io.FileInputStream;
import
java.io.IOException;
import
java.util.HashMap;
import
java.util.List;
import
java.util.Map;
import
org.apache.commons.digester.Digester;
import
org.apache.commons.logging.Log;
import
org.apache.commons.logging.LogFactory;
import
org.jvk.chatroom.bean.Message;
import
org.jvk.chatroom.bean.Room;
import
org.jvk.chatroom.bean.User;
import
org.xml.sax.SAXException;
public
class
ChatroomManager {
private
static
Log
log
= LogFactory.getLog(ChatroomManager.
class
);
private
ChatroomManager() {
}
private
static
ChatroomManager
instance
=
new
ChatroomManager();
private
Map<String, Room>
rooms
=
new
HashMap<String, Room>();
public
static
ChatroomManager newInstance() {
return
instance
;
}
public
synchronized
void
config(FileInputStream in)
throws
IOException, SAXException{
log
.info(
"
初始化聊天室配置信息
"
);
Digester digester =
new
Digester();
digester.setValidating(
false
);
digester.push(
this
);
digester.addObjectCreate(
"rooms/room"
, Room.
class
);
digester.addBeanPropertySetter(
"rooms/room/name"
,
"name"
);
digester.addBeanPropertySetter(
"rooms/room/notice"
,
"notice"
);
digester.addBeanPropertySetter(
"rooms/room/maxMessage"
,
"maxMessage"
);
digester.addBeanPropertySetter(
"rooms/room/maxUser"
,
"maxUser"
);
digester.addSetNext(
"rooms/room"
,
"addRoom"
);
digester.parse(in);
}
public
synchronized
void
config(File file)
throws
IOException{
log
.info(
"
聊天室配置文件
:"
+file.getAbsolutePath());
config(
new
FileInputStream(file));
}
return
rooms
;
}
this
.
rooms
= rooms;
}
public
Room getRoom(String roomName) {
return
rooms
.get(roomName);
}
public
Room getRoom(User user) {
return
user.getRoom();
}
public
void
addRoom(Room room) {
rooms
.put(room.getName(), room);
}
public
void
addUserToRoom(User user) {
rooms
.get(user.getRoom().getName()).addUser(user);
}
public
void
removeUserFromRoom(User user) {
rooms
.get(user.getRoom().getName()).removeUser(user);
}
public
void
addMessageToRoom(Message message, Room room) {
rooms
.get(room.getName()).addMessage(message);
}
public
List<Message> getMessagesFromRoom(User user) {
return
user.getRoom().getMessages(user);
}
public
List<User> getUsersFromRoom(User user) {
return
getRoom(user).getUsers(user);
}
public
boolean
exists(String roomName, String userName) {
Room room = getRoom(roomName);
for
(User user : room.getUsers())
if
(user.getName().equalsIgnoreCase(userName))
return
t rue
;
return
false
;
}
public
boolean
exists(Room room, String userName) {
for
(User user : room.getUsers())
if
(user.getName().equalsIgnoreCase(userName))
return
true
;
return
false
;
}
}
其中 config(FileInputStream in) 方法通过读取配置文件初始化聊天室。配置文件是一个XML格式文件,解析XML文件时使用了commons-digester 包的Digester。Digester可以让我们轻易地把XML转换为Java对象。(详情请访问
http://commons.apache.org/digester/)。
从以下的java代码
digester.addObjectCreate(
"rooms/room"
, Room.
class
);
digester.addBeanPropertySetter(
"rooms/room/name"
,
"name"
);
digester.addBeanPropertySetter(
"rooms/room/notice"
,
"notice"
);
digester.addBeanPropertySetter(
"rooms/room/maxMessage"
,
"maxMessage"
);
digester.addBeanPropertySetter(
"rooms/room/maxUser"
,
"maxUser"
);
digester.addSetNext(
"rooms/room"
,
"addRoom"
);
可以猜到XML配置文件是这样的:
<?
xml
version
=
"1.0"
encoding
=
"GBK"
?>
<
rooms
>
<
room
>
<
name
>
我的聊天室
</
name
>
<
notice
>
欢迎交流学习
</
notice
>
<
maxMessage
>
10
</
maxMessage
>
<
maxUser
>
100
</
maxUser
>
</
room
>
<
room
>
<
name
>
你的聊天室
</
name
>
<
notice
>
欢迎交流娱乐
</
notice
>
<
maxMessage
>
15
</
maxMessage
>
<
maxUser
>
150
</
maxUser
>
</
room
>
</
rooms
>
这个类除了读取配置文件进行初始化外,还担当“门面模式”的角色,以后不管如何操作Message、User和Room三个类,都通过ChatroomManager间接进行。
因为Room对象包含了User和Message,所以这里只需要一个Room的集合:
private
Map<String, Room>
rooms
=
new
HashMap<String, Room>();
只要有Room在手,一切掌握之中。
接下来可以进行 Servlet 的编写了。