PHP 8.4.2 Released!

PHP і COM

PHP можна використати для доступу до об'єктів COM і DCOM на платформах Win32.

  1. Я зібрав DLL для обчислень. Яким чином запустити цю DLL в PHP?
  2. Що означає "Unsupported variant type: xxxx (0xxxxx)"?
  3. Чи можливо керувати візуальними об'єктами в PHP?
  4. Чи я можу зберігати об'єкт COM в сесії?
  5. Як я можу перехопити помилки COM?
  6. Чи я можу генерувати файли DLL скриптами PHP, так як це робив на Perl?
  7. Що означає "Unable to obtain IDispatch interface for CLSID {xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx}"?
  8. Як мені запускати об'єкти COM з віддаленого сервера?
  9. Я отримую "DCOM is disabled in C:\path...\scriptname.php on line 6", що я можу зробити?
  10. Чи можливо завантажувати/маніпулювати об'єктом ActiveX на сторінці за допомогою PHP?
  11. Чи можливо отримати запущений екземпляр компонента?
  12. Чи є спосіб обробки події, надісланої з об’єкта COM?
  13. Не можу викликати метод об'єкта COM, який реалізує більше ніж один інтерфейс. Що я можу зробити?
  14. Отже, PHP працює з COM, як щодо COM+?
  15. Якщо PHP може керувати об'єктами COM, чи можемо ми уявити використання MTS для керування ресурсами компонентів у поєднанні з PHP?
Я зібрав DLL для обчислень. Яким чином запустити цю DLL в PHP?

Якщо це звичайна DLL, то її поки що не запустити з PHP. Якщо DLL містить COM сервер, ви можете мати доступ до нього, якщо він реалізував інтерфейс IDispatch.

Що означає "Unsupported variant type: xxxx (0xxxxx)"?

Є десятки типів VARIANT та їхніх комбінацій. Більшість з них вже підтримуються, але кілька ще на стадії впровадження. Масиви підтримуються не повністю. Тільки одновимірні індексовані масиви можуть передаватися між PHP та COM. Якщо ви знайшли інші типи, що не підтримуються, повідомте, будь ласка, про них, як про ваду (якщо вже не повідомлено) та надайте якнайбільше інформації.

Чи можливо керувати візуальними об'єктами в PHP?

Загалом так, але оскільки PHP є мовою веб-сценаріїв, її код запускається в контексті вебсервера, тому візуальні об'єкти ніколи не з'являться на робочому столі серверів. Якщо ви, наприклад, використовуєте PHP для написання програм спільно з PHP-GTK, то нема обмежень доступу або керування візуальними об'єктами через COM.

Чи я можу зберігати об'єкт COM в сесії?

Ні, не можете. Екземпляри COM розглядаються як ресурси, тому вони доступні лише в контексті одного сеансу.

Як я можу перехопити помилки COM?

Розширення COM викидає виключення com_exception, які ви можете ловити, щоб визначити і оглянути проблемну частину коду.

Чи я можу генерувати файли DLL скриптами PHP, так як це робив на Perl?

Ні, на жаль на PHP такий інструмент недоступний.

Що означає "Unable to obtain IDispatch interface for CLSID {xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx}"?

Ця помилка може бути з декількох причин:

  • неправильний CLSID
  • необхідна DLL відсутня
  • запитуваний компонент не реалізує інтерфейс IDispatch

Як мені запускати об'єкти COM з віддаленого сервера?

Так само, як і локальні об'єкти. Вам лише треба передати другим параметром конструктору COM IP віддаленої машини.

Переконайтеся, що ви визначили com.allow_dcom=true у вашому php.ini.

Я отримую "DCOM is disabled in C:\path...\scriptname.php on line 6", що я можу зробити?

Відредагуйте ваш php.ini, задавши com.allow_dcom=true.

Чи можливо завантажувати/маніпулювати об'єктом ActiveX на сторінці за допомогою PHP?

Це не має нічого спільного з PHP. Об'єкти ActiveX завантажуються у клієнтський код за запитом документа HTML. Це не стосується скрипту PHP, тому пряма взаємодія на стороні сервера неможлива.

Чи можливо отримати запущений екземпляр компонента?

Це можливо завдяки псевдонімам. Якщо треба отримати численні посилання на той самий екземпляр слова, ви можете створити цей екземпляр, як показано:

<?php
$word
= new COM("C:\docs\word.doc");
?>

Це створить новий екземпляр, якщо запущеного немає, або поверне дескриптор запущеного екземпляра, якщо він доступний.

Чи є спосіб обробки події, надісланої з об’єкта COM?

Ви можете створити обробник подій і прив'язати його, використавши com_event_sink(). Щоб PHP генерував скелет для класу приймача подій, є функція com_print_typeinfo().

Не можу викликати метод об'єкта COM, який реалізує більше ніж один інтерфейс. Що я можу зробити?

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

Отже, PHP працює з COM, як щодо COM+?

COM+ розширює COM платформою для керування компонентами через MTS і MSMQ, але в цьому немає нічого особливого, аби PHP мав підтримку цього продукту.

Якщо PHP може керувати об'єктами COM, чи можемо ми уявити використання MTS для керування ресурсами компонентів у поєднанні з PHP?

PHP сам ще не обробляє транзакції. Таким чином, якщо виникає помилка, відкочування не починається. Якщо ви використовуєте компоненти, які підтримують транзакції, вам треба власноруч реалізувати управління транзакціями.

add a note

User Contributed Notes 3 notes

up
8
Anonymous
19 years ago
Re: The Windows English CHM Sample with MS Word Automation.

I see that $Word->Release() is called after $Word->Quit().
This seems to be erroneous. Actually, $Word->Release() should not have to be called if proper COM garbage collection is taking place. Release() is a C++ construction not used in either Visual Basic or VBScript or even MS-JScript. Just to be sure, however, I ran the sample through php.exe (5.04 CLI on Windows XP SP1 with Office 2003) and got a RPC failed error on the line containing $Word->Release(). The rest of the sample works fine, and the results are as expected. So, I propose 2 scenarios:
1.There is a problem with the documentation (more likely).
2.There is a problem with PHP504 itself, as this problem is reproduced with any COM Automation call, not just Word.
up
6
junk.ghost@virgin dOtt net
20 years ago
It may be obvious to everyone else but...

If you want to write your own COM DLL in MSVC++6 and you want to pass it a string, you need the following in your .idl file:

HRESULT function_name([in] BSTR parameter_name,
[retval, out] BSTR * retval);

retval is the result of your function as a string to be passed back.

BSTR is an unsigned short *, so if you want to use your string with STL string etc. you may need to convert parameters to and from char *.

The burden of my message is that from PHP

$comThing = new COM("comThing.comThing");
print $comThing->function_name("Jeremy");

Jeremy will be marshalled as wide chars, which match BSTR.
up
2
codeslinger at compsalot dot com
17 years ago
in response to item #1 above: "If this is a simple DLL there is no way yet to run it from PHP."

Answer: There are several different packages/add-ons to php that enable low level access to the windows api. One of the most popular of these packages is available at http://www.winbinder.org

Winbinder does have the ability to load a dll and call it's functions. Winbinder also provides a large set of windows apis for creating windows and controls. This is useful for creating stand-alone desktop apps. It is a possible alternative to php-gtk.

I've had mixed results with Winbinder, some things work very well, others are buggy; source code is available. It's worth a look, Evaluate carefully.
To Top