Smail/test/review/smtp_findings_test.go

48 lines
1.9 KiB
Go

package smtp_server
import (
"net/http/httptest"
"strings"
"testing"
"git.pcux.cn/xuans/Smail/dto/parsemail"
"git.pcux.cn/xuans/Smail/dto/response"
"git.pcux.cn/xuans/Smail/models"
"git.pcux.cn/xuans/Smail/services/detail"
"git.pcux.cn/xuans/Smail/utils/context"
)
func TestAuditInboundBCCMustNotLeakToVisibleRecipient(t *testing.T) {
engine, _ := newAuditTestEngine(t)
visible := models.User{Account: "visible", Name: "Visible"}
hidden := models.User{Account: "hidden", Name: "Hidden"}
if _, err := engine.Insert(&visible, &hidden); err != nil {
t.Fatal(err)
}
raw := "From: sender@example.net\r\n" +
"To: visible@example.com\r\n" +
"Message-ID: <audit-private-recipient@example.net>\r\n" +
"Subject: privacy\r\nContent-Type: text/plain\r\n\r\nbody"
envelope := []string{"visible@example.com", "hidden@example.com"}
parsed, err := parsemail.NewEmailFromReader(envelope, strings.NewReader(raw), len(raw))
if err != nil {
t.Fatal(err)
}
users, stored, err := saveEmail(&context.Context{}, len(raw), parsed, 0, 0, envelope, true, true)
if err != nil || stored == nil || len(users) != 2 {
t.Fatalf("多收件人入库前置条件失败: users=%d stored=%v err=%v", len(users), stored != nil, err)
}
data, err := detail.GetEmailDetail(&context.Context{UserID: visible.ID}, stored.Id, false)
if err != nil {
t.Fatal(err)
}
// 执行网页详情使用的真实服务和响应序列化,不依赖 UI 是否显示该字段。
recorder := httptest.NewRecorder()
response.NewSuccessResponse(data).FPrint(recorder)
leaked := strings.Contains(recorder.Body.String(), "hidden@example.com")
t.Logf("raw_contains_hidden_recipient=%v persisted_recipient_count=%d visible_response_contains_hidden_recipient=%v", strings.Contains(raw, "hidden@example.com"), len(users), leaked)
if leaked {
t.Fatal("普通可见收件人的邮件详情响应泄露了仅存在于信封中的密送地址")
}
}