2012-03-07 79 views
5

我已經開始自己學習Innosetup腳本。爲此我創建了一個簡單的C#控制檯應用程序,它從配置文件中讀取一個元素並輸出到控制檯上。如何從Innosetup腳本修改exe.config

<configuration> 
    <appSettings> 
    <add key ="Name" value="Brad Pitt"/> 
    </appSettings> 
</configuration> 

例如:它應通過查詢關鍵屬性「Name」來讀取值。

我想要從Innosetup安裝腳本中寫入.config中的值。

即在安裝過程中我要聚集的名稱(即「布拉德·皮特」在這種情況下),並將其寫入配置文件

<add key ="Name" value="Brad Pitt"/> 

的問題是我如何做到這一點的值,使用一個Pascal腳本或一個標準腳本。

任何指導深深地理解

問候

跋蹉

+0

[Inno Setup修改基於自定義輸入的XML文件的可能的重複] (http://stackoverflow.com/questions/8141886/inno-setup-modify-xml-file-based-on-custom-input) – Deanna 2012-03-07 13:49:29

回答

7

爲了實現這一點,我創建一個簡單的程序,它接受XML文件名作爲輸入。該過程應解析每行並將內容寫入臨時文件。代碼檢查每一行尋找字符串「鍵=‘名稱’」:

if (Pos('key="Name"', strTest) <> 0) 

如果找到匹配,那麼我通過我的期望的變量,它的value是從我的自定義頁面變得替換特定的行。

strTest := ' <add key="Name" value="' + strName + '"/> '; 

這會寫入臨時文件。然後刪除原始的exe.config文件並將temp配置文件重命名爲exe.config文件(從而反映出我需要的更改)。下面是該過程的整個代碼段,也不要忘記從[文件]調用過程,即

[Files] 
Source: "HUS.exe.config"; DestDir: "{app}"; AfterInstall: ConvertConfig('HUS.exe.config') 

代碼段

procedure ConvertConfig(xmlFileName: String); 
var 
    xmlFile: String; 
    xmlInhalt: TArrayOfString; 
    strName: String; 
    strTest: String; 
    tmpConfigFile: String; 
    k: Integer; 
begin 
    xmlFile := ExpandConstant('{app}') + '\' + xmlFileName; 
    tmpConfigFile:= ExpandConstant('{app}') + '\config.tmp'; 
    strName := UserPage.Values[0] +' '+ UserPage.Values[1]; 

    if (FileExists(xmlFile)) then begin 
    // Load the file to a String array 
    LoadStringsFromFile(xmlFile, xmlInhalt); 

    for k:=0 to GetArrayLength(xmlInhalt)-1 do begin 
     strTest := xmlInhalt[k]; 
     if (Pos('key="Name"', strTest) <> 0) then begin 
     strTest := ' <add key="Name" value="' + strName + '"/> '; 
     end; 
     SaveStringToFile(tmpConfigFile, strTest + #13#10, True); 
    end; 

    DeleteFile(xmlFile); //delete the old exe.config 
    RenameFile(tmpConfigFile,xmlFile); 
    end; 
end; 
4

我知道這是一個有點老,但現在這是另一種方法;使用MSXML

procedure UpdateConfig(); 
var 
    XMLDoc, NewNode, RootNode, Nodes, Node: Variant; 
    ConfigFilename, Key: String; 
    i: integer; 

begin 
    ConfigFilename := ExpandConstant('{app}') + '\your-app-name.exe.config'; 

    try 
     XMLDoc := CreateOleObject('MSXML2.DOMDocument'); 
    except 
    RaiseException('MSXML is required to complete the post-installation process.'#13#13'(Error ''' + GetExceptionMessage + ''' occurred)'); 
    end; 

    XMLDoc.async := False; 
    XMLDoc.resolveExternals := False; 
    XMLDoc.load(ConfigFilename); 
    if XMLDoc.parseError.errorCode <> 0 then 
    RaiseException('Error on line ' + IntToStr(XMLDoc.parseError.line) + ', position ' + IntToStr(XMLDoc.parseError.linepos) + ': ' + XMLDoc.parseError.reason); 

    RootNode := XMLDoc.documentElement; 
    Nodes := RootNode.selectNodes('//configuration/appSettings/add'); 
    for i := 0 to Nodes.length - 1 do 
    begin 
    Node := Nodes.Item[i]; 
    if Node.NodeType = 1 then 
    begin 
     key := Node.getAttribute('key'); 
     Case key of 
     'MyValue1' : Node.setAttribute('value', ConfigPage.Values[0]); 
     'MyValue2' : Node.setAttribute('value', ConfigPage.Values[1]); 
     'MyValue3' : Node.setAttribute('value', ConfigPage.Values[2]); 
     end; 
    end; 
    end; 

    XMLDoc.Save(ConfigFilename); 

end; 

乾杯, 馬特

+0

在我的代碼中使用Nodes.Item [i]給我一個「無法導入VARARRAYGET」啓動實際設置時出錯。 – Nyerguds 2013-05-08 12:52:47

+0

對不起,沒關係。錯誤是由於在另一次迭代中不使用.Item而導致的。謝謝你,我的代碼現在工作:) – Nyerguds 2013-05-08 12:58:38

0

僅有貢獻,這裏遵循上述程序的更新,現在接收的參數,與任何屬性被使用:

procedure UpdateConfigKeyValue(ConfigFilename,NodeName,KeyName,Value:String); 
var 
    XMLDoc, NewNode, RootNode, Nodes, Node: Variant; 
    Key: String; 
    i: integer; 
begin 
    try 
     XMLDoc := CreateOleObject('MSXML2.DOMDocument'); 
    except 
    RaiseException('MSXML is required to complete the post-installation process.'#13#13'(Error ''' + GetExceptionMessage + ''' occurred)'); 
    end; 

    XMLDoc.async := False; 
    XMLDoc.resolveExternals := False; 
    XMLDoc.load(ConfigFilename); 
    if XMLDoc.parseError.errorCode <> 0 then 
    RaiseException('Error on line ' + IntToStr(XMLDoc.parseError.line) + ', position ' + IntToStr(XMLDoc.parseError.linepos) + ': ' + XMLDoc.parseError.reason); 

    RootNode := XMLDoc.documentElement; 
    Nodes := RootNode.selectNodes(NodeName); 
    for i := 0 to Nodes.length - 1 do 
    begin 
    Node := Nodes.Item[i]; 
    if Node.NodeType = 1 then 
    begin 
     key := Node.getAttribute('key'); 
     Case key of 
     KeyName : Node.setAttribute('value', Value); 
     end; 
    end; 
    end; 

    XMLDoc.Save(ConfigFilename); 

end; 

用法樣品:

UpdateConfigKeyValue(ConfigPath,'//configuration/appSettings/add','hibernate.connection.data_source',SQLServer);