Как получить значение из VBScript для моего хоста C ++? - PullRequest
0 голосов
/ 07 марта 2019

Я пытаюсь выполнить VBScript из консольного приложения C ++ ATL (не VBS-файл, а просто скрипт, встроенный в мой код) и получить из него строку.

Я пробовал что-то вроде этого:

HRESULT hr = S_OK;
CComVariant result;
EXCEPINFO ei = { };

LPCOLESTR sCmd = L"s = \"something\"\r\n"
"WScript.Echo s\r\n";

hr = spVBScriptParse->ParseScriptText(sCmd, NULL, NULL, NULL, 0, 0, 0, &result, &ei);

std::cout << "got:" << result.cVal << std::endl;

См. Также этот вопрос, чтобы узнать, как его настроить:

Как загрузить и вызвать функцию VBScript изв C ++?

Если я запускаю это, VBScript жалуется на несуществующий объект "WScript".

Я попытался заменить WScript.Echo на MsgBox, и код работает нормально (но, конечно, не возвращает строку).

Я пытался использовать это:

LPCOLESTR sCmd = L"s = \"something\"\r\n"
                  "Set fso = CreateObject (\"Scripting.FileSystemObject\")\r\n"
                  "Set stdout = fso.GetStandardStream (1)\r\n"
                  "stdout.WriteLine s\r\n"

Это записывает мою строку в консоль, где было запущено приложение C ++, но неВернуть строку в мой код.

Как мне получить значение s из скрипта в моем хост-процессе?

Просто чтобы уточнить: я не хочусохранить VBS, а не строку во временном файле.

Цель состоит в том, чтобы хранить все в памяти без доступа к диску.

Я знаю, что могу использовать реестр, но я бы хотел избежатьвысота.Не знаю, доступно ли какое-либо совместное использование памяти для vbscript.

Другая идея - именованные каналы, но я понятия не имею, как разделить ее между c ++ и vbscript.

1 Ответ

0 голосов
/ 08 марта 2019

Просто добавьте второй вызов к ParseScriptText, который оценивает вашу строковую переменную как выражение.

Вы должны передать SCRIPTTEXT_ISEXPRESSION в качестве аргумента dwFlags, чтобы механизм сценариев знал, что вы хотите получить значение выражения.

Это также в официальной документации для ParseScriptText:

https://docs.microsoft.com/en-us/scripting/winscript/reference/iactivescriptparse-parsescripttext

Я протестировал его в Delphi , и он работает как шарм:

procedure TestActiveScripting;
const
  SCRIPTTEXT_ISEXPRESSION = $00000020;
var
  hr: HResult;
  ScriptSite: IActiveScriptSite;
  VBScript: IActiveScript;
  VBScriptParse: IActiveScriptParse;
  res: Variant;
  ei: TExcepInfo;
begin
  // Initialize
  ScriptSite := TSimpleScriptSite.Create as IActiveScriptSite;

  hr := CoCreateInstance(CLSID_VBScript, nil, CLSCTX_INPROC_SERVER, IID_IActiveScript, VBScript);
  hr := VBScript.SetScriptSite(ScriptSite);
  VBScriptParse := VBScript as IActiveScriptParse;
  hr := VBScriptParse.InitNew;

  // Run some scripts
  hr := VBScriptParse.ParseScriptText('s = "something"', nil, nil, nil, 0, 0, 0, @res, ei);
  hr := VBScriptParse.ParseScriptText('s', nil, nil, nil, 0, 0, SCRIPTTEXT_ISEXPRESSION, @res, ei);
  ShowMessage(res);
end;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...