简单FTP

需求:

1. 用户登陆

2. 上传/下载文件
3. 不同用户家目录不同
4. 查看当前目录下文件
5. 充分使用面向对象知识

</br>

6. **测试:**

----------

用户登陆

1,用户登陆
2,用户注册
3. 退出

请输入索引进行选择:1

请输入你的用户名(q返回):a

请输入你的密码:a

登陆成功!

请输入你想执行的命令(q退出)>>help

请用'put'+'空格'+'文件名'的格式上传文件

请用'get'+'空格'+'文件名'的格式下载文件

输入'dir'查看用户家目录文件

----------

7. **备注:**

1.程序运行在bin/startclient.py和startserver.py,请先运行server端,在运行client端

2.模拟的本地目录为db/client/目录,下面有两个测试文件a,b

3.模拟的服务器用户家目录为db/home/$name目录

4.测试账号用户名密码为a,a,测试目录为a,下面有两个测试文件,c,d

5.当client段或者server端强制退出时,另一端会报错。。

 

client端代码

import socket,os
from conf import settings

def file_cmd(client):

    while True:
        msg = input("请输入你想执行的命令(q退出)>>")
        if msg.lower().strip() == 'q':
            print('退出成功!')
            break
        if not msg:
            continue
        if msg.lower().strip() == 'help':
            print ("请用'put'+'空格'+'文件名'的格式上传文件")
            print ("请用'get'+'空格'+'文件名'的格式下载文件")
            print ("输入'dir'查看用户家目录文件")
            continue
        if msg.lower().strip() == 'dir':
            client.send('dir'.encode('utf-8'))
            data = client.recv(4096)
            print (data.decode())
            continue
        if msg.lower().strip().startswith('put'):
            client.send(msg.encode('utf-8'))
            msg_file, filename = msg.strip().split(' ')
            filename = os.path.join(settings.CLIENT_HOME,filename)
            if os.path.exists(filename):
                print("开始上传文件!")
                file_size = os.stat(filename).st_size
                client.send(str(file_size).encode('utf-8'))
                client.recv(4096)
                print("开始发送文件...")
                with open(filename, 'rb') as f:
                    for line in f:
                        client.send(line)
                print('发送完毕')
            else:
                print('文件不存在!')

        if msg.lower().strip().startswith('get'):
            client.send(msg.encode('utf-8'))
            msg_file, filename = msg.strip().split(' ')
            filename = os.path.join(settings.CLIENT_HOME, filename)
            file_size = client.recv(4096)
            if file_size.decode() == 'no':
                print('文件不存在!')
            else:
                client.send('please send file'.encode('utf-8'))
                file_size_all = int(file_size.decode())
                file_size_recv = 0
                with open(filename, 'wb') as f:
                    print("开始下载文件!")
                    while file_size_recv < file_size_all:
                        data = client.recv(4096)
                        file_size_recv = len(data) + 1
                        f.write(data)
                    else:
                        print('文件下载完毕!')


def Login(client):
    while True:
        name = input("请输入你的用户名(q返回):")
        if name.lower().strip() == 'q':
            print('返回上一层成功!')
            break
        else:
            password = input("请输入你的密码:")
            command = 'login'+' '+ name + ',' + password
            client.sendall(command.encode('utf-8'))
            msg = client.recv(4096)
            if msg.decode() == 'yes':
                print ("登陆成功!")
                file_cmd(client)
            elif msg.decode() == 'no':
                print ("用户名密码错误,或用户不存在!")
            else:
                print ("未知错误!")


def Register(client):
    while True:
        name = input("请输入你需要注册的用户名(q返回):")
        if name.lower().strip() == 'q':
            print('返回上一层成功!')
            break
        else:
            password = input("请输入你要注册的密码:")
            command = 'register' + ' ' + name + ',' + password
            client.sendall(command.encode('utf-8'))
            msg = client.recv(4096)
            if msg.decode() == 'yes':
                print("注册成功!")
                file_cmd(client)
            elif msg.decode() == 'no':
                print("用户名已经存在!")
            else:
                print("未知错误!")


def main(client):
    while True:
        menu = """
                1,用户登陆
                2,用户注册
                3. 退出
        """
        print (menu)
        choose = input("请输入索引进行选择:")
        if choose == '1':
            Login(client)
        elif choose == '2':
            Register(client)
        elif choose == '3':
            exit('退出成功!')
        else:
            print ("你的选择有误!")


def run():
    client = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
    client.connect((settings.HOST,settings.PORT))
    main(client)
    client.close()
client.py

 

server端代码

import socket
from core.user import User
from conf import settings


def run():
    ftpserver = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
    ftpserver.bind((settings.HOST,settings.PORT))
    ftpserver.listen(5)
    print ("服务运行中:正在监听{0}地址的{1}端口:".format(settings.HOST,settings.PORT))
    while True:
        conn,addr = ftpserver.accept()
        while True:
            data = conn.recv(4096)
            if not data:
                break
            else:
                print(data)
                data = data.decode()
                print(data)
                if data == 'dir':
                    users.view_file(conn)
                    continue
                msg, filename = data.strip().split(' ')
                msg = msg.lower()
                if msg == 'put':
                    users.Recvfile(conn, filename)

                elif msg == 'get':
                    re = users.judgement_file(filename)
                    if re == True:
                        users.Sendfile(conn, filename)
                    else:
                        conn.send('no'.encode('utf-8'))

                elif msg == 'login':
                    name, password = filename.split(',')
                    users = User(name, password)
                    re = users.login()
                    if re == True:
                        conn.send('yes'.encode('utf-8'))
                    else:
                        conn.send('no'.encode('utf-8'))
                elif msg == 'register':
                    name, password = filename.split(',')
                    print(name,password)
                    users = User(name, password)
                    re = users.register()
                    if re == True:
                        conn.send('yes'.encode('utf-8'))
                    else:
                        conn.send('no'.encode('utf-8'))
                else:
                    print("请求方的输入有错!")
server.py

用户交互代码

import os
import json
from conf import  settings


class User(object):
    def __init__(self,name,password):
        self.name = name
        self.password = password
        self.homedir = os.path.join(settings.USER_HOME,self.name)
        self.auth = os.path.join(settings.USER_AUTH,self.name)


    def login(self):
        if os.path.exists(self.auth):
            with open(self.auth,'r') as f:
                user_dict = json.load(f)
                if user_dict['password'] == self.password:
                    return True
                else:
                    return False
        else:
            return False


    def register(self):
        if os.path.exists(self.auth):
            return False
        else:
            os.mkdir(self.homedir)
            data = {'username': self.name,
                    'password': self.password}
            with open(self.auth, 'w') as f:
                json.dump(data,f)
            return True

    def judgement_file(self,filename):
        filename = os.path.join(self.homedir, filename)
        if os.path.exists(filename):
            return True
        else:
            return False


    def view_file(self,conn):
        data = os.popen('dir'+' '+ self.homedir).read()
        conn.sendall(data.encode('utf-8'))

    def Recvfile(self,conn,filename):
        print("开始接收文件...")
        filename = os.path.join(self.homedir, filename)
        file_size = conn.recv(4096)
        conn.send('please send file'.encode('utf-8'))
        file_size_all = int(file_size.decode())
        file_size_recv = 0
        with open(filename, 'wb') as f:
            print("开始下载文件!")
            while file_size_recv < file_size_all:
                data = conn.recv(4096)
                file_size_recv = len(data) + 1
                f.write(data)
            else:
                print('文件下载完毕!')



    def Sendfile(self,conn,filename):
        filename = os.path.join(self.homedir,filename)
        file_size = os.stat(filename).st_size
        conn.send(str(file_size).encode('utf-8'))
        conn.recv(4096)
        print("开始发送文件...")
        with open(filename, 'rb') as f:
            for line in f:
                conn.send(line)
        print('发送完毕')
user

 settings文件

#!/usr/bin/env python
# coding=utf-8
#Author:yang
import  os
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
BASE_DIR_DB = os.path.join(BASE_DIR,'db')
USER_HOME = os.path.join(BASE_DIR_DB,'home')
USER_AUTH = os.path.join(BASE_DIR_DB,'auth')
CLIENT_HOME = os.path.join(BASE_DIR_DB,'client')

HOST = 'localhost'
PORT = 9999
settings

 

转载于:https://www.cnblogs.com/judge9/p/7103363.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值