gpt4 book ai didi

python - 在 Flask 中验证验证码

转载 作者:行者123 更新时间:2023-12-01 05:34:08 24 4
gpt4 key购买 nike

我创建验证码只是为了练习。验证码图像的创建看起来不错。但每次我尝试验证用户输入的验证码质询时,都会针对下一个验证码进行验证。我不知道如何处理这个问题。创建验证码图像的函数- captcha.py

import random
import Image
import ImageFont
import ImageDraw
import ImageFilter
import JpegImagePlugin
import PngImagePlugin


def gen_captcha(text, fnt, fnt_sz, file_name, fmt='JPEG'):
fgcolor = random.randint(0,0xff0000)
bgcolor = fgcolor ^ 0xffffff
font = ImageFont.truetype(fnt,fnt_sz)
dim = font.getsize(text)
im = Image.new('RGB', (dim[0]+5,dim[1]+5), bgcolor)
d = ImageDraw.Draw(im)
x, y = im.size
r = random.randint
for num in range(100):
d.rectangle((r(0,x),r(0,y),r(0,x),r(0,y)),fill=r(0,0xffff00))
d.text((3,3), text, font=font, fill=fgcolor)
im = im.filter(ImageFilter.EDGE_ENHANCE_MORE)
im.save(file_name)

views.py 中的注册函数

@app.route('/signup', methods = ['GET', 'POST'])
def signup():
if g.user is not None and g.user.is_authenticated():
return redirect(url_for('index'))

words = open('app/corncob_caps.txt').readlines()
captcha_word = words[random.randint(1,len(words))]
captcha_filename = ''.join(random.choice(string.ascii_uppercase + string.digits) for x in range(10)) + '.jpg'
captcha.gen_captcha(captcha_word.strip(), 'app/os.ttf', 25, 'app/static/' + captcha_filename + '')


form = SignUpForm(captcha_word)

if form.validate_on_submit() == False:
return render_template('signup.html', form = form, filename = captcha_filename)
else:
user = User(form.email.data, form.password.data)
db.session.add(user)
db.session.commit()
flash('You have successfully signed up.')
flash('You may login now.')
return redirect(url_for('login'))

return render_template('signup.html', form = form, filename = captcha_filename)

我正在将 captcha_word 传递给我的表单类。表单类是:

class SignUpForm(Form):
email = EmailField('Email Address', validators = [email()])
password = PasswordField('Password', validators = [Required('Please enter a valid password between 8 and 30 characters.'), Length(min = 8, max = 30)])
captcha = TextField('Captcha', validators = [Required('You must enter the challenge captcha.')])
submit = SubmitField('Create Account')
captcha_word = ''

def __init__(self, word, *args, **kwargs):
Form.__init__(self, *args, **kwargs)
self.get_word(word)

def get_word(self, word):
self.captcha_word = word

def validate(self):
if not Form.validate(self):
return False
elif self.captcha_word != self.captcha.data.upper():
print self.captcha_word
print self.captcha.data.upper()
self.captcha.errors.append("Wrong captcha!")
return False

user = self.get_user()
if user:
self.email.errors.append("That email is already taken.")
return False
else:
return True

def get_user(self):
return User.query.filter_by(email = self.email.data.lower()).first()

我在里面插入了两个 print 语句来看看为什么比较会出错。第一个打印显示下一个验证码,而 print self.captcha.data.upper() 显示用户输入的数据。

我不确定,但似乎注册路由被调用了两次。但我不知道如何解决这个问题。有任何想法吗?

最佳答案

如果需要使用验证码,可以使用feature that's already built into Flask-WTF并避免自己重新发明轮子。

如果您确实想重新发明轮子,那么您遇到的主要问题是当用户提交表单时重新创建验证码,您无法记住并引用旧值。

这就是目前的工作方式:

  • 用户登录时,您生成验证码,然后由于他们尚未提交表单,因此会显示包含验证码图片的登录表单。
  • 用户填写表单并点击提交按钮 - 这会再次加载注册 View ,创建一个新的随机验证码,然后向下提交表单逻辑路径,因此当您将用户验证码数据与当前验证码数据进行比较时,它不匹配。

所以你缺少持久性,你第一次生成的验证码不会保存在任何地方,所以当用户提交时你无法引用它。所以你需要将验证码存储在某个地方。您可以简单地将验证码单词存储在用户的 session 中,并在需要时使用它进行验证,或者使用 itsdangerous 对其进行签名。并将其作为隐藏字段存储在表单本身中?

代码示例:

这只是需要你的代码并稍微调整一下以将值存储在 session 中 - 未经测试,并且肯定可以改进,但应该可以工作:

@app.route('/signup', methods = ['GET', 'POST'])
def signup():

if g.user is not None and g.user.is_authenticated():
return redirect(url_for('index'))

if request.method == 'post':
captcha_word = session["captcha"]
else:
words = open('app/corncob_caps.txt').readlines()
captcha_word = words[random.randint(1,len(words))]
session["captcha"] = captcha_word
captcha_filename = ''.join(random.choice(string.ascii_uppercase + string.digits) for x in range(10)) + '.jpg'
captcha.gen_captcha(captcha_word.strip(), 'app/os.ttf', 25, 'app/static/' + captcha_filename + '')


form = SignUpForm(captcha_word)

if form.validate_on_submit() == False:
return render_template('signup.html', form = form, filename = captcha_filename)
else:
user = User(form.email.data, form.password.data)
db.session.add(user)
db.session.commit()
flash('You have successfully signed up.')
flash('You may login now.')
return redirect(url_for('login'))

return render_template('signup.html', form = form, filename = captcha_filename)

关于python - 在 Flask 中验证验证码,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19543917/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com