Skip to content

Commit

Permalink
Merge branch 'develop' into develop
Browse files Browse the repository at this point in the history
  • Loading branch information
tpurschke committed Sep 14, 2024
2 parents 0bb575b + c9bcdd6 commit 314e1d8
Show file tree
Hide file tree
Showing 56 changed files with 294 additions and 128 deletions.
16 changes: 16 additions & 0 deletions CODING_GUIDELINES_FRONTEND.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@

# Code Guidelines


## General
- Close your tag - Leaving some tags open is simply a bad practice. Only self-closing tags are valid. Normal elements can never have self-closing tags.
- Don't use inline styles(if possible) - When creating your markup, do not use inline styling because it would be very hard to override these styles in case you need to.
- Try not to use "!important" - Using the !important declaration is often considered bad practice because it has side effects that mess with one of CSS's core mechanisms: specificity. In many cases, using it could indicate poor CSS architecture.

## Components
- Organize files and components in a folder structure like this. This makes it easy to find the code related to a page, without having to browse the entire file explorer. Try, as much as possible, to respect the SOLID principles. Mainly by creating autonomous and extensible components: inject the smallest possible service or parameter, manage all the possibilities offered by the component. For example, a data modification page should display the data, check their values and save the data at the end of the process.

## UI
# Responsiveness
- Use the bootstrap grid and it's column classes to have easy and responsive design. [Bootstrap](https://getbootstrap.com/docs/5.3/layout/columns/)
- Decide if you want to develop mobile or desktop design first and test respectively.
3 changes: 3 additions & 0 deletions documentation/revision-history-develop.md
Original file line number Diff line number Diff line change
Expand Up @@ -222,3 +222,6 @@ bugfix release:
- workflow: external state handling
- fix config value
- remove uniqueness of owner names

# 8.3.2 - 09.09.2024 DEVELOP
- Added welcome message and settings
2 changes: 1 addition & 1 deletion inventory/group_vars/all.yml
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
### general settings
product_version: "8.3.1"
product_version: "8.3.2"
ansible_user: "{{ lookup('env', 'USER') }}"
ansible_become_method: sudo
ansible_python_interpreter: /usr/bin/python3
Expand Down
2 changes: 2 additions & 0 deletions roles/database/files/sql/creation/fworch-fill-stm.sql
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,7 @@ insert into config (config_key, config_value, config_user) VALUES ('impChangeNot
insert into config (config_key, config_value, config_user) VALUES ('impChangeNotifyStartAt', '00:00:00', 0);

insert into config (config_key, config_value, config_user) VALUES ('extTicketSystems', '[{"Url":"","TicketTemplate":"{\"ticket\":{\"subject\":\"@@TICKET_SUBJECT@@\",\"priority\":\"@@PRIORITY@@\",\"requester\":\"@@ONBEHALF@@\",\"domain_name\":\"\",\"workflow\":{\"name\":\"@@WORKFLOW_NAME@@\"},\"steps\":{\"step\":[{\"name\":\"Erfassung des Antrags\",\"tasks\":{\"task\":{\"fields\":{\"field\":[@@TASKS@@]}}}}]}}}","TasksTemplate":"{\"@xsi.type\":\"multi_access_request\",\"name\":\"GewünschterZugang\",\"read_only\":false,\"access_request\":{\"order\":\"AR1\",\"verifier_result\":{\"status\":\"notrun\"},\"use_topology\":true,\"targets\":{\"target\":{\"@type\":\"ANY\"}},\"users\":{\"user\":@@USERS@@},\"sources\":{\"source\":@@SOURCES@@},\"destinations\":{\"destination\":@@DESTINATIONS@@},\"services\":{\"service\":@@SERVICES@@},\"action\":\"@@ACTION@@\",\"labels\":\"\"}},{\"@xsi.type\":\"text_area\",\"name\":\"Grund für den Antrag\",\"read_only\":false,\"text\":\"@@REASON@@\"},{\"@xsi.type\":\"drop_down_list\",\"name\":\"Regel Log aktivieren?\",\"selection\":\"@@LOGGING@@\"},{\"@xsi.type\":\"date\",\"name\":\"Regel befristen bis:\"},{\"@xsi.type\":\"text_field\",\"name\":\"Anwendungs-ID\",\"text\":\"@@APPID@@\"},{\"@xsi.type\":\"checkbox\",\"name\":\"Die benötigte Kommunikationsverbindung ist im Kommunikationsprofil nach IT-Sicherheitsstandard hinterlegt\",\"value\":@@COM_DOCUMENTED@@},{\"@xsi.type\":\"drop_down_list\",\"name\":\"Expertenmodus: Exakt wie beantragt implementieren (Designervorschlag ignorieren)\",\"selection\":\"Nein\"}"}]', 0);
insert into config (config_key, config_value, config_user) VALUES ('welcomeMessage', '', 0);

INSERT INTO "report_format" ("report_format_name") VALUES ('json');
INSERT INTO "report_format" ("report_format_name") VALUES ('pdf');
Expand Down Expand Up @@ -268,6 +269,7 @@ insert into stm_obj_typ (obj_typ_id,obj_typ_name) VALUES (16,'gsn_handover_group
insert into stm_obj_typ (obj_typ_id,obj_typ_name) VALUES (17,'voip_sip');
insert into stm_obj_typ (obj_typ_id,obj_typ_name) VALUES (18,'simple-gateway');
insert into stm_obj_typ (obj_typ_id,obj_typ_name) VALUES (19,'external-gateway');
insert into stm_obj_typ (obj_typ_id,obj_typ_name) VALUES (20,'voip'); -- general voip object replacing old specific ones and including CpmiVoipSipDomain

insert into stm_action (action_id,action_name) VALUES (1,'accept'); -- cp, fortinet
insert into stm_action (action_id,action_name) VALUES (2,'drop'); -- cp
Expand Down
5 changes: 5 additions & 0 deletions roles/database/files/sql/idempotent/fworch-texts.sql
Original file line number Diff line number Diff line change
Expand Up @@ -1831,6 +1831,8 @@ INSERT INTO txt VALUES ('sessionTimeoutNoticePeriod', 'German','Benachrichtigung
INSERT INTO txt VALUES ('sessionTimeoutNoticePeriod', 'English','Warning before session timeout (in minutes)');
INSERT INTO txt VALUES ('uiHostName', 'German', 'Hostname der UI');
INSERT INTO txt VALUES ('uiHostName', 'English', 'UI Hostname');
INSERT INTO txt VALUES ('welcomeMessage', 'German', 'Willkommensnachricht');
INSERT INTO txt VALUES ('welcomeMessage', 'English', 'Welcome Message');
INSERT INTO txt VALUES ('maxMessages', 'German', 'Max Anzahl Nachrichten');
INSERT INTO txt VALUES ('maxMessages', 'English', 'Max number of messages');
INSERT INTO txt VALUES ('messageViewTime', 'German', 'Nachrichten-Anzeigedauer (in Sekunden)');
Expand Down Expand Up @@ -6219,3 +6221,6 @@ INSERT INTO txt VALUES ('H9053', 'English', 'The assigned modeller can reject th
<li>If configured by the administrator (<a href="/help/workflow/actions">Actions</a>), the interface can also be rejected inside the workflow request.</li>
</ul>
');

INSERT INTO txt VALUES ('H9054', 'German', 'Nachricht die auf der Anmeldeseite angezeigt werden soll.');
INSERT INTO txt VALUES ('H9054', 'English', 'Message that is displayed on Login Page.');
1 change: 1 addition & 0 deletions roles/database/files/upgrade/8.3.2.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
insert into config (config_key, config_value, config_user) VALUES ('welcomeMessage', '', 0) ON CONFLICT DO NOTHING;
4 changes: 3 additions & 1 deletion roles/importer/files/importer/checkpointR8x/cp_const.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,9 @@
svc_obj_table_names = group_svc_obj_types + simple_svc_obj_types + [ 'CpmiAnyObject' ]
# usr_obj_table_names : do not exist yet - not fetchable via API

api_obj_types = nw_obj_table_names + svc_obj_table_names # all obj table names to look at during import
simple_user_obj_types = ['users']

api_obj_types = nw_obj_table_names + svc_obj_table_names + simple_user_obj_types # all obj table names to look at during import

cp_specific_object_types = [ # used for fetching enrichment data via "get object" separately (no specific API call)
'simple-gateway', 'simple-cluster', 'CpmiVsClusterNetobj', 'CpmiVsxClusterNetobj', 'CpmiVsxClusterMember', 'CpmiVsNetobj',
Expand Down
4 changes: 2 additions & 2 deletions roles/importer/files/importer/checkpointR8x/cp_getter.py
Original file line number Diff line number Diff line change
Expand Up @@ -224,7 +224,7 @@ def get_layer_from_api_as_dict (api_v_url, sid, show_params_rules, layerUid=None
raise Exception ( "get_nat_rules_from_api - rulebase does not contain to field, get_rulebase_chunk_from_api found garbled json " + str(rulebase))

# adding inline and domain layers (if they exist)
add_inline_layers (current_layer_json, api_v_url, sid, show_params_rules)
add_inline_layers (current_layer_json, api_v_url, sid, show_params_rules, nativeConfig=nativeConfig)

return current_layer_json

Expand All @@ -235,7 +235,7 @@ def add_inline_layers (rulebase, api_v_url, sid, show_params_rules, access_type=
for chunk in rulebase['layerchunks']:
if 'rulebase' in chunk:
for rules_chunk in chunk['rulebase']:
add_inline_layers(rules_chunk, api_v_url, sid, show_params_rules)
add_inline_layers(rules_chunk, api_v_url, sid, show_params_rules, nativeConfig=nativeConfig)
else:
if 'rulebase' in rulebase:
rulebase_idx = 0
Expand Down
22 changes: 5 additions & 17 deletions roles/importer/files/importer/checkpointR8x/cp_rule.py
Original file line number Diff line number Diff line change
Expand Up @@ -171,15 +171,10 @@ def parse_single_rule(nativeRule, rulebase, layer_name, import_id, rule_num, par
rule_time = list_delimiter.join(timeObjects.values()) # only considering the first time object

# starting with the non-chunk objects
if 'name' in nativeRule and nativeRule['name'] != '':
rule_name = nativeRule['name']
else:
rule_name = None
rule_name = nativeRule.get('name', None)

# new in v8.0.3:
rule_custom_fields = None
if 'custom-fields' in nativeRule:
rule_custom_fields = nativeRule['custom-fields']
rule_custom_fields = nativeRule.get('custom-fields', None)

if 'meta-info' in nativeRule and 'last-modifier' in nativeRule['meta-info']:
rule_last_change_admin = nativeRule['meta-info']['last-modifier']
Expand All @@ -197,17 +192,10 @@ def parse_single_rule(nativeRule, rulebase, layer_name, import_id, rule_num, par
parent_rule_uid = None

# new in v5.5.1:
if 'rule_type' in nativeRule:
rule_type = nativeRule['rule_type']
else:
rule_type = 'access'
rule_type = nativeRule.get('rule_type', 'access')

if 'comments' in nativeRule:
if nativeRule['comments'] == '':
comments = None
else:
comments = nativeRule['comments']
else:
comments = nativeRule.get('comments', None)
if comments == '':
comments = None

if 'hits' in nativeRule and 'last-date' in nativeRule['hits'] and 'iso-8601' in nativeRule['hits']['last-date']:
Expand Down
21 changes: 16 additions & 5 deletions roles/importer/files/importer/checkpointR8x/cp_user.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
import json
# from checkpointR8x.cp_getter import ParseUidToName

def collect_users_from_rule(rule, users, objDict):
def collect_users_from_rule(rule, users): #, objDict):
if 'rule-number' in rule: # standard rule
logger = getFwoLogger()
if 'type' in rule and rule['type'] != 'place-holder':
Expand All @@ -17,18 +17,18 @@ def collect_users_from_rule(rule, users, objDict):
user_name = src['name']
user_uid = src['uid']
user_typ = 'group'
user_comment = src['comments']
user_comment = src.get('comments', None)
user_color = src['color']
if 'users' in src:
user_typ = 'simple'
elif src['type'] == 'LegacyUserAtLocation':
user_str = src["name"]
user_ar = user_str.split('@')
user_name = user_ar[0]
user_uid = src["userGroup"]
user_uid = src.get('userGroup', None)
user_typ = 'group'
user_comment = src['comments']
user_color = src['color']
user_comment = src.get('comments', None)
user_color = src.get('color', None)
else:
break
if user_comment == '':
Expand Down Expand Up @@ -60,4 +60,15 @@ def collect_users_from_rulebase(rulebase, users):
def parse_user_objects_from_rulebase(rulebase, users, import_id):
collect_users_from_rulebase(rulebase, users)
for user_name in users.keys():
# TODO: get user info via API
userUid = getUserUidFromCpApi(user_name)
# finally add the import id
users[user_name]['control_id'] = import_id



def getUserUidFromCpApi (userName):
# show-object with UID
# dummy implementation returning the name as uid
return userName

2 changes: 1 addition & 1 deletion roles/importer/files/importer/checkpointR8x/fwcommon.py
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ def get_config(config2import, full_config, current_import_id, mgm_details, limit

cp_network.normalize_network_objects(full_config, config2import, current_import_id, mgm_id=mgm_details['id'])
cp_service.normalize_service_objects(full_config, config2import, current_import_id)
#parse_users_from_rulebases(full_config, full_config['rulebases'], full_config['users'], config2import, current_import_id)
parse_users_from_rulebases(full_config, full_config['rulebases'], full_config['users'], config2import, current_import_id)
config2import.update({'rules': cp_rule.normalize_rulebases_top_level(full_config, current_import_id, config2import) })
if not parsing_config_only: # get config from cp fw mgr
logout_cp("https://" + mgm_details['hostname'] + ":" + str(mgm_details['port']) + "/web_api/", sid)
Expand Down
4 changes: 2 additions & 2 deletions roles/importer/files/importer/common.py
Original file line number Diff line number Diff line change
Expand Up @@ -365,14 +365,14 @@ def get_config_from_api(importState, full_config_json, config2import, import_tmp
importState.ErrorString += " login failed: mgm_id=" + str(importState.MgmDetails.Id) + ", mgm_name=" + importState.MgmDetails.Name + ", " + e.message
importState.ErrorCount += 1
logger.error(importState.ErrorString)
fwo_api.delete_import(importState.FwoConfig['fwo_api_base_url'], importState) # deleting trace of not even begun import
fwo_api.delete_import(importState) # deleting trace of not even begun import
importState.ErrorCount = fwo_api.complete_import(importState)
raise FwLoginFailed(e.message)
except ImportRecursionLimitReached as e:
importState.ErrorString += " recursion limit reached: mgm_id=" + str(importState.MgmDetails.Id) + ", mgm_name=" + importState.MgmDetails.Name + ", " + e.message
importState.ErrorCount += 1
logger.error(importState.ErrorString)
fwo_api.delete_import(importState.FwoConfig['fwo_api_base_url'], importState.Jwt, importState.ImportId) # deleting trace of not even begun import
fwo_api.delete_import(importState.Jwt) # deleting trace of not even begun import
importState.ErrorCount = fwo_api.complete_import(importState)
raise ImportRecursionLimitReached(e.message)
except:
Expand Down
1 change: 1 addition & 0 deletions roles/importer/files/importer/fwo_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -214,6 +214,7 @@ def readMainKey(filePath=fwo_const.mainKeyFile):
return mainKey


# this mgm field is used by mw dailycheck scheduler
def log_import_attempt(fwo_api_base_url, jwt, mgm_id, successful=False):
now = datetime.datetime.now().isoformat()
query_variables = { "mgmId": mgm_id, "timeStamp": now, "success": successful }
Expand Down
2 changes: 1 addition & 1 deletion roles/importer/files/importer/import-main-loop.py
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@ def stop(self):
if not skipping and mgm_details["deviceType"]["id"] in (9, 11, 17, 22, 23, 24): # only handle CPR8x Manager, fortiManager, Cisco MgmCenter, Palo Panorama, Palo FW, FortiOS REST
logger.debug("import-main-loop: starting import of mgm_id=" + id)
try:
import_result = import_management(mgm_id=id, debug_level_in=debug_level,
import_result = import_management(mgmId=id, debug_level_in=debug_level,
clearManagementData=args.clear, force=args.force, limit=str(api_fetch_limit))
except (FwoApiFailedLockImport, FwLoginFailed):
pass # minor errors for a single mgm, go to next one
Expand Down
1 change: 1 addition & 0 deletions roles/lib/files/FWO.Api.Client/Data/WfReqTaskBase.cs
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ public struct AdditionalInfoKeys
{
public const string ConnId = "ConnId";
public const string ReqOwner = "ReqOwner";
public const string GrpName = "GrpName";
}

public class WfReqTaskBase : WfTaskBase
Expand Down
3 changes: 3 additions & 0 deletions roles/lib/files/FWO.Config.Api/Data/ConfigData.cs
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,9 @@ public class ConfigData : ICloneable
[JsonProperty("uiHostName"), JsonPropertyName("uiHostName")]
public string UiHostName { get; set; } = "http://localhost:5000";

[JsonProperty("welcomeMessage"), JsonPropertyName("welcomeMessage")]
public string WelcomeMessage { get; set; } = "";

// [JsonProperty("maxMessages"), JsonPropertyName("maxMessages"), UserConfigData]
// public int MaxMessages { get; set; } = 3;

Expand Down
2 changes: 2 additions & 0 deletions roles/lib/files/FWO.Report/ReportAppRules.cs
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,7 @@ private async Task GetAppServers(ApiConnection apiConnection)
{
relevantObjects.Add(obj);
found = true;
break;
}
}
}
Expand Down Expand Up @@ -220,6 +221,7 @@ private void PrepareFilter(ManagementReport mgt)
}
}
}
mgt.RelevantObjectIds = mgt.RelevantObjectIds.Distinct().ToList();
mgt.HighlightedObjectIds = mgt.HighlightedObjectIds.Distinct().ToList();
}

Expand Down
1 change: 1 addition & 0 deletions roles/ui/files/FWO.UI/Pages/Compliance/ZoneTable.razor
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@
@(userConfig.GetText("None"))
}
</DetailTemplate>
<Pager ShowPageNumber="true" ShowTotalCount="true" />
</Table>

@code
Expand Down
42 changes: 31 additions & 11 deletions roles/ui/files/FWO.UI/Pages/Login.razor
Original file line number Diff line number Diff line change
Expand Up @@ -20,14 +20,14 @@
@inject CircuitHandler circuitHandler

@if (showLoginForm)
{
<div class="center-div">
<div>
<br><br>
{
<div class="row text-center">
<div class="col-lg-4 col-md-3 col-sm-2"></div>
<div class="col-lg-4 col-md-6 col-sm-8 col-xs-12">
<img src="images/FWO_logo.png">
<br><br>
@* <h2 class="text-center"> @(userConfig.GetText("login")) </h2> *@
<div class="shadow-sm card p-3" style="width: 250px;">
<br><br>
@* <h2 class="text-center"> @(userConfig.GetText("login")) </h2> *@
<div class="shadow-sm card p-3">
<form class="d-flex flex-column">
<div class="form-group">
<input type="text" class="form-control @InputClass" id="UsernameInput" placeholder="@(globalConfig.GetText("username"))" value="@Username" @oninput="OnUsernameInput" @ref="usernameInput">
Expand All @@ -42,16 +42,31 @@
}
else
{
<div class="spinner-border text-primary align-self-center mt-3 mb-3" role="status"></div>
<div class="spinner-border text-primary align-self-center mt-3" role="status"></div>
}
@if(!string.IsNullOrEmpty(errorMessage))
{
<label class="m-2">@errorMessage</label>
}
</form>
</form>
</div>
</div>
</div>
<div class="col-lg-4 col-md-3 col-sm-2"></div>
</div>
@if(ShowWelcomeMessage)
{
<div class="row mt-4">
<div class="col-lg-4 col-md-3 col-sm-2">
</div>
<div class="col-lg-4 col-md-6 col-sm-8 col-xs-12">
<div class="alert alert-primary" role="alert">
<span>@((MarkupString)@globalConfig.WelcomeMessage)</span>
</div>
</div>
<div class="col-lg-4 col-md-3 col-sm-2">
</div>
</div>
}
}

@if (showPasswordChangeForm)
Expand Down Expand Up @@ -107,6 +122,8 @@
private string newPassword2 = "";
private string chgPwErrorMessage = "";

private bool ShowWelcomeMessage { get; set; }

protected override async Task OnAfterRenderAsync(bool firstRender)
{
//ApiConnection.Dispose();
Expand All @@ -127,6 +144,9 @@
}
catch (Exception ex) { Log.WriteError("Session Restore", "Session restore unsuccessful.", ex); }
}

if(!string.IsNullOrWhiteSpace(globalConfig.WelcomeMessage))
ShowWelcomeMessage = true;

// else no reconnect / reconnect unsuccessful
showLoginForm = true;
Expand Down Expand Up @@ -254,4 +274,4 @@
passwordChangeInProgress = false;
}
}
}
}
Loading

0 comments on commit 314e1d8

Please sign in to comment.