MS Word DDE: Что разрушает мою кодировку? - PullRequest
1 голос
/ 16 июня 2010

У меня проблема с автоматизацией MS Word DDE, управляемой нашей системой CRM.

Настройка

Основой для созданного документа является шаблон Word .dot, который запускает макрос в Document.New. Внутри этого макроса я создаю компонент .Net, зарегистрированный для COM.

Set myCOMObject = CreateObject("MyCOMObject")

Компонент извлекает некоторые данные из базы данных и передает строковые значения, которые присваиваются Word DocumentVariables.

Set someClass = myCOMObject.GetSomeClass(123)
ActiveDocument.Variables("docaddress") = someClass.GetSenderAddress(456)

Все строковые значения, возвращаемые компонентом, кодируются в UTF-16 (кодовая страница 1200).

Что происходит

Проблема возникает, когда система CRM вызывает Word для создания нового документа с помощью DDE (winword.exe / n / dde): строковые значения из компонента преобразуются в строки в кодировке UTF-8.

Весь статический текст внутри шаблона остается хорошо закодированным в UTF-16 - например, umlaut ü внутри моих DocumentVariables превращается в c3 b0 , пока он остается fc для остальной части документа (проверенный файл в шестнадцатеричном редакторе).

Если я создаю документ из шаблона с той же самой макрофункцией напрямую (без DDE), все строки в порядке; т.е. кодируются в UTF-16.

Побочные эффекты Если я создаю новый документ из моего шаблона, оставляю этот документ открытым и создаю новый документ, управляемый DDE, символы кодируются правильно!

Это также работает наоборот: создание документа, управляемого DDE, сначала нарушает кодировку символов при создании второго документа напрямую.

1 Ответ

0 голосов
/ 01 июля 2010

Как оказалось, решение состоит в том, чтобы заменить доступ к базе данных через System.Data.OleDb

OleDbCommand command = new OleDbCommand(query, connection);

OleDbParameter companyIdParam = command.CreateParameter();
companyIdParam.ParameterName = "companyId";
companyIdParam.Direction = ParameterDirection.Input;
companyIdParam.OleDbType = OleDbType.Integer;
companyIdParam.Value = companyId;
command.Parameters.Add(companyIdParam);

по System.Data.OracleClient

OracleCommand command = new OracleCommand(query, connection);

OracleParameter companyIdParam = command.CreateParameter();
companyIdParam.ParameterName = "I_COMPANYID";
companyIdParam.Direction = ParameterDirection.Input;
companyIdParam.OracleType = OracleType.Number;
companyIdParam.Value = companyId;
command.Parameters.Add(companyIdParam);

Или Oracle.DataAccess.Client

OracleCommand command = new OracleCommand(query, connection);

OracleParameter companyIdParam = command.CreateParameter();
companyIdParam.ParameterName = "companyId";
companyIdParam.Direction = ParameterDirection.Input;
companyIdParam.DbType = DbType.Int32;
companyIdParam.Value = companyId;
command.Parameters.Add(companyIdParam);
...