51

Re: WSH: Использование COM-сервера без его регистрации в системе

Хотел бы в качестве некоторого офтопа повторить вопрос The gray Cardinal'a заданный на первой странице: в чём проблема регистрации компонента, если это можно сделать для текущего пользователя, т.е. права админа вроде как не требуются? Мне действительно это неясно.

Насчёт портабельности с манифестами. В варианте max7 нужно иметь при себе wscript.exe. От какой Windows? Ведь они разные должны быть, например, на ХР и на 7. Если же использовать наличный wscript.exe, то нужно манифест для него класть рядом с ним, т.е. в system32. На это разве права не нужны? И что если там уже есть какой-то манифест? Своим перезаписывать? Сливать воедино?

52 (изменено: Flasher, 2012-02-14 08:11:08)

Re: WSH: Использование COM-сервера без его регистрации в системе

YMP, эти вопросы все мне адресованы?
Цель любой портабельности - не нагадить в реестр и системную папку чужой машины, а также запускать скрипты/приложения без необходимости ручной регистрации из консоли или дописи методов с вызовом команд регистрирации/дерегистрации (я уже писал про костыли). К тому же скриптов, создающих объект одного компонента, может быть несколько. Писать для каждого регистрацию, мягко говоря, нерационально.
Ещё, вероятно, предлагаемый способ позволяет обойти чужой файрвол, запрещающий/проверяющий регистрации и записи в системные папки.

В варианте max7 не сказано, что перенос wscript.exe и написание для него манифеста является необходимостью. Нужно бы этот момент прояснить. Версия WSH со времён XP SP3 вроде бы не обновлялась.

53

Re: WSH: Использование COM-сервера без его регистрации в системе

Flasher
Вопросы ко всем, кому есть что сказать, т.к. для меня не совсем ясно, в чём здесь проблема.

Запись данных в реестр вы называете "гадить"? Но ведь реестр для того и предназначен, чтобы программы в него писали и читали из него. Конечно, любое дело можно сделать нормально и через попу, но процедура регистрации ActiveX в реестре довольно проста и неясно, что там можно испортить. По-моему, манифесты сложнее.

Манифест нужен в первую очередь для приложения, т.е. в данном случае wscript.exe. Именно в его манифесте система смотрит, что необходимо для его работы. Так что либо нужно класть для него манифест в system32, либо носить wscript.exe с собой. Насколько взаимозаменяемы его версии, не знаю. Изначально на ХР была версия 5.6, а сейчас у себя вижу такие версии продукта в свойствах:
W7 SP1 5.8.7600.16385
XP SP3 5.7.0.18066

max7 пишет:

Работает примерно так. OS для запускаемого экзешника ищет *.manifest в начале в его ресурсах, если не находит смотрит в той же папке, где он лежит, и если не находит то действует как обычно. А если находит, то действует в соответствии с ним: загружает библиотеки, разрешает имена, и т.д. (в том числе и для activex).

54

Re: WSH: Использование COM-сервера без его регистрации в системе

YMP пишет:

Запись данных в реестр вы называете "гадить"?

Да. У меня на основной работе попытка зарегистрировать ActiveX приводит к полной (часа на полтора) проверке компа Симантеком. То же - при попытке записи в системные папки. Такая корпоративная политика информационной безопасности (блин!). Попытка изменения своих прав или обхода ограничений - к эскалации инцидента до руководителя подразделения с копией руководителю службы безопасности. Поэтому к портабельности, о которой, собственно, и говорил уважаемый Flasher, я отношусь более чем серьёзно.

55 (изменено: Flasher, 2012-02-16 00:03:00)

Re: WSH: Использование COM-сервера без его регистрации в системе

YMP, откровенно говоря, желания вступать в споры, считать это гажением или нет, не было. Каждый сам это для себя решает по обстоятельстам. Я для себя это решил давно. Остальные аргументы приведены (вкл. пояснение Serge Yolkin). Поэтому и обратился к людям, знающим как решать задачу (выделено курсивом). О плюсах портабельности можно поговорить в отдельной теме. Есть уйма пользователей, которые к данной задаче относятся скрупулёзно (я в их числе).
"Сложность" манифестов нисколько не пугает.

YMP пишет:

Так что либо нужно класть для него манифест в system32, либо носить wscript.exe с собой.

Это проверенное утверждение?
Впрочем, даже если так, то пока эта информация ничего не меняет. Я пробовал и совместное использование. Мне (да  не только) всё равно нужны алгоритмы.

56

Re: WSH: Использование COM-сервера без его регистрации в системе

Serge Yolkin
Ничего себе порядки. Спасибо, теперь понятнее.

Flasher
Wscript.exe, ActiveX и манифесты для обоих должны находиться в одной папке.
Каюсь, на 7 до этого не проверял. Оказалось, что системная папка (пробовал SysWOW64, где у меня лежит 32-битный wscript.exe) для этого не годится. Какие-то дополнительные заморочки. В обычной папке работает. Если убрать wscript.exe.manifest — не работает.

57

Re: WSH: Использование COM-сервера без его регистрации в системе

YMP, ясно. А скрипты тоже обязательно должны лежать рядом, или их можно класть в родительскую папку?
И по существу запроса есть что сказать? Или ждём знатоков?

58 (изменено: YMP, 2012-02-15 07:25:43)

Re: WSH: Использование COM-сервера без его регистрации в системе

Скрипты могут лежать где угодно, при условии что запускаются через правильный wscript.exe. ActiveX со своим манифестом может лежать как рядом с wscript.exe, так и в подпапке рядом с wscript.exe, названной именем сборки, как оно указано в манифесте wscript.exe.

Алгоритмы на все случаи жизни я дать не могу, так что ждём знатоков, видимо.

Если будете сами экспериментировать, учтите, что система (по кр. мере 7) где-то кэширует информацию о сборках, что может привести к озадачивающим результатам. Когда я создал подпапку с именем сборки и перенёс туда dll и её манифест, скрипт работать перестал — "не найден указанный модуль". Вторая странность случилась, когда я удалил манифест dll и скрипт продолжал нормально работать, при том что CLSID объекта взять уже было неоткуда. После перелогина всё пришло в норму.

59

Re: WSH: Использование COM-сервера без его регистрации в системе

Насчёт местоположения скриптов я не уточнил. Речь о вызове скрипта не в качестве параметра wscript, а напрямую.

За информацию по кешу спасибо, буду иметь в виду.

60

Re: WSH: Использование COM-сервера без его регистрации в системе

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

Разве что такой трюк: скрипт запускается двойным щелчком на системном wscript.exe и потом запускает сам себя на переносимом wscript.exe и завершается.

61

Re: WSH: Использование COM-сервера без его регистрации в системе

Двойной щелчок у нас давно - Enter или кнопка на тулбаре.
Значит, всё-таки сразу в реестр лезет. Ясно. Насчёт запуска скрипта по запуску wscript не понял. Впрочем, не суть, могу прописывать и с параметром, главное, чтобы работало.
Такой вопрос: wscript.exe вне папки system32 запускается? Диалог выводит?

И не очень понятно, как программа будет взаимодействовать с зарегистрированными компонентами, не отражёнными в манифесте?

62

Re: WSH: Использование COM-сервера без его регистрации в системе

Flasher, да, WScript запускается вполне нормально вне системной папки.
Все на самом деле очень просто. Если необходимые компоненты подключены (указанные в манифесте), то при вызове их в скриптах они запустятся без проблем (что вполне логично). Если же часть компонентов отсутствует в манифесте, то их поиск будет начинаться с реестра, затем через апишный LoadLibrary.

Что касается того, как работать с незарегистрированными компонентами из скриптов, пока решение такое:
1) При запуске скрипта идет проверка нет ли рядом программы-хоста (WScript.exe). В случае отсутствия требуется сгенерировать этот файл (неважно каким путем: копирование из системной папки, закачка с вашего сервера, генерация из тела скрипта).
2) Проверяем, имеется ли рядом с появившимся WScript файл манифеста приложения.
3) В случае если скрипт был запущен из систмной папки, перегружаем его из нашего хоста.
4) Не забываем рядом положить файл ActiveX компонента.

63

Re: WSH: Использование COM-сервера без его регистрации в системе

Flasher
Не понял, о каком диалоге речь? В остальном JSman уже ответил.

Про запуск я вот что имел в виду: при двойном щелчке или Enter на файле скрипта будет запущен wscript.exe, который прописан в реестре, т.е. находящийся в system32. Скрипт может это определить. После этого он запускает wscript.exe, который вы носите с собой, передав ему в качестве параметра путь к самому себе, а сам после этого завершается.

Определить, как именно он запущен, скрипт может по наличию или отсутствию собственных параметров. При прямом запуске никаких параметров скрипту не передаётся, а когда он потом сам себя запустит на "своём" wscript.exe, он может сам себе передать какой-то параметр, сигнализирующий об этом.

Т.е. скрипт при запуске проверяет, переданы ли ему параметры. Если нет, значит, он запущен двойным кликом. Если да, значит, он запущен своей предыдущей копией уже на своём wscript.exe.

64

Re: WSH: Использование COM-сервера без его регистрации в системе

YMP пишет:

Определить, как именно он запущен, скрипт может по наличию или отсутствию собственных параметров. При прямом запуске никаких параметров скрипту не передаётся, а когда он потом сам себя запустит на "своём" wscript.exe, он может сам себе передать какой-то параметр, сигнализирующий об этом.

Передавать какой-то параметр - избыточно и нерационально. Достаточно а проверять способ своего запуска, например:


if ( WScript.FullName.match(/system32/i) ) {

	// получить полный путь до самого себя
	var path = WScript.ScriptFullName.replace(/[^\\]+$/, '');

	// получить список аргументов, переданных скрипту в момент запуска
	var args = <...>

	// запустить собственную копию wscript, который находится рядом со скриптом
	// аргументы командной строки передаются аналогично
	<...> .Run(path + 'wscript.exe ' + WScript.ScriptFullName + args);
	WScript.Quit();
}
( 2 * b ) || ! ( 2 * b )

65 (изменено: Flasher, 2012-02-16 00:43:15)

Re: WSH: Использование COM-сервера без его регистрации в системе

JSman пишет:

Flasher, да, WScript запускается вполне нормально вне системной папки.

Я пытаюсь запустить из другой папки, выдаёт:

Не удалось запустить приложение, поскольку его параллельная конфигурация неправильна. Дополнительные сведения содержатся в журнале событий приложений или используйте программу командной строки sxstrace.exe для получения дополнительных сведений.

JSman пишет:

Все на самом деле очень просто. Если необходимые компоненты подключены (указанные в манифесте), то при вызове их в скриптах они запустятся без проблем (что вполне логично).

Да, если манифест составлен правильно, что я и ставлю на повестку. Можете написать рабочий манифест с пояснениями нюансов (хотя бы не отражённых в топике) для WSHExtra, например?

JSman пишет:

Если же часть компонентов отсутствует в манифесте, то их поиск будет начинаться с реестра, затем через апишный LoadLibrary.

Так ли это? Ведь мы запускаем wscript с другим манифестом, скрипт же ему передаётся в качестве параметра.

JSman пишет:

Что касается того, как работать с незарегистрированными компонентами из скриптов, пока решение такое:
1) При запуске скрипта идет проверка нет ли рядом программы-хоста (WScript.exe).

Так, стоп, тут пишут, что ничего рядом не проверяется и сразу сопоставляются данные с реестром (HKCR\VBSFile\Shell\Open\Command). Так проверяет рядом или нет?

JSman пишет:

2) Проверяем, имеется ли рядом с появившимся WScript файл манифеста приложения.
3) В случае если скрипт был запущен из систмной папки, перегружаем его из нашего хоста.

Всё это видится лишним. Проще передавать через параметр.


YMP пишет:

Flasher
Не понял, о каком диалоге речь?

О таком.

YMP пишет:

После этого он запускает wscript.exe, который вы носите с собой, передав ему в качестве параметра путь к самому себе, а сам после этого завершается.

Понял.

66

Re: WSH: Использование COM-сервера без его регистрации в системе

Flasher
WshExtra я не смог зарегистрировать у себя на W7 — какая-то ошибка в DllRegisterServer.
Но с манифестами запустить удалось.

WshExtraAsm.manifest

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">

<assemblyIdentity
    type="win32"
    name="WshExtraAsm"
    version="1.0.0.1" />

<file name="WshExtra.dll" hash="bbf52114179d1f3d871674198abaac69ec61c4ff" hashalg="SHA1">
    <typelib
        tlbid="{CD1572B0-0C22-490C-B12C-F053986EFE69}"
        version="1.0"
        helpdir="" />
    <comClass
        clsid="{CB65F84A-BA77-4AD6-9882-B5FD20471CBF}"
        progid="WshExtra.Clipboard"
        threadingModel="Apartment" />
    <comClass
        clsid="{D199C0CE-78E8-4DE2-B863-CCDC022A2FCA}"
        progid="WshExtra.FileChooser"
        threadingModel="Apartment" />
    <comClass
        clsid="{AA35C1FF-4FE4-4357-83A2-488AC609DC1B}"
        progid="WshExtra.FileQuery"
        threadingModel="Apartment" />
 </file>

</assembly>

wscript.exe.manifest

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">

<assemblyIdentity
    type="win32"
    name="wscript.exe"
    version="1.0.0.0" /> 

<dependency>
    <dependentAssembly>
        <assemblyIdentity
            type="win32"
            name="WshExtraAsm"
            version="1.0.0.1" />
    </dependentAssembly>
</dependency>

 </assembly>

67

Re: WSH: Использование COM-сервера без его регистрации в системе

YMP
Это всё здорово, конечно. Но меня, как я уже писал, интересует не конечный результат, а алгоритм получения данных и правки. Сейчас, например, проверил SHA1 у WshExtra.dll через ТС, так он другой показывает, нежели тут написан. CRC вообще обязательно указывать? Вроде бы без них работает. Я ещё обратил внимание, что если в wscript.exe.manifest есть лишняя зависимость, или в её теле допущена ошибка, то exe-шник не будет работать вне зависимости от выбранного компонента в скрипте.
Также я пока не понял, почему tlbid у comClass опущены, хотя генерируются? Откуда взялся элемент <typelib/>? И я так понял из названия, что написание WshExtra.sxs необязательно, хотя в описании написано.
Поймал момент с кешированием. нужно делать вынужденную ошибку в манифесте wscript, чтобы по новой перечитывалось.
В общем, нужен какой-то внятный пересказ действий.
И ещё интересно, как быть с компонентапи в виде exe.

68

Re: WSH: Использование COM-сервера без его регистрации в системе

Flasher
Это всё понятно, но я в этой области не знаток. Знатоков мы пока что ждём, а тем временем можно и самим поэкспериментировать. Может, они вообще не появятся.

hash — необязательный атрибут. Я его получил через mt.exe — это консольная программка из Windows 7 SDK, предназначенная для работы с манифестами. Вообще от неё толку мало, использовал только для hash. Почему через ТС он другой, не знаю. Я WshExtra скачивал отсюда.

tlbid у comClass — необязательный атрибут. Поскольку без них работает, то зачем они? typelib я вписал, потому что без него не работало. Взял его в реестре, как и clsid и progid. На 7 у меня dll не хотела регистрироваться, поэтому я её зарегил на виртуалке в ХР и посмотрел в реестр.

Если манифест не встроен в саму dll в виде ресурса, а лежит рядом отдельным файлом, то название сборки и манифеста должно отличаться от имени dll, по крайней мере так написано у майкрософта. Поэтому я добавил Asm, а у max7, видимо, по той же причине добавлено .sxs.

Вы первоисточник-то читали? Там указано, какие атрибуты обязательны, а какие нет.

69

Re: WSH: Использование COM-сервера без его регистрации в системе

WshExtra я, что логично, тоже отсюда скачивал. Без tlbid работает ровно как и без hash, в то время как последний был заействован. Первое экспериментальным путём выявлено?
А в реестре какой куст? Я просто утилитами пользуюсь, не в курсе. Regsvr42 не сгенерировал typelib.

Первоисточник не видел, с английским не очень (особенно, когда речь о подобных заморочках). За наводку спасибо, таблица уже больше проясняет. Посмотрим, что кто ещё полезного скажет вдовесок.

70

Re: WSH: Использование COM-сервера без его регистрации в системе

Flasher пишет:

Без tlbid работает ровно как и без hash, в то время как последний был заействован. Первое экспериментальным путём выявлено?

Необязательность tlbid? В той же таблице видно. Я пробовал их вставлять, когда не работало даже с typelib. Но это опять из-за кэша оказалось, так что потом убрал.

А в реестре какой куст?

Если речь о TypeLib, то путь такой: в HKEY_CLASSES_ROOT ищем ProgID компонента, например, WshExtra.Clipboard. Там узнаём его CLSID — {CB65F84A-BA77-4AD6-9882-B5FD20471CBF}. Потом ищем раздел с именем этого CLSID — HKEY_CLASSES_ROOT\CLSID\{CB65F84A-BA77-4AD6-9882-B5FD20471CBF}. Там есть подраздел TypeLib, из которого и узнаём её CLSID. Потом ищем раздел уже с именем её CLSID и там узнаём её версию, т.к. это обязательный атрибут. helpdir тоже обязателен, но разрешается поставить пустую строку.

71

Re: WSH: Использование COM-сервера без его регистрации в системе

YMP пишет:

Там есть подраздел TypeLib

А если нет этого подраздела при регистрации какой-то библиотеки, как tlbid генерировать?

Mt.exe, Pktextract.exe и Manifestchk.vbs без SDK будут работать? Можете выложить?

72

Re: WSH: Использование COM-сервера без его регистрации в системе

Если подраздела нет, значит и библиотеки типов у ActiveX нет, он без неё работает. Соответственно и в манифесте ничего писать не надо.

Работать будут, наверно. Лучше напишите мне на почту (из профиля), я вышлю. Но manifestchk.vbs у меня отсутствует — возможно, он больше не нужен, т.к. mt.exe имеет ключ -validate_manifest.

73 (изменено: Flasher, 2012-02-17 08:45:08)

Re: WSH: Использование COM-сервера без его регистрации в системе

Не знаю. Беру dsofile (нет typelib). Пишу dsofile.sxs.manifest:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
<assemblyIdentity type="win32" name="dsofile.sxs" version=" 2.1.0.0" />
  <file name="dsofile.dll">
    <comClass
        clsid="{58968145-CF05-4341-995F-2EE093F6ABA3}"
        progid="DSOFile.OleDocumentProperties"
        threadingModel="Apartment" />
  </file>
</assembly>

Пишу wscript.exe.manifest:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">

<assemblyIdentity
  type="win32"
  name="wscript.exe"
  version="1.0.0.0" /> 

  <dependency>
          <dependentAssembly>
              <assemblyIdentity
                  type="win32"
                  name="dsofile.sxs"
                  version="2.1.0.0" />
          </dependentAssembly>
  </dependency>

</assembly>

Вызываю скрипт по wscript.exe Path

Set DSO = CreateObject("DSOFile.OleDocumentProperties")

Ругается.

А что мне писать на почту? Сразу мне и пишите ссылки через профиль.

74

Re: WSH: Использование COM-сервера без его регистрации в системе

Письмо от вас нужно, чтобы я узнал ваш email и выслал на него эти программки. Выкладывать их я не буду.

В ResHacker'e однако видно ресурс TYPELIB.
В хексредакторе видно строчку TypeLib\{58968145-CF00-4341-995F-2EE093F6ABA3}. Может, всё-таки есть? Да и как именно ругается, тоже лучше процитировать.

75

Re: WSH: Использование COM-сервера без его регистрации в системе

А разве при написании отсюда нельзя сразу отправить ссылки мне на почту? Я же тоже почты не знаю. Тут форма отправки для всех едина.

Ругается так же, как в #65. Редакторы ресурсов-то показывают, но регистрация ничего не даёт. В Hex тоже
ничего не вижу.