Обновление таблицы MSI с использованием API программирования MSI
Мне нужно обновить столбец атрибутов в файле MSI. К сожалению, я не могу найти какую-либо документацию (особенно для C++).
Вот фрагмент кода того, что я пытаюсь сделать:
DatabasePtr db = /* opening db succeeds*/
ViewPtr view = db->OpenView(_bstr_t("SELECT Attributes FROM Component"));
view->Execute(NULL);
RecordPtr record=view->Fetch();
record->PutIntegerData(2, record->GetIntegerData(1)|2048);
// I do not exactly understand the next 2 lines
// Should I really call Execute before Modify?
record->Execute(record);
record->Modify(msiViewModifyUpdate, record); //throws a _com_error
Как указано после записи->Modify(...), выдается _com_error с сообщением: IDispatch error #1000? Что это значит. Где я могу найти эти коды ошибок? Это не HRESULTs...
Но более важные вопросы - как правильно обновить запись? Как я могу перебрать все выбранные записи? Выполнение новой выборки и сравнение записи с NULL приводит к бесконечному циклу.
Спасибо за помощь,
Ованес
2 ответа
Решение
Ок, нашел проблему:(
Я открыл базу данных в режиме только для чтения.
Вот разрезанный, который работает:
InstallerPtr installer(TEXT("WindowsInstaller.Installer"));
VARIANT open_flag;
VariantInit(&open_flag);
open_flag.vt = VT_I4;
open_flag.lVal = msiOpenDatabaseModeTransact;
DatabasePtr db = installer->OpenDatabase(msi_path, open_flag);
{
ViewPtr view = db->OpenView(_bstr_t("SELECT Attributes FROM Component"));
view->Execute(NULL);
RecordPtr record=view->Fetch();
if(!record) ... //error handling
while(record)
{
record->PutIntegerData(1, record->GetIntegerData(1)|2048);
record->Modify(msiViewModifyUpdate, record);
record=view->Fetch();
}
} //view->Close() is called implicitly
db->Commit();
Надеюсь, что это помогает кому-то.
Ованес
Использование C++ для этого немного излишне. Прочитайте DTF: