Skip to content

Commit 99df6cd

Browse files
committed
Fix bug passing CustomActionData
Reformat code
1 parent 3b61a52 commit 99df6cd

12 files changed

+544
-227
lines changed

PowerShellActions/CustomAction.cs

+48-61
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,21 @@
11
using System;
2-
using System.Collections.Generic;
32
using System.Text;
4-
using System.Threading;
3+
using System.Web;
54
using System.Xml.Linq;
65
using Microsoft.Deployment.WindowsInstaller;
76

7+
using View = Microsoft.Deployment.WindowsInstaller.View;
8+
89
namespace PowerShellActions
910
{
1011
public class CustomActions
1112
{
13+
public const uint TickIncrement = 10000;
14+
15+
// Specify or calculate the total number of ticks the custom action adds to the length of the ProgressBar
16+
public const uint TotalTicks = TickIncrement * NumberItems;
17+
private const uint NumberItems = 100;
18+
1219
[CustomAction]
1320
public static ActionResult PowerShellFilesImmediate(Session session)
1421
{
@@ -22,26 +29,31 @@ public static ActionResult PowerShellFilesImmediate(Session session)
2229
View view = db.OpenView("SELECT `Id`, `File`, `Arguments` FROM `PowerShellFiles`");
2330
view.Execute();
2431

25-
var data = new CustomActionData();
26-
27-
XDocument doc = new XDocument(new XElement("r"));
32+
var doc = new XDocument(new XDeclaration("1.0", "utf-16", "yes"), new XElement("r"));
2833

2934
foreach (Record row in view)
3035
{
31-
doc.Root.Add(new XElement("d", new XAttribute("Id", row["Id"]), new XAttribute("file", session.Format(row["File"].ToString())), new XAttribute("args", session.Format( row["Arguments"].ToString()))));
36+
// XML comes in with entities already. We need to decode these before putting them back into XML again
37+
var args = HttpUtility.HtmlDecode(session.Format(row["Arguments"].ToString()));
38+
39+
session.Log("args '{0}'", args);
40+
41+
doc.Root.Add(new XElement("d", new XAttribute("Id", row["Id"]), new XAttribute("file", session.Format(row["File"].ToString())), new XAttribute("args", args)));
3242
}
3343

34-
session["PowerShellFilesDeferred"] = doc.ToString();
44+
var cad = new CustomActionData { { "xml", doc.ToString() } };
45+
46+
session["PowerShellFilesDeferred"] = cad.ToString();
3547

3648
// Tell the installer to increase the value of the final total
3749
// length of the progress bar by the total number of ticks in
3850
// the custom action.
39-
Record hProgressRec = new Record(2);
51+
var hProgressRec = new Record(2);
4052

4153
hProgressRec[1] = 3;
42-
hProgressRec[2] = iTotalTicks;
54+
hProgressRec[2] = TotalTicks;
4355
MessageResult iResult = session.Message(InstallMessage.Progress, hProgressRec);
44-
if ((iResult == MessageResult.Cancel))
56+
if (iResult == MessageResult.Cancel)
4557
{
4658
return ActionResult.UserExit;
4759
}
@@ -63,20 +75,19 @@ public static ActionResult PowerShellFilesImmediate(Session session)
6375
public static ActionResult PowerShellFilesDeferred(Session session)
6476
{
6577
session.Log("PowerShellFilesDeferred start");
66-
Record hActionRec = new Record(3);
67-
Record hProgressRec = new Record(3);
78+
var hActionRec = new Record(3);
79+
var hProgressRec = new Record(3);
6880

6981
// Installer is executing the installation script. Set up a
7082
// record specifying appropriate templates and text for
7183
// messages that will inform the user about what the custom
7284
// action is doing. Tell the installer to use this template and
7385
// text in progress messages.
74-
7586
hActionRec[1] = "PowerShellFilesDeferred";
7687
hActionRec[2] = "PowerShell Files";
7788
hActionRec[3] = "[1] of [2], [3]";
7889
MessageResult iResult = session.Message(InstallMessage.ActionStart, hActionRec);
79-
if ((iResult == MessageResult.Cancel))
90+
if (iResult == MessageResult.Cancel)
8091
{
8192
return ActionResult.UserExit;
8293
}
@@ -86,39 +97,38 @@ public static ActionResult PowerShellFilesDeferred(Session session)
8697
hProgressRec[2] = 1;
8798
hProgressRec[3] = 0;
8899
iResult = session.Message(InstallMessage.Progress, hProgressRec);
89-
if ((iResult == MessageResult.Cancel))
100+
if (iResult == MessageResult.Cancel)
90101
{
91102
return ActionResult.UserExit;
92103
}
93104

94105
try
95106
{
96-
var doc = XDocument.Parse(session.CustomActionData.ToString());
107+
string content = session.CustomActionData["xml"];
97108

98-
foreach (var row in doc.Root.Elements("d"))
109+
XDocument doc = XDocument.Parse(content);
110+
111+
foreach (XElement row in doc.Root.Elements("d"))
99112
{
100113
string file = row.Attribute("file").Value;
101114

102115
string arguments = row.Attribute("args").Value;
103116

104-
using (var sr = new System.IO.StreamReader(file))
117+
using (var task = new PowerShellTask(file, arguments, session))
105118
{
106-
string content = sr.ReadToEnd();
107-
108-
using (var task = new PowerShellTask(file, arguments, session))
109-
{
110-
task.Execute();
111-
}
119+
task.Execute();
112120
}
113121
}
122+
114123
return ActionResult.Success;
115124
}
116125
catch (Exception ex)
117126
{
118-
session.Log(ex.Message);
127+
session.Log(ex.ToString());
119128
return ActionResult.Failure;
120129
}
121130
}
131+
122132
[CustomAction]
123133
public static ActionResult PowerShellScriptsImmediate(Session session)
124134
{
@@ -144,12 +154,12 @@ public static ActionResult PowerShellScriptsImmediate(Session session)
144154
// Tell the installer to increase the value of the final total
145155
// length of the progress bar by the total number of ticks in
146156
// the custom action.
147-
Record hProgressRec = new Record(2);
157+
var hProgressRec = new Record(2);
148158

149159
hProgressRec[1] = 3;
150-
hProgressRec[2] = iTotalTicks;
160+
hProgressRec[2] = TotalTicks;
151161
MessageResult iResult = session.Message(InstallMessage.Progress, hProgressRec);
152-
if ((iResult == MessageResult.Cancel))
162+
if (iResult == MessageResult.Cancel)
153163
{
154164
return ActionResult.UserExit;
155165
}
@@ -158,7 +168,7 @@ public static ActionResult PowerShellScriptsImmediate(Session session)
158168
}
159169
catch (Exception ex)
160170
{
161-
session.Log(ex.Message);
171+
session.Log(ex.ToString());
162172
return ActionResult.Failure;
163173
}
164174
finally
@@ -167,40 +177,23 @@ public static ActionResult PowerShellScriptsImmediate(Session session)
167177
}
168178
}
169179

170-
private static void ExtendProgressForCustomAction(Session session, int total)
171-
{
172-
var record = new Record(2);
173-
record[1] = 3;
174-
record[2] = total;
175-
session.Message(InstallMessage.Progress, record);
176-
}
177-
178-
// Specify or calculate the number of ticks in an increment
179-
// to the ProgressBar
180-
public const uint iTickIncrement = 10000;
181-
182-
// Specify or calculate the total number of ticks the custom action adds to the length of the ProgressBar
183-
const uint iNumberItems = 100;
184-
public const uint iTotalTicks = iTickIncrement * iNumberItems;
185-
186-
180+
// Specify or calculate the number of ticks in an increment to the ProgressBar
187181
[CustomAction]
188182
public static ActionResult PowerShellScriptsDeferred(Session session)
189183
{
190-
Record hActionRec = new Record(3);
191-
Record hProgressRec = new Record(3);
184+
var hActionRec = new Record(3);
185+
var hProgressRec = new Record(3);
192186

193187
// Installer is executing the installation script. Set up a
194188
// record specifying appropriate templates and text for
195189
// messages that will inform the user about what the custom
196190
// action is doing. Tell the installer to use this template and
197191
// text in progress messages.
198-
199192
hActionRec[1] = "PowerShellScriptsDeferred";
200193
hActionRec[2] = "PowerShell Scripts";
201194
hActionRec[3] = "[1] of [2], [3]";
202195
MessageResult iResult = session.Message(InstallMessage.ActionStart, hActionRec);
203-
if ((iResult == MessageResult.Cancel))
196+
if (iResult == MessageResult.Cancel)
204197
{
205198
return ActionResult.UserExit;
206199
}
@@ -210,7 +203,7 @@ public static ActionResult PowerShellScriptsDeferred(Session session)
210203
hProgressRec[2] = 1;
211204
hProgressRec[3] = 0;
212205
iResult = session.Message(InstallMessage.Progress, hProgressRec);
213-
if ((iResult == MessageResult.Cancel))
206+
if (iResult == MessageResult.Cancel)
214207
{
215208
return ActionResult.UserExit;
216209
}
@@ -219,7 +212,7 @@ public static ActionResult PowerShellScriptsDeferred(Session session)
219212
{
220213
CustomActionData data = session.CustomActionData;
221214

222-
foreach (KeyValuePair<string, string> datum in data)
215+
foreach (var datum in data)
223216
{
224217
string script = Encoding.Unicode.GetString(Convert.FromBase64String(datum.Value));
225218

@@ -228,20 +221,14 @@ public static ActionResult PowerShellScriptsDeferred(Session session)
228221
task.Execute();
229222
}
230223
}
224+
231225
return ActionResult.Success;
232226
}
233227
catch (Exception ex)
234228
{
235-
session.Log(ex.Message);
229+
session.Log(ex.ToString());
236230
return ActionResult.Failure;
237231
}
238232
}
239-
240-
private static void DisplayWarningMessage(Session session, string message)
241-
{
242-
var record = new Record(0);
243-
record[0] = message;
244-
session.Message(InstallMessage.Warning, record);
245-
}
246233
}
247-
}
234+
}

PowerShellActions/PowerShellActions.csproj

+1
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@
3838
<SpecificVersion>False</SpecificVersion>
3939
<HintPath>..\..\..\Program Files (x86)\Reference Assemblies\Microsoft\WindowsPowerShell\3.0\System.Management.Automation.dll</HintPath>
4040
</Reference>
41+
<Reference Include="System.Web" />
4142
<Reference Include="System.Xml.Linq" />
4243
<Reference Include="Microsoft.CSharp" />
4344
<Reference Include="System.Xml" />

PowerShellActions/PowerShellTask.cs

+14-14
Original file line numberDiff line numberDiff line change
@@ -1,57 +1,57 @@
11
using System;
2-
using System.IO;
32
using System.Management.Automation.Runspaces;
3+
44
using Microsoft.Deployment.WindowsInstaller;
55

66
namespace PowerShellActions
77
{
88
internal class PowerShellTask : IDisposable
99
{
1010
/// <summary>
11-
/// The context that the Windows PowerShell script will run under.
11+
/// The context that the Windows PowerShell script will run under.
1212
/// </summary>
1313
private Pipeline _pipeline;
1414

15-
internal PowerShellTask( string script, Session session )
15+
internal PowerShellTask(string script, Session session)
1616
{
17-
var runspace = RunspaceFactory.CreateRunspace( new WixHost( session ) );
17+
Runspace runspace = RunspaceFactory.CreateRunspace(new WixHost(session));
1818

1919
_pipeline = runspace.CreatePipeline();
20-
_pipeline.Commands.AddScript( script );
20+
_pipeline.Commands.AddScript(script);
2121
_pipeline.Runspace.Open();
22-
_pipeline.Runspace.SessionStateProxy.SetVariable( "session", session );
22+
_pipeline.Runspace.SessionStateProxy.SetVariable("session", session);
2323
}
2424

2525
internal PowerShellTask(string file, string arguments, Session session)
2626
{
27-
var runspace = RunspaceFactory.CreateRunspace( new WixHost( session ) );
27+
Runspace runspace = RunspaceFactory.CreateRunspace(new WixHost(session));
2828

2929
_pipeline = runspace.CreatePipeline();
3030

3131
// http://stackoverflow.com/a/530418/25702
3232
_pipeline.Commands.AddScript(string.Format("& '{0}' {1}", file, arguments));
3333
_pipeline.Runspace.Open();
34-
_pipeline.Runspace.SessionStateProxy.SetVariable( "session", session );
34+
_pipeline.Runspace.SessionStateProxy.SetVariable("session", session);
3535
}
3636

3737
public void Dispose()
3838
{
39-
Dispose( true );
40-
GC.SuppressFinalize( this );
39+
Dispose(true);
40+
GC.SuppressFinalize(this);
4141
}
4242

4343
public bool Execute()
4444
{
45-
var result = _pipeline.Invoke();
45+
_pipeline.Invoke();
4646

4747
return _pipeline.HadErrors;
4848
}
4949

50-
protected virtual void Dispose( bool disposing )
50+
protected virtual void Dispose(bool disposing)
5151
{
52-
if ( disposing )
52+
if (disposing)
5353
{
54-
if ( _pipeline.Runspace != null )
54+
if (_pipeline.Runspace != null)
5555
{
5656
_pipeline.Runspace.Dispose();
5757
_pipeline = null;

0 commit comments

Comments
 (0)