Passed
Pull Request — master (#244)
by
unknown
01:25
created

create_and_start_task()   A

Complexity

Conditions 2

Size

Total Lines 25
Code Lines 18

Duplication

Lines 25
Ratio 100 %

Importance

Changes 0
Metric Value
cc 2
eloc 18
nop 6
dl 25
loc 25
rs 9.5
c 0
b 0
f 0
1
# -*- coding: utf-8 -*-
2
# Copyright (C) 2018 inovex GmbH
3
#
4
# SPDX-License-Identifier: GPL-3.0-or-later
5
#
6
# This program is free software: you can redistribute it and/or modify
7
# it under the terms of the GNU General Public License as published by
8
# the Free Software Foundation, either version 3 of the License, or
9
# (at your option) any later version.
10
#
11
# This program is distributed in the hope that it will be useful,
12
# but WITHOUT ANY WARRANTY; without even the implied warranty of
13
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
# GNU General Public License for more details.
15
#
16
# You should have received a copy of the GNU General Public License
17
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
18
19
20
def check_args(args):
21
    len_args = len(args.script) - 1
22
    message = """
23
        This script makes an alert scan
24
        It needs two parameters after the script name.
25
26
        1. <sender_email>     -- E-Mail of the sender
27
        2. <receiver_email>   -- E-Mail of the receiver
28
        
29
                Example:
30
            $ gvm-script --gmp-username name --gmp-password pass \
31
ssh --hostname <gsm> scripts/start-multiple-alert-scan.gmp.py <sender_email> <receiver_email>
32
    """
33
    if len_args != 2:
34
        print(message)
35
        quit()
36
37
38
# returns a list containing all port_list names
39
def get_port_list_names(gmp):
40
    res = gmp.get_port_lists()
41
    port_names_list = [""]
42
    for name in res.findall("port_list/name"):
43
        port_names_list.append(str(name.text))
44
    return port_names_list
45
46
47 View Code Duplication
def get_config(gmp, debug=False):
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
48
    # get all configs of the openvas instance
49
    res = gmp.get_configs()
50
51
    # configurable template
52
    template = "fast"
53
54
    # match the config abbreviation to accepted config names
55
    config_list = [
56
        'Full and fast',
57
        'Full and fast ultimate',
58
        'Full and very deep',
59
        'Full and very deep ultimate',
60
        'System Discovery',
61
    ]
62
    template_abbreviation_mapper = {
63
        "fast": config_list[0],
64
        "fast-ulti": config_list[1],
65
        "deep": config_list[2],
66
        "deep-ulti": config_list[3],
67
        "discovery": config_list[4],
68
    }
69
    config_id = "-"
70
    for conf in res.xpath('config'):
71
        cid = conf.xpath('@id')[0]
72
        name = conf.xpath('name/text()')[0]
73
74
        # get the config id of the desired template
75
        if template_abbreviation_mapper.get(template, "-") == name:
76
            config_id = cid
77
            if debug:
78
                print("%s: %s" % (name, config_id))
79
            break
80
    # check for existence of the desired config
81
    if config_id == "-":
82
        print(
83
            "error: could not recognize template '%s'\n"
84
            "valid template names are: %s\n" % (template, config_list)
85
        )
86
        exit()
87
88
    return config_id
89
90
91
def get_target(gmp, debug=False):
92
    # find a targetName
93
    targets = gmp.get_targets()
94
95
    counter = 0
96
    exists = True
97
98
    # iterate over existing targets and find a vacant targetName
99
    while exists:
100
        exists = False
101
        target_name = "targetName%s" % str(counter)
102
        for target in targets.xpath('target'):
103
            name = target.xpath('name/text()')[0]
104
            if name == target_name:
105
                exists = True
106
                break
107
        counter += 1
108
109
    if debug:
110
        print("target name: %s" % target_name)
0 ignored issues
show
introduced by
The variable target_name does not seem to be defined in case the while loop on line 99 is not entered. Are you sure this can never be the case?
Loading history...
111
112
    # iterate over existing port lists and find a vacant name
113
    new_port_list_name = "portlistName"
114
    counter = 0
115
116
    while True:
117
        portlist_name = '%s%s' % (new_port_list_name, str(counter))
118
        if portlist_name not in get_port_list_names(gmp):
119
            break
120
        counter += 1
121
122
    # configurable port string
123
    port_string = "T:80-80"
124
    # create port list
125
    portlist = gmp.create_port_list(portlist_name, port_string)
126
    portlist_id = portlist.xpath('@id')[0]
127
    if debug:
128
        print("Portlist-name:\t%s" % str(portlist_name))
129
        print("Portlist-id:\t%s" % str(portlist_id))
130
131
    # configurable hosts
132
    hosts = ["localhost"]
133
134
    # integrate port list id into create_target
135
    res = gmp.create_target(target_name, hosts=hosts, port_list_id=portlist_id)
136
    return res.xpath('@id')[0]
137
138
139
def get_alerts(gmp, sender_email, recipient_email, debug=False):
140
    # configurable alert name
141
    alert_name = recipient_email
142
143
    # create alert if necessary
144
    alert_object = gmp.get_alerts(filter='name=%s' % alert_name)
145
    alert_id = None
146
    alert = alert_object.xpath('alert')
147 View Code Duplication
    if len(alert) == 0:
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
148
        gmp.create_alert(
149
            alert_name,
150
            event=gmp.types.AlertEvent.TASK_RUN_STATUS_CHANGED,
151
            event_data={'status': 'Done'},
152
            condition=gmp.types.AlertCondition.ALWAYS,
153
            method=gmp.types.AlertMethod.EMAIL,
154
            method_data={
155
                """Task '$n': $e
156
157
After the event $e,
158
the following condition was met: $c
159
160
This email escalation is configured to attach report format '$r'.
161
Full details and other report formats are available on the scan engine.
162
163
$t
164
165
Note:
166
This email was sent to you as a configured security scan escalation.
167
Please contact your local system administrator if you think you
168
should not have received it.
169
""": "message",
170
                "2": "notice",
171
                sender_email: "from_address",
172
                "[OpenVAS-Manager] Task": "subject",
173
                "c402cc3e-b531-11e1-9163-406186ea4fc5": "notice_attach_format",
174
                recipient_email: "to_address",
175
            },
176
        )
177
        alert_object = gmp.get_alerts(filter='name=%s' % recipient_email)
178
        alert = alert_object.xpath('alert')
179
        alert_id = alert[0].get('id', 'no id found')
180
    else:
181
        alert_id = alert[0].get('id', 'no id found')
182
        if debug:
183
            print("alert_id: %s" % str(alert_id))
184
185
    # second configurable alert name
186
    alert_name2 = "%s-2" % recipient_email
187
188
    # create second alert if necessary
189
    alert_object2 = gmp.get_alerts(filter='name=%s' % alert_name2)
190
    alert_id2 = None
191
    alert2 = alert_object2.xpath('alert')
192 View Code Duplication
    if len(alert2) == 0:
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
193
        gmp.create_alert(
194
            alert_name2,
195
            event=gmp.types.AlertEvent.TASK_RUN_STATUS_CHANGED,
196
            event_data={'status': 'Done'},
197
            condition=gmp.types.AlertCondition.ALWAYS,
198
            method=gmp.types.AlertMethod.EMAIL,
199
            method_data={
200
                """Task '$n': $e
201
202
After the event $e,
203
the following condition was met: $c
204
205
This email escalation is configured to attach report format '$r'.
206
Full details and other report formats are available on the scan engine.
207
208
$t
209
210
Note:
211
This email was sent to you as a configured security scan escalation.
212
Please contact your local system administrator if you think you
213
should not have received it.
214
""": "message",
215
                "2": "notice",
216
                sender_email: "from_address",
217
                "[OpenVAS-Manager] Task": "subject",
218
                recipient_email: "to_address",
219
            },
220
        )
221
        alert_object2 = gmp.get_alerts(filter='name=%s' % recipient_email)
222
        alert2 = alert_object2.xpath('alert')
223
        alert_id2 = alert2[0].get('id', 'no id found')
224
    else:
225
        alert_id2 = alert2[0].get('id', 'no id found')
226
        if debug:
227
            print("alert_id2: %s" % str(alert_id2))
228
229
    return (alert_id, alert_id2)
230
231
232
def get_scanner(gmp):
233
    res = gmp.get_scanners()
234
    scanner_ids = res.xpath('scanner/@id')
235
    return scanner_ids[1]  # default scanner
236
237
238 View Code Duplication
def create_and_start_task(
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated in your project.
Loading history...
239
    gmp, config_id, target_id, scanner_id, alerts, debug=False
240
):
241
    # Create the task
242
    tasks = gmp.get_tasks(filter="name~ScanDoneMultipleAlert")
243
    task_name = "ScanDoneMultipleAlert{0}".format(len(tasks.xpath('tasks/@id')))
244
    task_comment = "test comment"
245
    res = gmp.create_task(
246
        task_name,
247
        config_id,
248
        target_id,
249
        scanner_id,
250
        alert_ids=alerts,
251
        comment=task_comment,
252
    )
253
    # Start the task
254
    task_id = res.xpath('@id')[0]
255
    gmp.start_task(task_id)
256
257
    print('Task started: %s' % task_name)
258
259
    if debug:
260
        # Stop the task (for performance reasons)
261
        gmp.stop_task(task_id)
262
        print('Task stopped')
263
264
265
def main(gmp, args):
266
    # pylint: disable=undefined-variable
267
268
    check_args(args)
269
270
    sender_email = args.script[1]
271
    recipient_email = args.script[2]
272
273
    config_id = get_config(gmp)
274
    target_id = get_target(gmp)
275
    alerts = get_alerts(gmp, sender_email, recipient_email)
276
    scanner_id = get_scanner(gmp)
277
278
    create_and_start_task(gmp, config_id, target_id, scanner_id, alerts)
279
280
    print("\nScript finished\n")
281
282
283
if __name__ == '__gmp__':
284
    main(gmp, args)
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable args does not seem to be defined.
Loading history...
Comprehensibility Best Practice introduced by
The variable gmp does not seem to be defined.
Loading history...
285