Примечание! тем, кто связывает это сообщение с:https://i.stack.imgur.com/hHZPl.png это НЕ решает проблему, и все в нем было протестировано.
У меня есть классическая форма ASP, которая отправляет через CDO с использованием шаблона HTML для отправки электронной почты... передача специальных языковых символов (в данном случае датских символов æ,ø,å
) из формы на страницу ASP, содержащую код CDO, работает нормально и отображает символы правильно при создании Response.Write
на этой странице. Но когда электронная почта отправляет переданные символы, они путаются. Однако, если я напишу символы непосредственно в HTML-шаблоне, они правильно отобразятся в электронном письме. Для всех трех документов установлена кодировка UTF-8, а для страниц ASP установлена кодировка CODEPAGE 65001. Может ли кто-нибудь увидеть, что происходит, чтобы вызвать такое поведение?
Вот что происходит в электронной почте:
Шаблон электронного письма (только определение):
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>Email</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<style type="text/css">
a[x-apple-data-detectors] {
color: inherit !important;
}
</style>
</head>
<body style="margin: 0; padding: 0;">
</body>
</html>
sendmail.asp :
<%@Codepage = 65001%>
<%
Option explicit
Response.CodePage = 65001
Response.CharSet = "UTF-8"
Dim SettingsConn
Set SettingsConn = Server.CreateObject("ADODB.Connection")
SettingsConn.ConnectionString="Provider=SQLOLEDB; DATA SOURCE=<SERVER>;UID=<USERNAME>;PWD=<PASSWORD>;DATABASE=<DB>"
SettingsConn.Open
Dim SettingsSQL, objSettings
SettingsSQL = "SELECT SMTPServer,SMTPPort,MailFromName,MailFromEmail,MailCC,MailBCC,EFPVersion FROM EFP_Settings WHERE ID = 1;"
Set objSettings = SettingsConn.Execute(SettingsSQL)
dim pde : set pde = createobject("scripting.dictionary")
function getTextFromFile(path)
dim fso, f, txt
set fso = createobject("Scripting.FileSystemObject")
if not fso.fileexists(path) then
getTextFromFile = ""
exit function
end if
set f = fso.opentextfile(path,1)
if f.atendofstream then txt = "" else txt = f.readall
f.close
set f = nothing
set fso = nothing
getTextFromFile = txt
end function
dim redir, mailto, mailfrom, subject, item, body, cc, bcc, message, html, template, usetemplate, testmode
redir = request.form("redirect")
mailto = request.form("mailto")
if pde.exists(mailto) then mailto = pde(mailto)
cc = objSettings("MailCC")
bcc = objSettings("MailBCC")
subject = request.form("subject")
message = request.form("message")
template = request.form("template")
if len(template) > 0 then template = getTextFromFile(server.mappath(template))
if len(template) > 0 then usetemplate = true else usetemplate = false
dim msg : set msg = server.createobject("CDO.Message")
dim smtpServer, yourEmail, yourPassword
msg.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/sendusing") = 2
msg.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpserver") = "" & objSettings("SMTPServer") & ""
msg.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpserverport") = objSettings("SMTPPort")
msg.Configuration.Fields.Update
msg.subject = subject
msg.to = mailto
msg.from = """" & objSettings("MailFromName") & """ <" & objSettings("MailFromEmail") & ">"
msg.Sender = """" & objSettings("MailFromName") & """ <" & objSettings("MailFromEmail") & ">"
if len(cc) > 0 then msg.cc = cc
if len(bcc) > 0 then msg.bcc = bcc
if not usetemplate then
body = body & message & vbcrlf & vbcrlf
else
body = template
end if
for each item in request.form
select case item
case "redirect", "mailto", "cc", "bcc", "subject", "message", "template", "html", "testmode"
case else
if not usetemplate then
if item <> "mailfrom" then body = body & item & ": " & request.form(item) & vbcrlf & vbcrlf
else
body = replace(body, "[$" & item & "$]", replace(request.form(item),vbcrlf,"<br>"))
end if
end select
next
if usetemplate then
dim rx : set rx = new regexp
rx.pattern = "\[\$.*\$\]"
rx.global = true
body = rx.replace(body, "")
end if
msg.htmlbody = body
msg.send
response.redirect redir
set msg = nothing
%>
ОБНОВЛЕНИЕ:
На основании комментариев ниже;
Я попытался преобразовать FSO в ADODB, чтобы он выглядел так, как показано ниже, но это ошибка:
Код :
function getTextFromFile(path)
Dim adoStream, txt
Set adoStream = CreateObject("Adodb.Stream")
if not adoStream.FileSystemObject(path) then
getTextFromFile = ""
exit function
end if
adoStream.Open
adoStream.Charset = "UTF-8"
txt = adoStream.ReadText(-1)
adoStream.LoadFromFile txt
adoStream.Close
Set adoStream = Nothing
getTextFromFile = txt
end function
Последнее обновление (28 марта 2021 г.) – 11:36
Последний файл sendmail.asp:
<%@Codepage = 65001%>
<%
Option explicit
Response.CodePage = 65001
Response.CharSet = "UTF-8"
Dim SettingsConn
Set SettingsConn = Server.CreateObject("ADODB.Connection")
SettingsConn.ConnectionString="Provider=SQLOLEDB; DATA SOURCE=<SERVER>;UID=<USERNAME>;PWD=<PASSWORD>;DATABASE=<DATABASE>"
SettingsConn.Open
Dim SettingsSQL, objSettings
SettingsSQL = "SELECT SMTPServer,SMTPPort,MailFromName,MailFromEmail,MailCC,MailBCC,EFPVersion FROM EFP_Settings WHERE ID = 1;"
Set objSettings = SettingsConn.Execute(SettingsSQL)
dim redir, mailto, mailfrom, subject, item, body, cc, bcc, html, template, usetemplate, testmode
redir = request.form("redirect")
mailto = request.form("mailto")
cc = objSettings("MailCC")
bcc = objSettings("MailBCC")
subject = request.form("subject")
template = request.form("template")
Response.Write request.form("template")
' Output of request.form("template") is templates/emailtemplate_report_issue.htm
Dim adoStream, getTextFromFile
Set adoStream = CreateObject("Adodb.Stream")
adoStream.Type = 2
adoStream.Open
adoStream.Charset = "UTF-8"
adoStream.LoadFromFile server.mappath("" & template & "")
template = adoStream.ReadText(-1)
adoStream.Close
Set adoStream = Nothing
getTextFromFile = template
dim msg : set msg = server.createobject("CDO.Message")
dim smtpServer, yourEmail, yourPassword
msg.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/sendusing") = 2
msg.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpserver") = "" & objSettings("SMTPServer") & ""
msg.Configuration.Fields.Item ("http://schemas.microsoft.com/cdo/configuration/smtpserverport") = objSettings("SMTPPort")
msg.Configuration.Fields.Update
msg.subject = subject
msg.to = mailto
msg.from = """" & objSettings("MailFromName") & """ <" & objSettings("MailFromEmail") & ">"
msg.Sender = """" & objSettings("MailFromName") & """ <" & objSettings("MailFromEmail") & ">"
if len(cc) > 0 then msg.cc = cc
if len(bcc) > 0 then msg.bcc = bcc
body = template
for each item in request.form
body = replace(body, "[$" & item & "$]", replace(request.form(item),vbcrlf,"<br>"))
next
dim rx : set rx = new regexp
rx.pattern = "\[\$.*\$\]"
rx.global = true
body = rx.replace(body, "")
msg.htmlbody = body
msg.send
response.redirect redir
set msg = nothing
%>
Вывод по электронной почте, где символы не отображаются должным образом (обе переменные передаются из формы и жестко закодированы)
@CodePage
. Кроме того, убедитесь, что ваши строковые данные SQL Server хранятся какNVARCHAR
, а неVARCHAR
. - person user692942   schedule 26.03.2021@CodePage
не имеет никакого значения для вывода электронной почты, по-прежнему не отображает символы правильно ... @ user692942 : В процессе передачи переменных со страницы asp формы для отправки почты asp на HTML-страницу я не вызываю никакого соединения с ДБ. - person   schedule 26.03.2021request.form
элементов в[$FormItems$]
? - person   schedule 27.03.2021@CodePage
? См. дубликат, где он должен быть размещен. Также вы можете показать страницу, которая отправляет форму? - person user692942   schedule 27.03.2021msg.BodyPart.Charset = "utf-8"
? (См. дубликат ссылки). - person user692942   schedule 27.03.2021msg.htmlbody = Server.HTMLEncode(body)
не работает, ноmsg.BodyPart.Charset = "utf-8"
работает для значений, прошедших из формы, теперь они правильно отображаются в электронной почте, однако все датские символы, жестко закодированные в HTML-файле шаблона, теперь перепутались. вверх, они работали раньше. - person   schedule 27.03.2021<meta charset="UTF-8" /> <meta http-equiv="Content-Type" content="text/html;charset=UTF-8" />
- person   schedule 27.03.2021getTextFromFile(server.mappath(template))
, как и в дублирующем вопросеFileSystemObject
, по умолчанию не читает UTF-8, и для этого лучше всего использовать объектADODB.Stream
, как описано в дублирующемся ответе. Не мог этого понять, пока не отформатировал код в вопросе. - person user692942   schedule 27.03.2021msg.BodyPart.Charset = "utf-8"
и пытался понять, как изменить FSO на ADODB.Stream, но, честно говоря, я ничего не знаю ... какие-либо советы о том, как я должен изменить свой FSO для использования ADODB. Поток? - person   schedule 27.03.2021getTextFromFile = txt
) в вашей функцииgetTextFromFile()
на примерADODB.Stream
, затем установитьadoStream.loadFromFile path
для загрузки пути, который вы передаете, и установитьtxt = adoStream.ReadText(-1)
, поскольку переменнаяtxt
— это то, что вы возвращаете из функции. Надеюсь это поможет. - person user692942   schedule 27.03.2021ADODB.Stream
не поддерживаетFileExists()
, то естьFileSystemObject
, вы также удалили строкуgetTextFromFile = txt
, которая вам все еще нужна в конце функции, чтобы вернуть значениеtxt
. - person user692942   schedule 27.03.2021ADODB .Stream
иFileSystemObject
. Я предположил, что у вас есть эти базовые знания, потому что вы были очень красноречивы, когда дело доходило до обсуждения проблемы кодирования. Существует множество примеров использованияADODB.stream
для преобразования файла в строку UTF-8. - person user692942   schedule 27.03.2021If
(в том числе между иEnd If
), который вы пытаетесь использовать, чтобы проверить, существует ли файл, и попробуйте это, думаю, вы обнаружите, что это сработает. Проверка существования файлаIf
может быть добавлена позже, но это должно помочь вам преодолеть черту. - person user692942   schedule 27.03.2021Arguments are of the wrong type, are out of acceptable range, or are in conflict with one another
... посмотрю, смогу ли я выяснить, что не так. :-) - person   schedule 28.03.2021adoStream.LoadFromFile txt
, прежде чем звонитьtxt = adoStream.ReadText(-1)
. Каким-то образом вы перепутали порядок, это должно исправить. - person user692942   schedule 28.03.2021adoStream.Charset = "UTF-8"
››adoStream.LoadFromFile txt
››txt = adoStream.ReadText(-1)
››adoStream.Close
.. ошибка в строке 23 этоadoStream.LoadFromFile txt
- person   schedule 28.03.2021adoStream.Type = 2
иadoStream.LoadFromFile server.mappath("" & template & "")
, но электронное письмо, которое я получаю, не возвращает ожидаемые символы ни для жестко запрограммированных, ни для переданных переменных, так что теперь все специальные символы испорчены, и я вернулся к тому, с чего начал раньше ADODB.Поток. См. обновленный код и снимок экрана в разделе Последнее обновление (28 марта 2021 г.) — 11:36. - person   schedule 28.03.2021æ, ø and å
, которые теперь отображают оба отправленных символа формы и жестко заданные символы верны. - person   schedule 28.03.2021Type
равно 2 илиadTypeText
, поэтому настройка ничего не делает. Изменение кодировки в шаблоне HTML просто вызовет другие проблемы и еще больше запутает проблему. Не уверен, почему вы деконструировали функцию в пользу встроенной, но вы просто создаете больше проблем, например, оставляете ссылку на возврат функции без функции, что теперь должен делатьgetTextFromFile = template
? Ты как-то все испортил до неузнаваемости. - person user692942   schedule 28.03.2021result.eml
в сути заключается в том, что, поскольку вы не задаете текстовое тело, CDO создает тело по умолчанию, отличное от UTF-8. Поэтому вы можете также закодировать текстовое тело. - person user692942   schedule 29.03.2021