implement email verification feature, add captcha validation middleware, and enhance user authentication flow

This commit is contained in:
2025-07-22 08:50:16 +08:00
parent 6187425df6
commit a0d215fa2e
26 changed files with 844 additions and 50 deletions

View File

@ -0,0 +1,70 @@
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="UTF-8">
<title>{{.Title}}</title>
<style>
body {
font-family: Arial, sans-serif;
line-height: 1.6;
color: #333;
background-color: #f9f9f9;
margin: 0;
padding: 0;
}
.container {
max-width: 600px;
margin: 20px auto;
background: #fff;
border: 1px solid #ddd;
border-radius: 8px;
padding: 20px;
}
.header {
text-align: center;
margin-bottom: 20px;
}
.header h1 {
font-size: 24px;
color: #007BFF;
}
.content {
margin-bottom: 20px;
}
.content p {
margin: 10px 0;
}
.code {
font-size: 20px;
font-weight: bold;
color: #007BFF;
text-align: center;
margin: 20px 0;
padding: 10px;
background-color: #f0f8ff;
border-radius: 4px;
}
.footer {
text-align: center;
font-size: 12px;
color: #888;
}
</style>
</head>
<body>
<div class="container">
<div class="header">
<h1>欢迎使用 {{.Title}}</h1>
</div>
<div class="content">
<p>尊敬的用户 {{.Email}},您好!</p>
<p>{{.Details}} 以下是您的验证码:</p>
<div class="code">{{.VerifyCode}}</div>
<p>请在 <strong>{{.Expire}}</strong> 分钟内使用此验证码完成验证。</p>
</div>
<div class="footer">
<p>如果您未请求此邮件,请忽略。</p>
</div>
</div>
</body>
</html>

31
internal/static/embed.go Normal file
View File

@ -0,0 +1,31 @@
package static
import (
"bytes"
"embed"
"fmt"
"html/template"
)
//go:embed assets/*
var AssetsFS embed.FS
// RenderTemplate 从嵌入的文件系统中读取模板并渲染
func RenderTemplate(name string, data interface{}) (string, error) {
templatePath := "assets/" + name
templateContent, err := AssetsFS.ReadFile(templatePath)
if err != nil {
return "", fmt.Errorf("读取模板文件失败: %w", err)
}
// 解析模板
tmpl, err := template.New(name).Parse(string(templateContent))
if err != nil {
return "", fmt.Errorf("解析模板失败: %w", err)
}
// 渲染模板
var buf bytes.Buffer
if err := tmpl.Execute(&buf, data); err != nil {
return "", fmt.Errorf("渲染模板失败: %w", err)
}
return buf.String(), nil
}

View File

@ -0,0 +1,18 @@
package static
import (
"testing"
)
func TestRenderTemplate(t *testing.T) {
template, err := RenderTemplate("email/verification-code.tmpl", map[string]interface{}{
"Title": "Test Page",
"Email": "xxx@.comcom",
"Details": "nihao",
})
t.Logf(template)
if err != nil {
t.Errorf("渲染模板失败: %v", err)
return
}
}