-
Notifications
You must be signed in to change notification settings - Fork 0
/
harken.ps1
220 lines (190 loc) · 9.12 KB
/
harken.ps1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
<#
.SYNOPSIS
Creates a .NET HTTP Listener as a Windows service which allows PowerShell Commands to be invoked via HTTP calls.
.DESCRIPTION
Creates a .NET HTTP Listener as a Windows service which allows PowerShell Commands to be invoked via HTTP calls.
More information about the .NET HTTP Listener is available here: https://gallery.technet.microsoft.com/scriptcenter/Simple-REST-api-for-b04489f1
.PARAMETER ServiceName
Optional, String: The name you would like to set for the service.
Default: Harken
.PARAMETER HttpListenerURL
Optional, String: The URL you'd like to use for the HTTP Listener. (http://localhost:8888/harken)
Default: harken
.PARAMETER HttpListenerPort
Optional, String: The port number you would like to use for the HTTP Listener.
Default: 8888
.PARAMETER HttpListenerAuth
Optional, String: The authentication method you would like to use for the HTTP Listener.
Valid Options: Anonymous, Basic, Digest, IntegratedWindowsAuthentication, Negotiate, None, Ntlm
Default: IntegratedWindowsAuthentication
More Info: https://msdn.microsoft.com/en-us/library/system.net.authenticationschemes(v=vs.110).aspx
.PARAMETER HttpListenerVersion
Optional, String: The version of HTTPListener you'd like to download.
Default: 1.0.1
.PARAMETER HttpListenerDir
Optional, String: The HttpListener directory.
Default: C:\Windows\System32\WindowsPowerShell\v1.0\Modules
.PARAMETER NssmVersion
Required, String: The version of nssm you'd like to download.
Default: 2.24
.PARAMETER NssmDir
Optional, String: The nssm directory.
Default: C:\nssm\
.PARAMETER NssmArch
Optional, String: The Architecture of nssm you'd like to use.
Valid Options: win32, win64
Default: win64
.EXAMPLE Install Harken with all the defaults.
Install-Harken
.EXAMPLE Uninstall Harken
Uninstall-Harken
.EXAMPLE Using Harken
Visit this URL in your browser http://localhost:8888/harken?command=get-service winmgmt&format=text"
#>
# Function to unzip files.
function Unzip-File {
param(
[Parameter(mandatory=$true)][string]$File,
[Parameter(mandatory=$true)][string]$Destination
)
Write-Host "Extracting file: $File to $Destination"
Add-Type -assembly 'system.io.compression.filesystem'
if (!(Get-ChildItem -Path $Destination)) {
[io.compression.zipfile]::ExtractToDirectory($File, $Destination)
}
Write-Host 'Extraction Complete!'
}
# Function to download files
function Download-File {
param(
[Parameter(mandatory=$true)][string]$URL,
[Parameter(mandatory=$true)][string]$Destination
)
$StartTime = Get-Date
Invoke-WebRequest -Uri $URL -OutFile $Destination
Write-Host "Downloading file from: $URL"
Write-Host "Download took: $((Get-Date).Add(-$StartTime).Millisecond) ms."
Write-Host ' '
}
# Install Harken Function
function Install-Harken {
param(
[Parameter(mandatory=$false)][string]$ServiceName = 'Harken',
[Parameter(mandatory=$false)][string]$HttpListenerURL = 'harken',
[Parameter(mandatory=$false)][string]$HttpListenerPort = 8888,
[Parameter(mandatory=$false)][System.Net.AuthenticationSchemes] $HttpListenerAuth = [System.Net.AuthenticationSchemes]::IntegratedWindowsAuthentication,
[Parameter(mandatory=$false)][string]$HttpListenerVersion = '1.0.1',
[Parameter(mandatory=$false)][string]$HttpListenerDir = 'C:\Windows\System32\WindowsPowerShell\v1.0\Modules\',
[Parameter(mandatory=$false)][string]$NssmVersion = '2.24',
[Parameter(mandatory=$false)][string]$NssmDir = 'C:\nssm\',
[Parameter(mandatory=$false)][ValidateSet('win32','win64')][string]$NssmArch = 'win64'
)
try {
# Create the NssmDir if it does not exist.
if (!(Test-Path -Path $NssmDir -PathType Container)) {
New-Item -Path $NssmDir -ItemType Directory
}
else {
Write-Host ' '
Write-Host ($NssmDir + 'already exists, continuing installation...')
}
# Create temporary download location for files.
$TempDir = 'C:\temp'
if (!(Test-Path -Path $TempDir -PathType Container)) {
New-Item -Path $TempDir -ItemType Directory | Out-Null
}
# Go download the latest nssm (Non-Sucking Service Manager) if it's not already installed.
$NssmURL = ('http://nssm.cc/release/nssm-' + $NssmVersion + '.zip')
$NssmZip = ($TempDir + '\nssm.zip')
Download-File -URL $NssmURL -Destination $NssmZip
# Unzip the download into the $NssmDir location.
Unzip-File -File $NssmZip -Destination $NssmDir
# Create the HttpListenerDir if it does not exist.
if (!(Test-Path -Path $HttpListenerDir -PathType Container)) {
New-Item -Path $HttpListenerDir -ItemType Directory
}
else {
Write-Host ' '
Write-Host ($HttpListenerDir + 'already exists, continuing installation...')
}
# Go download the lastest PowerShell HTTP Listener.
$HttpListenerFileURL = ('https://gallery.technet.microsoft.com/Simple-REST-api-for-b04489f1/file/126130/1/HttpListener_' + $HttpListenerVersion + '.zip')
$HttpListenerZip = ($TempDir + '\HttpListener.zip')
Download-File -URL $HttpListenerFileURL -Destination $HttpListenerZip
# Unzip into the $HttpListenerDir location.
Unzip-File -File $HttpListenerZip -Destination $HttpListenerDir
# Create the .NET HTTPListener as a Windows Service using nssm.exe (Harken)
$NssmCmd = ('install ' + $ServiceName + ' "C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe" "-command "& { Import-Module -Name HTTPListener ; Start-HTTPListener -URL ' + $HttpListenerURL + ' -Port ' + $HttpListenerPort + ' -Auth ' + $HttpListenerAuth + ' }"" ')
switch ($NssmArch) {
# Create and install the service using the 32bit version of nssm.exe
'win32' {
Set-Location ($NssmDir + '\nssm-2.24\' + $NssmArch)
Start-Process -FilePath .\nssm.exe -ArgumentList $NssmCmd -NoNewWindow -Wait
Write-Host "Service $ServiceName installed with $NssmArch nssm.exe"
}
# Create and install the service using the 64bit version of nssm.exe
'win64' {
Set-Location ($NssmDir + '\nssm-2.24\' + $NssmArch)
Write-Host $NssmCmd
Start-Process -FilePath .\nssm.exe -ArgumentList $NssmCmd -NoNewWindow -Wait
Write-Host "Service $ServiceName installed with $NssmArch nssm.exe"
}
}
# Test that the service was successfully installed
if (Get-Service -Name $ServiceName) {
Write-Host "The $ServiceName service was created successfully."
}
# Check if the service is stopped. If it is, start it!
if ((Get-Service -Name $ServiceName).Status -eq 'Stopped') {
Get-Service -Name $ServiceName | Start-Service
}
# Test basic HTTP call using Invoke-RestMethod
# Do some basic clean up.
if (Test-Path -Path $TempDir -PathType Container) {
Remove-Item -Path $TempDir -Recurse -Force
}
# Once everything looks good, notify the user where the service is currently running.
Write-Host ' '
Write-Host '-------------------------------------------------'
Write-Host ('Harken is now running at http://localhost:' + $HttpListenerPort + '/' + $HttpListenerURL )
Write-Host '-------------------------------------------------'
Write-Host ' '
}
catch {
Write-Warning $_
}
}
# Uninstall Harken Function
function Uninstall-Harken {
param(
[Parameter(mandatory=$false)][string]$ServiceName = 'Harken', # ServiceName
[Parameter(mandatory=$false)][string]$NssmDir = 'C:\nssm\', # NssmInstallDir (where you want to install nssm)
[Parameter(mandatory=$false)][ValidateSet('win32','win64')][string]$NssmArch = 'win64' # NssmArch (32 or 64 bit .exe file)
)
try {
# Stop the Service
Get-Service -Name $ServiceName | Stop-Service
# Uninstall the Service
switch ($NssmArch) {
# Uninstall the service using the 32bit version of nssm.exe
'win32' {
Set-Location ($NssmDir + '\nssm-2.24\' + $NssmArch)
$cmd = ('remove ' + $ServiceName + ' confirm')
Start-Process -FilePath .\nssm.exe -ArgumentList $cmd -NoNewWindow
Start-Sleep 5
Write-Host "Service $ServiceName removed with $NssmArch nssm.exe"
}
# Uninstall the service using the 64bit version of nssm.exe
'win64' {
Set-Location ($NssmDir + '\nssm-2.24\' + $NssmArch)
$cmd = ('remove ' + $ServiceName + ' confirm')
Start-Process -FilePath .\nssm.exe -ArgumentList $cmd -NoNewWindow
Start-Sleep 5
Write-Host "Service $ServiceName removed with $NssmArch nssm.exe"
}
}
}
catch {
Write-Warning $_
}
}