📄 ftpdhandler.java
字号:
import java.io.*;import java.net.*;import java.util.*;public class FtpdHandler extends Thread { Socket socket; Socket dataSocket; ServerSocket serverSocketData; BufferedReader in; PrintWriter out; File dir; boolean passiveMode=false; String dataType="I"; File target= new File(""); public FtpdHandler(Socket s, String rootdir) { socket = s; File temp = new File(rootdir); if (temp.isDirectory()) dir = temp; else return; start(); } public void run() { int port = 1; String user=""; String host=""; InetAddress inet; try { //determine hostname inet = socket.getInetAddress(); host = inet.getHostName(); System.out.println(host+" connected"); in = new BufferedReader(new InputStreamReader(socket.getInputStream())); out = new PrintWriter(socket.getOutputStream(),true); out.println("220 SOOT2-Ftpd Ready"); //登陆标识,注意本代码片没有进行密码验证 boolean login = false; while (!login) { try { String str = in.readLine(); StringTokenizer token = new StringTokenizer(str); String command = token.nextToken(); if(command.equals("USER")) { user = token.nextToken(); //提示输入密码 out.println("331 Password"); } else if(command.equals("PASS")) { //提示登陆成功 out.println("230 User "+user+" logged in."); login = true; } else out.println("530 Not logged in."); } catch(NoSuchElementException e) { out.println("500 syntax error dude."); } } while(true) { try { //Read command String str = in.readLine(); StringTokenizer token = new StringTokenizer(str); String command = token.nextToken(); //if command is RETR (==download) //从服务器下载文件 if(command.equals("RETR")) { //得到文件名 String filename = token.nextToken(); //只读方式打开文件 RandomAccessFile outFile = new RandomAccessFile(dir.getPath()+"/"+filename,"r"); //判断是主动模式还是被动模式 if (!passiveMode) { //主动模式主动建立连接 dataSocket = new Socket(inet,port); } else { //本例主要实现被动模式 passiveMode=false; } int amount; try { //二进制的形式 if (dataType.equals("I")) { out.println("150 Binary data connection."); OutputStream out2 = dataSocket.getOutputStream(); //以字节流的形式读写 byte bb[] = new byte[1024]; while((amount = outFile.read(bb)) != -1) { out2.write(bb, 0, amount); } out2.close(); } //ascii码形式 else if (dataType.equals("A")) { out.println("150 ASCII data."); PrintWriter out2 = new PrintWriter(dataSocket.getOutputStream()); //以字符流的形式读写 String line = outFile.readLine(); while(line != null) { out2.println(line); line = outFile.readLine(); } out2.close(); } out.println("226 transfer complete"); outFile.close(); dataSocket.close(); } catch(IOException e8) { out.println("426 Connection closed; transfer aborted."); try { outFile.close(); dataSocket.close(); } catch(Exception e9) {} } } //if command equals STOR (==upload) //将客户端提交的文件写入服务器 else if(command.equals("STOR")) { String filename = token.nextToken(); //以读写方式打开文件 RandomAccessFile inFile = new RandomAccessFile(dir.getPath()+"/"+filename,"rw"); if (!passiveMode) { dataSocket = new Socket(inet,port); } else { passiveMode=false; } int amount; try { if (dataType.equals("I")) { out.println("150 Binary data connection."); InputStream in2 = dataSocket.getInputStream(); byte bb[] = new byte[1024]; while((amount = in2.read(bb)) != -1) { inFile.write(bb, 0, amount); } in2.close(); } else if (dataType.equals("A")) { out.println("150 ASCII data."); BufferedReader in2 = new BufferedReader(new InputStreamReader(dataSocket.getInputStream())); String line = in2.readLine(); while(line != null) { inFile.writeBytes(line); line = in2.readLine(); } in2.close(); } out.println("226 transfer complete"); inFile.close(); dataSocket.close(); } catch(IOException e6) { out.println("426 Connection closed; transfer aborted."); try { inFile.close(); dataSocket.close(); } catch(Exception e7) {} } } else if(command.equals("TYPE")) { String tp = token.nextToken(); if (tp.equals("A") || tp.equals("I")) { out.println("200 type set to "+tp); //设置数据类型 dataType = tp; } else out.println("500 what type?"); } else if(command.equals("DELE")) { String filename = token.nextToken(); File f = new File(dir,filename); f.delete(); out.println("250 delete command successful"); } else if(command.equals("CDUP")) { File temp = dir.getParentFile(); if (temp != null) dir = temp; out.println("250 CWD command succesful."); } else if(command.equals("CWD")) { String newdir = token.nextToken(); if (newdir.equals("..")) { File temp = dir.getParentFile(); if (temp != null) dir = temp; out.println("250 CWD command succesful"); } else { //搜索是否有该目录 File temp = new File(dir.getPath() + "/" + newdir); File temp2 = new File(newdir); if (temp.isDirectory()) { dir = temp; out.println("250 CWD command succesful"); } else if (temp2.isDirectory()) { dir = temp2; out.println("250 CWD command succesful"); } else out.println("550 No can do, directory doesn`t exist."); } } else if(command.equals("QUIT")) { out.println("221 Have a nice day"); System.out.println(host+" connection closed"); break; } else if(command.equals("PWD")) { out.println("257 \""+dir.getPath()+"\" is current directory"); } else if(command.equals("SYST")) { out.println("215 UNIX ."); } else if(command.equals("PASV")) { StringTokenizer token2 = new StringTokenizer(socket.getLocalAddress().getHostAddress()); String[] parts = new String[4]; for (int i=0;i<3;i++) { parts[i]=token2.nextToken("."); } //最后一个IP段没有点分隔符 parts[3]=token2.nextToken(); out.println("227 Entering Passive Mode ("+parts[0]+","+parts[1]+","+parts[2]+","+parts[3]+",7,228)"); //在2020开启一个监听端口 serverSocketData= new ServerSocket(2020); dataSocket=serverSocketData.accept(); //有连接请求后返回socket,并关闭监听服务 serverSocketData.close(); //设置被动模式 passiveMode=true; } else if(command.equals("PORT")) { token.nextToken(","); token.nextToken(); token.nextToken(); token.nextToken(); int res = 0; while (token.hasMoreTokens()) { String a = token.nextToken(); res = res * 256; res += Integer.parseInt(a); } port = res; out.println("200 PORT command successful."); } //得到服务器FTP目录的文件列表 else if(command.equals("LIST")) { if (!passiveMode) { dataSocket = new Socket(inet,port); } else { passiveMode=false; } PrintWriter out2 = new PrintWriter(dataSocket.getOutputStream(),true); try { out.println("150 ASCII data."); //打印当前目录的所以文件 File[] a = dir.listFiles(); out2.println("total "+a.length); for(int i = 0 ; i < a.length ; i++ ) { if (a[i].isDirectory()) out2.println("dr-------- "+a[i].getName()); else out2.println("-r-------- "+a[i].getName()); } out2.close(); dataSocket.close(); out.println("226 transfer complete"); } catch(IOException e) { out.println("426 Connection closed; transfer aborted."); try { out2.close(); dataSocket.close(); } catch(Exception e) {} } } else if(command.equals("MKD")) { String newdir = token.nextToken(); //建立一个目录 File temp = new File(newdir); if (!temp.isAbsolute()) temp = new File(dir,newdir); //建立成功 if(temp.mkdir()) out.println("257 "+newdir+" created."); else out.println("550 directory not created."); } else if(command.equals("RMD")) { String newdir = token.nextToken(); File temp = new File(newdir); if (!temp.isAbsolute()) temp = new File(dir,newdir); //删除相应目录 if(temp.delete()) out.println("257 "+newdir+" deleted."); else out.println("550 directory not deleted."); } else if(command.equals("RNFR")) { String tname = token.nextToken(); target = new File(tname); //判断文件是否存在 if (!target.isAbsolute()) target = new File (dir,tname); if (target.exists()) out.println("350 File exists."); else out.println("550 No such file."); } else if(command.equals("RNTO")) { String tname = token.nextToken(); File temp = new File(tname); if (!temp.isAbsolute()) temp = new File(dir,tname); //将文件改名 if (target.renameTo(temp)) out.println("250 File renamed."); else out.println("550 No can do."); } else { out.println("500 Command not understood."); } } catch(Exception e) { out.println("500 error"); } } socket.close(); } catch (Exception e3) { try { socket.close(); } catch(Exception e2) {} } } }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -