Temporary rows added by custom-action are ignored by WriteRegistryValues

好久不见. 提交于 2021-02-07 10:15:41

问题


I'm writing a WIX script.

I have a custom-action that adds rows dynamically to the Registry table:

function AddRegistry() 
{
    var registryView = Session.Database.OpenView("SELECT * FROM Registry");
    registryView.Execute();

    var record = Session.Installer.CreateRecord(6);
    record.StringData(1) = "Unique123456";
    record.IntegerData(2) = 2;
    record.StringData(3) = "Software";
    record.StringData(4) = "my_registry_string";
    record.StringData(5) = "value";
    record.StringData(6) = "MyComponent";

    registryView.Modify(7, record); //InsertTemporary
    registryView.Close();

    return 1; //Ok
}

The custom-action is scheduled to run as "immediate" and before the "WriteRegistryValues" action:

<CustomAction Id="AddRegistry" BinaryKey="CustomActionJS" 
              JScriptCall="AddRegistry" 
              Execute="immediate" Impersonate="no" />

<InstallExecuteSequence>
    <Custom Action="AddRegistry" Before="WriteRegistryValues" />
    <Custom Action="CheckRegistry" After="WriteRegistryValues" />
...
</InstallExecuteSequence>

I've added a 2nd custom-action that enumerates the Registry table, and shows all the entries just find (fixed and temporary).

However, when the WriteRegistryValues is being executed (it is deferred, as far as I understand), it only writes the fixed entries. My dynamic entries are ignored, and not added to the registry.

A fixed Registry entry to the same registry path works fine:

<Component Id="MyComponent">
    <RegistryValue Id="Unique11111" Root="HKLM" Key="Software" 
                   Name="my_fixed_value" Value="my_value" 
                   Action="write" Type="string"/>
</Component>

Any idea what I'm doing wrong?


回答1:


I do it this way using a generic method: (Example is in C# using DTF as ActiveScript Custom Actions such as JScript/VBScript are not a best practice for MSI )

private static void InsertRecord(Session session, string tableName, Object[] objects)
{
  Database db = session.Database; 
  string sqlInsertSring = db.Tables[tableName].SqlInsertString + " TEMPORARY";
  session.Log("SqlInsertString is {0}", sqlInsertSring);
  View view = db.OpenView(sqlInsertSring); 
  view.Execute(new Record(objects)); 
  view.Close(); 
}

Using it looks like

object[] fields = new object[] { .... };
InsertRecord(session, "TableName", fields);



回答2:


OK!

I figured it our - the CA that adds rows to the Registry table must run before InstallValidate (which runs before WriteRegistryValues)

so changing

<Custom Action="AddRegistry" Before="WriteRegistryValues" />

to

<Custom Action="AddRegistry" Before="InstallValidate" />

solved the problem



来源:https://stackoverflow.com/questions/11970453/temporary-rows-added-by-custom-action-are-ignored-by-writeregistryvalues

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!