-1
我遇到了套接字/ tkinter登錄應用程序的問題。服務器在Raspberry Pi上,但即使服務器沒有啓動,我也沒有理由認爲這應該在啓動時掛起。我已經導入了一個我將要包含的模塊。使用套接字的Tkinter應用程序開始掛起
爲什麼它掛起?
這裏是我的客戶端代碼 - 那掛着一個: -
import socket, pickle
import Tkinter as tk
import loginutility
class Server(object):
def __init__(self):
self.s = socket.socket()
self.p = 10000
self.ip = "192.168.1.120"
def addUser(self, userinfo):
puserinfo = pickle.dumps(userinfo)
self.s.connect((self.ip, self.p))
self.s.sendall("check")
self.sendall(puserinfo)
if self.s.recv(1024) == False:
self.s.sendall("add")
self.send(puserinfo)
return True
else:
return False
def userDump(self):
self.s.sendall("userdump")
return pickle.loads(self.s.recv(1024))
class Main(tk.Tk):
def __init__(self):
tk.Tk.__init__(self)
class LoginFrame(tk.Frame):
def __init__(self, parent):
tk.Frame.__init__(self, parent)
self.pack()
self.l = loginutility.LoginBox(self)
login = tk.Button(self, text="Login", command=self.login)
login.pack()
def login(self):
u, p = self.l.values()
users = Server.userDump()
if u in users and users[u] == p:
tk.Label(self, text="Success").pack()
main = Main()
mf = LoginFrame(main)
main.mainloop()
服務器代碼進行測試時是不是:
import loginutility as lu
import socket
import pickle
s = socket.socket()
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
address = ''
port = 10000
s.bind((address, port))
s.listen(5)
users = lu.UserList("accounts")
while True:
c, clientaddress = s.accept()
c.send("You're Connected")
d = c.recv(1024)
if d == "add":
userdata = c.recv(1024)
username, password = pickle.loads(userdata)
users.adduser(username, password)
print "User {} added with password of {}.".format(username, password)
c.send("Success")
elif d == "check":
username, password = pickle.loads(c.recv(1024))
if users.checkuser(username) == False:
c.sendall(False)
else:
c.sendall(True)
elif d == "userdump":
c.send(pickle.dumps(users.dumpuser())
c.close()
必要loginutility代碼:
class LoginBox:
def __init__(self, parent):
self.l1=Label(parent, text="Username:").grid()
self.ubox=Entry(parent)
self.ubox.grid()
self.l2=Label(parent, text="Password:").grid()
self.pbox=Entry(parent, show="*")
self.pbox.grid()
def values(self):
return (self.ubox.get(), self.pbox.get())
class UserList:
def __init__(self, file=None):
self.users = {}
self.file = file
if file != None:
with open(file, "rb") as f:
self.users = pickle.load(f)
def adduser(self, user, pswrd):
self.users[user] = pswrd
if file != None:
with open(self.file, "wb") as f:
pickle.dump(self.users, f)
def dumpuser(self):
return self.users
任何幫助非常感謝!
如果服務器代碼在測試此代碼時未啓用,爲什麼要包含它?您應該將此代碼降低到仍能再現問題的絕對最少線條。在這種情況下,你可能會刪除2/3的代碼。 –
您的服務器在測試時運行。當你調用self.s.connect()時,你的應用程序可能會永遠等待你的服務器響應。如果您的服務器沒有運行,客戶端將凍結在那裏。你可以通過添加一個[timeout](https://docs.python.org/2/library/socket.html#socket.socket.settimeout)到你的套接字來解決這個問題,你也可以通過做網絡東西來避免鎖定你的應用程序在另一個線程中。但要小心,因爲線程會讓你的應用程序**調試更復雜。 –
@TomásGonzalezDowling不,不是的,我已經接受⬇️下面的答案,但謝謝你的建議! –