-- -- (C) 2017-20 - ntop.org -- local dirs = ntop.getDirs() package.path = dirs.installdir .. "/scripts/lua/modules/?.lua;" .. package.path require "lua_utils" require "graph_utils" local template = require "template_utils" local proto_filter = _GET["l7proto"] local category_filter = _GET["category"] local protos_utils = require("protos_utils") local info = ntop.getInfo() local has_protos_file = protos_utils.hasProtosFile() local ifId = getInterfaceId(ifname) if not haveAdminPrivileges() then return end local base_url = ntop.getHttpPrefix() .. "/lua/admin/edit_categories.lua" local page_params = { l7proto = proto_filter, category = category_filter, tab = "protocols" } local catid = nil if not isEmptyString(category_filter) then catid = split(category_filter, "cat_")[2] end local app_warnings = {} if (_POST["action"] == "add") or (_POST["action"] == "edit") then local action = _POST["action"] local hosts_list = _POST["custom_hosts"] local application = _POST["new_application"] or _POST["l7proto"] local hosts = string.split(hosts_list, ",") or {ternary(hosts_list ~= "", hosts_list, nil)} local rules = {} -- Preliminary check local applications = interface.getnDPIProtocols() local lower_app = string.lower(application) local existing_app = nil -- case insensitive search for applications for k in pairs(applications) do if string.lower(k) == lower_app then existing_app = k break end end if((action == "edit") and (existing_app == nil)) then app_warnings[#app_warnings + 1] = { type = "danger", text = i18n("custom_categories.application_not_exists", { app = application, }) } elseif((action == "add") and (existing_app ~= nil)) then app_warnings[#app_warnings + 1] = { type = "danger", text = i18n("custom_categories.application_exists", { app = existing_app, }) } else for _, host in ipairs(hosts) do -- TODO implement match logic on existing hosts to avoid duplicates local rule = protos_utils.getProtosTxtRule(host) if rule == nil then app_warnings[#app_warnings + 1] = { type = "warning", text = i18n("custom_categories.invalid_rule", { rule = host, }) } end rules[#rules + 1] = rule end if protos_utils.overwriteAppRules(application, rules) then if action == "add" then app_warnings[#app_warnings + 1] = { type = "success", text = i18n("custom_categories.new_app_added", {product=info.product, app = application}) } else app_warnings[#app_warnings + 1] = { type = "success", text = i18n("custom_categories.protos_reboot_necessary", {product=info.product}) } end else app_warnings[#app_warnings + 1] = { type = "danger", text = i18n("custom_categories.protos_unexpected_error", {product=info.product}) } end end elseif not table.empty(_POST) then local custom_categories = getCustomnDPIProtoCategories() for k, new_cat in pairs(_POST) do if starts(k, "proto_") then local id = split(k, "proto_")[2] local old_cat new_cat = tonumber(split(new_cat, "cat_")[2]) -- get the current category if custom_categories[id] ~= nil then old_cat = custom_categories[id] else old_cat = ntop.getnDPIProtoCategory(tonumber(id)) old_cat = old_cat and old_cat.id or 0 end if old_cat ~= new_cat then -- io.write("Changing nDPI category for " .. id .. ": " .. old_cat .. " -> " .. new_cat .. "\n") setCustomnDPIProtoCategory(tonumber(id), new_cat) end end end end printMessageBanners(app_warnings) local function makeApplicationEditor(area_id, required) return [[

]].. i18n("notes") ..[[ ]] end print( template.gen("modal_confirm_dialog.html", { dialog={ id = "edit_application_rules", action = "editApplication()", title = i18n("custom_categories.edit_custom_rules"), custom_alert_class = "", custom_dialog_class = "dialog-body-full-height", message = [[

]] .. i18n("custom_categories.the_following_is_a_list_of_hosts_app", {application=''}).. [[:

]] .. makeApplicationEditor("application-hosts-list"), confirm = i18n("save"), cancel = i18n("cancel"), } }) ) -- NOTE: having some rules is required for the application print[[ ]] print [[
]] if not isEmptyString(proto_filter) then local proto_name = interface.getnDPIProtoName(tonumber(proto_filter)) print[[]] end print[[
]] if catid ~= nil then print("

"..i18n("users.cat_protocols", {cat=interface.getnDPICategoryName(tonumber(catid))}).."

") end print[[
]] print( template.gen("typeahead_input.html", { typeahead={ base_id = "t_app", action = base_url, parameters = { ifid = tostring(ifId), category = category_filter, tab = "protocols", custom_hosts = "", }, json_key = "key", query_field = "l7proto", query_url = ntop.getHttpPrefix() .. "/lua/find_app.lua", query_title = i18n("categories_page.search_application"), style = "margin-left:1em; width:25em;", } }) ) print[[
]] print(i18n("notes")) print[[]] print[[

]]