试一下JDK5的多线程编程,附件是代码,下载后改一下后缀名为.tgz
测试环境
OSX 10.5.6
JDK6
JUnit4.5
参考
[url=http://www.blogjava.net/sterning/archive/2007/10/13/152508.html] Java基于Socket文件传输示例[/url]
[url=file:///Users/mac/Library/Application%20Support/Firefox/Profiles/m04t1dbq.default/ScrapBook/data/20081224102238/index.html]Java5 多线程实践[/url]
Test 图
[img]/upload/attachment/67236/2e3c864f-a954-33ec-a717-b6443b5a71b2.png[/img]
Server 接口
/**
*
* @author rikugun
*/
public interface Server {
/*
* 启动服务器
*/
public void startup();
/*
* 停止服务器
*/
public void stop();
/*
* 判断服务器是否正在运行
* @return boolean 返回服务器是否正在运行
*/
public boolean isRunning();
}
客户端接口
/**
*
* @author rikugun
*/
public interface Client {
/*
* 批量获取文件
* @param String[] 文件名
* @return boolean 成功获取返回true
*/
public boolean getFiles(String[] file_names);
/*
* 获取单个文件
* @param String 文件名
* @return boolean 成功获取返回true
*/
public boolean getFile(String file_name);
}
服务器进程
/**
* 服务器进程
* @author rikugun
*/
public class ServerImpl implements Server,Runnable {
private static int PORT = 1213;
private static int MAX_POOL = 10;
private ServerSocket serverListen;
private ExecutorService pool;
private Properties prop;
private boolean running = false;
public boolean isRunning() {
return running;
}
public ServerImpl(Properties prop) {
this.prop = prop;
PORT = Integer.parseInt(prop.getProperty("server.port"));
MAX_POOL = Integer.parseInt(prop.getProperty("server.max_pool"));
pool = Executors.newFixedThreadPool(MAX_POOL);
}
public void startup() {
try {
serverListen = new ServerSocket(PORT);
serverListen.setReuseAddress(true);
running = !serverListen.isClosed();
while (running) {
//获取一个连接后启动一个处理线程
pool.execute(new ServerThread(serverListen.accept(), prop));
System.out.println("Get a client");
}
} catch (IOException ex) {
Logger.getLogger(ServerImpl.class.getName()).log(Level.SEVERE, null, ex);
}
}
public void stop(){
if(serverListen!=null){
try {
serverListen.close();
running = serverListen.isClosed();
pool.shutdown();
} catch (IOException ex) {
Logger.getLogger(ServerImpl.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
public void run() {
startup();
}
}
文件传输线程
/**
* 传输文件的线程
* @author rikugun
*/
public class ServerThread implements Runnable {
private Properties prop;
private static String dir_name = "files/";
private Socket sock;
private DataOutputStream dos;
private DataInputStream dis;
private static int buf_size = 8192;
private static Logger logger = Logger.getLogger(ServerThread.class.getName());
public ServerThread(Socket sock, Properties prop) {
this.sock = sock;
this.prop = prop;
dir_name = prop.getProperty("server.file_path");
buf_size = Integer.parseInt(prop.getProperty("server.buf_size"));
}
@Override
public void run() {
try {
dos = new DataOutputStream(sock.getOutputStream());
dis = new DataInputStream(sock.getInputStream());
//获取文件名
String file_name = dis.readUTF();
if (file_name != null) {
dos.writeBoolean(true);
logger.log(Level.INFO, "Get the filename:[" + file_name + "],Start to Send file!");
DataInputStream fis = new DataInputStream(new BufferedInputStream(new FileInputStream(dir_name +File.separator+ file_name)));
byte[] buf = new byte[buf_size];
while (true) {
int read = 0;
read = fis.read(buf);
if (read == -1) {
break;
}
dos.write(buf,0,read);
}
dos.flush();
fis.close();
logger.log(Level.INFO, "Success Send file:[" + dir_name + file_name + "]");
} else {
logger.log(Level.INFO, "No such file named:[" + file_name + "] in [" + dir_name + "]");
dos.writeBoolean(false);
dos.writeUTF("No such file named:[" + file_name + "] in [" + dir_name + "]");
}
} catch (IOException ex) {
logger.log(Level.SEVERE, null, ex);
} finally {
try {
dos.close();
} catch (IOException ex) {
Logger.getLogger(ServerThread.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
}
客户端实现
/**
*
* @author rikugun
*/
public class ClientImpl implements Client {
private Properties prop ;
private ExecutorService pool;
public ClientImpl(Properties prop) {
this.prop = prop;
pool = Executors.newFixedThreadPool(Integer.parseInt(prop.getProperty("client.max_pool")));
}
/*
* @see csdemo.client.Clinet
*/
public boolean getFiles(String[] file_names) {
boolean success = true;
for (String string : file_names) {
success = success && getFile(string);
}
return success;
}
/*
* @see csdemo.client.Clinet
*/
public boolean getFile(String file_name) {
boolean success = false;
try {
Socket sock = new Socket(prop.getProperty("server.ip"), Integer.parseInt(prop.getProperty("server.port")));
if(sock.isConnected())System.out.println("Connect to Server");
//加载处理线程
pool.execute(new ClientThread(sock, file_name, prop));
success = true;
} catch (UnknownHostException ex) {
Logger.getLogger(ClientImpl.class.getName()).log(Level.SEVERE, null, ex);
} catch (IOException ex) {
Logger.getLogger(ClientImpl.class.getName()).log(Level.SEVERE, null, ex);
}
return success;
}
}
客户端接收文件线程
/**
*
* @author rikugun
*/
public class ClientThread implements Runnable {
private Socket sock;
private String file_name;
private DataInputStream dis;
private DataOutputStream fos, dos;
private Properties prop;
public ClientThread(Socket sock, String file_name, Properties prop) {
this.sock = sock;
this.file_name = file_name;
this.prop = prop;
}
public void run() {
try {
dos = new DataOutputStream(sock.getOutputStream());
dis = new DataInputStream(new BufferedInputStream(sock.getInputStream()));
//告知服务器需要获取的文件名
dos.writeUTF(file_name);
byte[] buf = new byte[Integer.parseInt(prop.getProperty("server.buf_size"))];
if (dis.readBoolean()) {
int read = 0;
fos = new DataOutputStream(new BufferedOutputStream(new FileOutputStream(prop.getProperty("client.file_path") + File.separator + file_name)));
while (true) {
read = dis.read(buf);
if (read == -1) {
break;
}
fos.write(buf,0,read);
}
fos.flush();
fos.close();
System.out.println("Success write the response to " + file_name);
} else {
System.out.println("Get file Failed! " + dis.readUTF());
}
} catch (IOException ex) {
Logger.getLogger(ClientThread.class.getName()).log(Level.SEVERE, null, ex);
} finally {
try {
dis.close();
sock.close();
} catch (IOException ex) {
Logger.getLogger(ClientThread.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
}
客户端测试类
/**
*
* @author rikugun
*/
public class ClientTest {
static Properties prop = new Properties();
static ServerImpl server;
Client instance;
public ClientTest() {
}
@BeforeClass
public static void setUpClass() throws Exception {
FileInputStream fis = new FileInputStream("conf.properties");
prop.load(fis);
System.out.println("Load prop success!");
server = new ServerImpl(prop);
// server.startup();
new Thread(server).start();
if (server.isRunning()) {
System.out.println("Server is running...");
}else{
System.out.println("Server start failed!");
}
}
@AfterClass
public static void tearDownClass() throws Exception {
server.stop();
}
@Before
public void setUp() {
instance = (Client) new ClientImpl(prop);
}
@After
public void tearDown() {
}
/**
* Test of getFiles method, of class Client.
*/
@Test
public void testGetFiles() {
System.out.println("getFiles");
String[] file_names = new String[]{"2.txt", "3.txt", "4.txt", "5.txt"};
boolean expResult = true;
boolean result = instance.getFiles(file_names);
assertEquals(expResult, result);
}
/**
* Test of getFile method, of class Client.
*/
@Test
public void testGetFile() {
System.out.println("getFile");
String file_name = "1.txt";
boolean expResult = true;
boolean result = instance.getFile(file_name);
assertEquals(expResult, result);
}
}