From 2986433706c7d1cf0996c278419b033e31797eb9 Mon Sep 17 00:00:00 2001 From: rdkartono Date: Fri, 24 Oct 2025 16:29:33 +0700 Subject: [PATCH] commit 24/10/2025 --- config.properties | 12 +- html/webpage/assets/js/schedulebank.js | 92 +-- html/webpage/assets/js/setting.js | 183 ++++-- html/webpage/setting.html | 3 +- src/Main.kt | 4 +- src/MainExtension01.kt | 8 +- src/codes/Somecodes.kt | 5 +- src/database/MariaDB.kt | 20 +- src/database/ScheduleBank.kt | 17 + src/web/WebApp.kt | 850 +++++++++++++++---------- 10 files changed, 738 insertions(+), 456 deletions(-) diff --git a/config.properties b/config.properties index 7d23ab5..d5a804e 100644 --- a/config.properties +++ b/config.properties @@ -1,15 +1,15 @@ #Configuration file -#Thu Oct 23 15:01:47 WIB 2025 +#Fri Oct 24 10:57:19 WIB 2025 database.host=localhost database.name=aas database.password=admin database.port=3306 database.user=admin -remark.FLD= -remark.GBD= -remark.GFC= -remark.GOP= -soundbank.directory=C\:\\Users\\rdkar\\OneDrive\\Documents\\IntelliJ Project\\AAS_NewGen\\soundbank +remark.FLD=Gate Change [4] +remark.GBD=Second Call [2] +remark.GFC=Last Call [3] +remark.GOP=First Call [1] +soundbank.directory=C\:\\soundbank webapp.admin.password=password webapp.admin.username=admin webapp.port=3030 diff --git a/html/webpage/assets/js/schedulebank.js b/html/webpage/assets/js/schedulebank.js index c368a8c..ed1d8f0 100644 --- a/html/webpage/assets/js/schedulebank.js +++ b/html/webpage/assets/js/schedulebank.js @@ -66,8 +66,8 @@ function fill_schedulebanktablebody(vv) { * @param {String} value from input date, which is in format yyyy-mm-dd * @returns {String} converted date in format dd/mm/yyyy */ -function Convert_input_date_to_string(value){ - if (value && value.length>0 && value.includes('-')){ +function Convert_input_date_to_string(value) { + if (value && value.length > 0 && value.includes('-')) { let parts = value.split('-'); if (parts.length === 3) { let year = parts[0]; @@ -84,8 +84,8 @@ function Convert_input_date_to_string(value){ * @param {String} value string date in format dd/mm/yyyy * @returns {String} converted date in format yyyy-mm-dd */ -function Convert_string_to_input_date(value){ - if (value && value.length>0 && value.includes('/')){ +function Convert_string_to_input_date(value) { + if (value && value.length > 0 && value.includes('/')) { let parts = value.split('/'); if (parts.length === 3) { let day = parts[0]; @@ -190,7 +190,7 @@ $(document).ready(function () { width: '100%', dropdownParent: $('#schedulemodal') }); - + $scheduledate.prop('disabled', true).val(''); $schedulezones.empty().select2({ data: window.BroadcastZoneList.map(zone => ({ id: zone.description, text: zone.description })), @@ -295,7 +295,6 @@ $(document).ready(function () { const hour = parseInt($schedulehour.val(), 10); const minute = parseInt($scheduleminute.val(), 10); const _Time = `${hour.toString().padStart(2, '0')}:${minute.toString().padStart(2, '0')}`; - console.log(`Adding schedule: Description=${Description}, Day=${_Day}, Time=${_Time}, Message=${Message}, Repeat=${Repeat}, Enable=${Enable}, BroadcastZones=${broadcastZones}, Language=${Language}`); if (Description.length > 0) { if (_Day.length > 0) { if (Message.length > 0) { @@ -367,7 +366,6 @@ $(document).ready(function () { BroadcastZones: cells.eq(7).text(), Language: cells.eq(8).text() } - console.log('Editing schedule:', sr); if (confirm(`Are you sure to edit schedule [${sr.index}] Description=${sr.Description}?`)) { $schedulemodal.modal('show'); clearScheduleModal(); @@ -387,8 +385,13 @@ $(document).ready(function () { case 'Everyday': $scheduleeveryday.click(); break; - case 'Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday': - console.log(`Setting weekly schedule for day: ${sr.Day}`); + case 'Sunday' : + case 'Monday': + case 'Tuesday': + case 'Wednesday': + case 'Thursday': + case 'Friday': + case 'Saturday': $scheduleweekly.click(); $weeklyselect.val(sr.Day).trigger('change'); break; @@ -415,49 +418,50 @@ $(document).ready(function () { if ($scheduleeveryday.is(':checked')) { Day = "Everyday"; } else if ($schedulespecialdate.is(':checked')) { - Day = $scheduledate.val(); - } else { - if ($schedulesunday.is(':checked')) Day = "Sunday"; - if ($schedulemonday.is(':checked')) Day = "Monday"; - if ($scheduletuesday.is(':checked')) Day = "Tuesday"; - if ($schedulewednesday.is(':checked')) Day = "Wednesday"; - if ($schedulethursday.is(':checked')) Day = "Thursday"; - if ($schedulefriday.is(':checked')) Day = "Friday"; - if ($schedulesaturday.is(':checked')) Day = "Saturday"; + // convert date from yyyy-mm-dd to dd/mm/yyyy + Day = Convert_input_date_to_string($scheduledate.val()); + } else if ($scheduleweekly.is(':checked')) { + Day = $weeklyselect.val(); } // Broadcast zones (assuming comma-separated string) - const BroadcastZones = $schedulezones.val(); - - // Validate required fields - if (!Description || !Soundpath || Day === "") { - alert("Description, sound path, and day are required."); - return; - } - + const BroadcastZones = $schedulezones.val().join(';'); + const Language = $languageselect.val().join(';'); // Format time as HH:mm const hour = parseInt($schedulehour.val(), 10); const minute = parseInt($scheduleminute.val(), 10); const Time = `${hour.toString().padStart(2, '0')}:${minute.toString().padStart(2, '0')}`; + if (Description && Description.length > 0) { + if (Day && Day.length > 0) { + if (Soundpath && Soundpath.length > 0) { + if (Time && Time.length > 0) { + if (Language && Language.length > 0) { + if (BroadcastZones && BroadcastZones.length > 0) { + // Prepare object + const scheduleObj = { + Description, + Day, + Time, + Soundpath, + Repeat, + Enable, + BroadcastZones, + Language + }; - // Prepare object - const scheduleObj = { - Description, - Day, - Time, - Soundpath, - Repeat, - Enable, - BroadcastZones - }; + fetchAPI(APIURL + "UpdateByIndex/" + sr.index, "PATCH", {}, scheduleObj, (okdata) => { + alert("Success edit schedule: " + okdata.message); + reloadTimerBank(APIURL); + }, (errdata) => { + alert("Error edit schedule: " + errdata.message); + }); + $schedulemodal.modal('hide'); + } else alert("At least one Broadcast Zone is required"); + } else alert("At least one Language is required"); + } else alert("Time is invalid"); + } else alert("Message is not selected"); + } else alert("Day is invalid"); + } else alert("Description is empty"); - fetchAPI(APIURL + "UpdateByIndex/" + sr.index, "PATCH", {}, scheduleObj, (okdata) => { - alert("Success edit schedule: " + okdata.message); - reloadTimerBank(APIURL); - }, (errdata) => { - alert("Error edit schedule: " + errdata.message); - }); - - $schedulemodal.modal('hide'); }); } } diff --git a/html/webpage/assets/js/setting.js b/html/webpage/assets/js/setting.js index da26ff0..1dd1577 100644 --- a/html/webpage/assets/js/setting.js +++ b/html/webpage/assets/js/setting.js @@ -1,21 +1,16 @@ -let selected_language = null; -let selected_category = null; -let selected_voice = null; /** * Load setting language dropdown */ -function load_setting_language(){ - selected_language = null; +function load_setting_language() { $("#setting_language").empty().off('change'); - - getLanguages( () => { - window.languages.forEach( (lang) => { + + getLanguages(() => { + window.languages.forEach((lang) => { let $option = $("").attr("value", lang).text(lang); $("#setting_language").append($option); }); - $("#setting_language").on('change', function() { - selected_language = $(this).val(); + $("#setting_language").on('change', function () { change_droparea_enable(); }); }); @@ -24,16 +19,14 @@ function load_setting_language(){ /** * Load setting category dropdown */ -function load_setting_category(){ - selected_category = null; +function load_setting_category() { $("#setting_category").empty().off('change'); - getCategories( () => { - window.categories.forEach( (cat) => { + getCategories(() => { + window.categories.forEach((cat) => { let $option = $("").attr("value", cat).text(cat); $("#setting_category").append($option); }); - $("#setting_category").on('change', function() { - selected_category = $(this).val(); + $("#setting_category").on('change', function () { change_droparea_enable(); }); }); @@ -42,25 +35,30 @@ function load_setting_category(){ /** * Load setting voice dropdown */ -function load_setting_voice(){ - selected_voice = null; +function load_setting_voice() { $("#setting_voice").empty().off('change'); - getVoiceTypes( () => { - window.voiceTypes.forEach( (voice) => { + getVoiceTypes(() => { + window.voiceTypes.forEach((voice) => { let $option = $("").attr("value", voice).text(voice); $("#setting_voice").append($option); }); - $("#setting_voice").on('change', function() { - selected_voice = $(this).val(); + $("#setting_voice").on('change', function () { change_droparea_enable(); }); }); } -function get_soundbank_path(){ +/** + * Get Soundbank path from server + */ +function get_soundbank_path() { + $("#setting_path").val(""); fetchAPI("Settings/SoundbankDirectory", "GET", {}, null, (okdata) => { - console.log("Soundbank path : " + okdata); - $("#setting_path").val(okdata); + if (okdata.message && okdata.message.trim().length > 0) { + let path = okdata.message.trim(); + //console.log("Soundbank path retrieved: " + path); + $("#setting_path").val(path); + } }, (errdata) => { alert("Error getting soundbank path : " + errdata.message); }); @@ -69,7 +67,10 @@ function get_soundbank_path(){ /** * Enable or disable drop area based on selections */ -function change_droparea_enable(){ +function change_droparea_enable() { + let selected_category = $("#setting_category").val(); + let selected_language = $("#setting_language").val(); + let selected_voice = $("#setting_voice").val(); if (selected_category && selected_language && selected_voice) { $("#drop-area").removeClass("disabled"); } else { @@ -77,45 +78,49 @@ function change_droparea_enable(){ } } -function load_messagebank(cbOK = null){ +/** + * Load message bank data into selection dropdowns + * @param {Function || null} cbOK callback when complete + */ +function load_messagebank(cbOK = null) { $("#input_GOP").empty(); $("#input_GBD").empty(); $("#input_GFC").empty(); $("#input_FLD").empty(); - // get messagebank data from server - reloadMessageBank(()=>{ - console.log("Will load " + window.messagebankdata.length + " message bank items into selection."); - window.messagebankdata.forEach((item)=>{ - let opt = `${item.description} [${item.aNN_ID}]`; - console.log("Adding option: " + opt); - $("#input_GOP").append($("").attr("value", opt).text(opt)); - $("#input_GBD").append($("").attr("value", opt).text(opt)); - $("#input_GFC").append($("").attr("value", opt).text(opt)); - $("#input_FLD").append($("").attr("value", opt).text(opt)); - }); - if (window.messagebankdata.length > 0) { - if (cbOK) cbOK(); - } + // get messagebank data from server, which contains [FLIGHT_NUMBER] + let messageData = [...new Set(window.messagebankdata.filter(mb => mb.message_Detail.includes('[FLIGHT_NUMBER]')).map(mb => `${mb.description} [${mb.aNN_ID}]`))]; + //console.log("Message bank data with [FLIGHT_NUMBER]: ", messageData); + messageData.forEach((item) => { + //console.log("Adding option: " + item); + $("#input_GOP").append($("").attr("value", item).text(item)); + $("#input_GBD").append($("").attr("value", item).text(item)); + $("#input_GFC").append($("").attr("value", item).text(item)); + $("#input_FLD").append($("").attr("value", item).text(item)); }); + if (window.messagebankdata.length > 0) { + if (cbOK) cbOK(); + } } -function load_remark_selection(){ +function load_remark_selection() { fetchAPI("Settings/FISCode", "GET", {}, null, (okdata) => { - $("#input_GOP").val(okdata.GOP); - $("#input_GBD").val(okdata.GBD); - $("#input_GFC").val(okdata.GFC); - $("#input_FLD").val(okdata.FLD); + //console.log("FIS codes retrieved: ", JSON.stringify(okdata)); + + $("#input_GOP").val(okdata.gop) + $("#input_GBD").val(okdata.gbd); + $("#input_GFC").val(okdata.gfc); + $("#input_FLD").val(okdata.fld); }, (errdata) => { alert("Error getting FIS codes : " + errdata.message); }); } -$(document).ready(function() { +$(document).ready(function () { console.log("setting.js loaded"); - - - $("#save_directory").off('click').on('click', function() { + + + $("#save_directory").off('click').on('click', function () { let new_path = $("#setting_path").val(); if (new_path && new_path.trim().length > 0) { fetchAPI("Settings/SoundbankDirectory", "POST", {}, { directory: new_path }, (okdata) => { @@ -126,15 +131,15 @@ $(document).ready(function() { } else { alert("Please enter a valid soundbank directory path."); } - }); + }); - // get_soundbank_path(); + get_soundbank_path(); load_setting_category(); load_setting_language(); load_setting_voice(); - load_messagebank(()=> load_remark_selection()); - $("#fiscodesave").off('click').on('click', function() { + load_messagebank(() => load_remark_selection()); + $("#fiscodesave").off('click').on('click', function () { let gop = $("#input_GOP").val(); let gbd = $("#input_GBD").val(); let gfc = $("#input_GFC").val(); @@ -154,7 +159,73 @@ $(document).ready(function() { } else { alert("Please select all FIS codes (GOP, GBD, GFC, FLD) before saving."); } - + }); - + + $("#drop-area").on('dragover', function (e) { + e.preventDefault(); + e.stopPropagation(); + $(this).addClass('dragover'); + }).on('dragleave', function (e) { + e.preventDefault(); + e.stopPropagation(); + $(this).removeClass('dragover'); + }).on('drop', function (e) { + e.preventDefault(); + e.stopPropagation(); + $(this).removeClass('dragover'); + if ($(this).hasClass('disabled')) { + alert("Please select Category, Language, and Voice Type before uploading files."); + return; + } + let lang = $("#setting_language").val().trim(); + let category = $("#setting_category").val().trim(); + let voice = $("#setting_voice").val().trim(); + let files = e.originalEvent.dataTransfer.files; + if (lang && lang.length > 0) { + if (category && category.length > 0) { + if (voice && voice.length > 0) { + if (files.length > 0) { + // check if each file have type audio/wav , size more than 0, and name ends with .wav + let allValid = true; + for (let i = 0; i < files.length; i++) { + let file = files[i]; + if (file.type !== 'audio/wav' && !file.name.toLowerCase().endsWith('.wav')) { + allValid = false; + } + if (file.size <= 0) { + allValid = false; + } + } + if (allValid) { + if (confirm(`Are you sure want to upload ${files.length} file(s) to the soundbank directory for Category: ${$("#setting_category").val()}, Language: ${$("#setting_language").val()}, Voice Type: ${$("#setting_voice").val()}?`)) { + let url = `api/Settings/UploadSoundbank/${lang}/${voice}/${category}`; + const formdata = new FormData(); + for (let i = 0; i < files.length; i++) { + formdata.append('files', files[i]); + } + try{ + fetch(url, { + method: 'POST', + body: formdata + }) + .then(response => response.json()) + .then(okdata => { + console.log("Upload result: ", JSON.stringify(okdata)); + }) + .catch(errdata => { + alert("Error uploading files to soundbank directory : " + errdata.message); + }); + } catch(err){ + alert("Error preparing file upload: " + err.message); + } + } + } else alert("Please upload only valid WAV audio files. Type must be audio/wav and size must be more than 0 bytes."); + } else alert("No files detected for upload."); + } else alert("Please select Voice Type before uploading files."); + } else alert("Please select Category before uploading files."); + } else alert("Please select Language before uploading files."); + + }); + }); \ No newline at end of file diff --git a/html/webpage/setting.html b/html/webpage/setting.html index 50a1a05..1a79094 100644 --- a/html/webpage/setting.html +++ b/html/webpage/setting.html @@ -38,7 +38,7 @@
-
+
@@ -80,7 +80,6 @@
- diff --git a/src/Main.kt b/src/Main.kt index 30063de..b5431a3 100644 --- a/src/Main.kt +++ b/src/Main.kt @@ -33,7 +33,7 @@ lateinit var audioPlayer: AudioPlayer val StreamerOutputs: MutableMap = HashMap() lateinit var udpreceiver: UDPReceiver lateinit var tcpreceiver: TCPReceiver -const val version = "0.0.10 (20/10/2025)" +const val version = "0.0.11 (24/10/2025)" // AAS 64 channels const val max_channel = 64 @@ -59,6 +59,8 @@ fun folder_preparation(){ // sementara diset begini, nanti pake config file //Somecodes.Soundbank_directory = Paths.get("c:\\soundbank") Somecodes.Soundbank_directory = Paths.get(config.Get(configKeys.SOUNDBANK_DIRECTORY.key)) + Somecodes.SoundbankResult_directory = Somecodes.Soundbank_directory.resolve("SoundbankResult") + Somecodes.PagingResult_directory = Somecodes.Soundbank_directory.resolve("PagingResult") Files.createDirectories(Somecodes.SoundbankResult_directory) Files.createDirectories(Somecodes.PagingResult_directory) Files.createDirectories(Somecodes.Soundbank_directory) diff --git a/src/MainExtension01.kt b/src/MainExtension01.kt index e738e64..931424d 100644 --- a/src/MainExtension01.kt +++ b/src/MainExtension01.kt @@ -901,22 +901,22 @@ class MainExtension01 { when(remark){ "GOP" -> { //TODO Combobox First_Call_Message_Chooser. - val remarkMsg = config.Get(configKeys.REMARK_GOP.toString()) + val remarkMsg = config.Get(configKeys.REMARK_GOP.key) ann_id = Regex("\\[(\\d+)]").find(remarkMsg)?.value?.toIntOrNull() ?: 0 } "GBD" ->{ // TODO Combobox Second_Call_Message_Chooser - val remarkMsg = config.Get(configKeys.REMARK_GBD.toString()) + val remarkMsg = config.Get(configKeys.REMARK_GBD.key) ann_id = Regex("\\[(\\d+)]").find(remarkMsg)?.value?.toIntOrNull() ?: 0 } "GFC" ->{ // TODO Combobox Final_Call_Message_Chooser - val remarkMsg = config.Get(configKeys.REMARK_GFC.toString()) + val remarkMsg = config.Get(configKeys.REMARK_GFC.key) ann_id = Regex("\\[(\\d+)]").find(remarkMsg)?.value?.toIntOrNull() ?: 0 } "FLD" ->{ // TODO Combobox Landed_Message_Chooser - val remarkMsg = config.Get(configKeys.REMARK_FLD.toString()) + val remarkMsg = config.Get(configKeys.REMARK_FLD.key) ann_id = Regex("\\[(\\d+)]").find(remarkMsg)?.value?.toIntOrNull() ?: 0 } } diff --git a/src/codes/Somecodes.kt b/src/codes/Somecodes.kt index ae24b32..695b3d2 100644 --- a/src/codes/Somecodes.kt +++ b/src/codes/Somecodes.kt @@ -1,5 +1,6 @@ package codes +import codes.Somecodes.Companion.Soundbank_directory import com.fasterxml.jackson.databind.JsonNode import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper import content.Category @@ -32,8 +33,8 @@ class Somecodes { val current_directory : String = System.getProperty("user.dir") var Soundbank_directory : Path = Path.of(current_directory,"Soundbank") - val SoundbankResult_directory : Path = Path.of(current_directory,"SoundbankResult") - val PagingResult_directory : Path = Path.of(current_directory,"PagingResult") + var SoundbankResult_directory : Path = Soundbank_directory.resolve("SoundbankResult") + var PagingResult_directory : Path = Soundbank_directory.resolve("PagingResult") val si = SystemInfo() val processor: CentralProcessor = si.hardware.processor diff --git a/src/database/MariaDB.kt b/src/database/MariaDB.kt index 7adadbb..1a14fa1 100644 --- a/src/database/MariaDB.kt +++ b/src/database/MariaDB.kt @@ -805,7 +805,7 @@ class MariaDB( "INSERT INTO ${super.dbName} (Description, Day, Time, Soundpath, `Repeat`, Enable, BroadcastZones, Language) VALUES (?, ?, ?, ?, ?, ?, ?, ?)" val statement = connection.prepareStatement(sql) for (sb in data) { - if (!ValidDate(sb.Day) || !ValidTime(sb.Time)) { + if (!ValidScheduleDay(sb.Day) || !ValidTime(sb.Time)) { Logger.error("Invalid date or time format for schedulebank: ${sb.Description}" as Any) continue } @@ -834,7 +834,7 @@ class MariaDB( override fun UpdateByIndex(index: Int, data: ScheduleBank): Boolean { - if (!ValidDate(data.Day)) { + if (!ValidScheduleDay(data.Day)) { Logger.error("Error updating schedulebank entry: Invalid date format ${data.Day}" as Any) return false } @@ -915,16 +915,27 @@ class MariaDB( Clear() // read each row and insert into database val _schedulebankList = ArrayList() + //Logger.info{"Sheet last row num: ${sheet.lastRowNum}"} for (rowIndex in 1..sheet.lastRowNum) { val row = sheet.getRow(rowIndex) ?: continue + //println(row) val description = row.getCell(1)?.stringCellValue ?: continue + //println(description.toString()) val day = row.getCell(2)?.stringCellValue ?: continue + //println(day.toString()) val time = row.getCell(3)?.stringCellValue ?: continue + //println(time.toString()) val soundpath = row.getCell(4)?.stringCellValue ?: continue + //println(soundpath.toString()) val repeat = row.getCell(5)?.stringCellValue?.toUByteOrNull() ?: continue - val enable = row.getCell(6)?.stringCellValue?.toBooleanStrictOrNull() ?: continue + // println(repeat.toString()) + //val enable = row.getCell(6)?.stringCellValue?.toBooleanStrictOrNull() ?: continue + val enable = row.getCell(6)?.stringCellValue?.toBoolean() ?: continue + //println(enable.toString()) val broadcastZones = row.getCell(7)?.stringCellValue ?: continue + //println(broadcastZones.toString()) val language = row.getCell(8)?.stringCellValue ?: continue + //println(language.toString()) val schedulebank = ScheduleBank( 0u, @@ -937,9 +948,10 @@ class MariaDB( broadcastZones, language ) + Logger.info{"SchedulebankList added 1"} + _schedulebankList.add(schedulebank) } - return scheduleDB.AddAll(_schedulebankList) } catch (e: Exception) { Logger.error { "Error importing Schedulebank, Msg: ${e.message}" } diff --git a/src/database/ScheduleBank.kt b/src/database/ScheduleBank.kt index aa0a6c9..d2e9ec6 100644 --- a/src/database/ScheduleBank.kt +++ b/src/database/ScheduleBank.kt @@ -16,7 +16,24 @@ data class ScheduleBank( return "ScheduleBank(index=$index, Description='$Description', Day='$Day', Time='$Time', Soundpath='$Soundpath', Repeat=$Repeat, Enable=$Enable, BroadcastZones='$BroadcastZones', Language='$Language')" } + /** + * Check if all string properties of the ScheduleBank are not empty. + */ fun isNotEmpty() : Boolean{ return Description.isNotEmpty() && Day.isNotEmpty() && Time.isNotEmpty() && Soundpath.isNotEmpty() && BroadcastZones.isNotEmpty() && Language.isNotEmpty() } + + /** + * Compare two ScheduleBank objects for equality based on their properties. + */ + fun isEqual(other: ScheduleBank) : Boolean { + return Description == other.Description && + Day == other.Day && + Time == other.Time && + Soundpath == other.Soundpath && + Repeat == other.Repeat && + Enable == other.Enable && + BroadcastZones == other.BroadcastZones && + Language == other.Language + } } diff --git a/src/web/WebApp.kt b/src/web/WebApp.kt index d765697..48b17ce 100644 --- a/src/web/WebApp.kt +++ b/src/web/WebApp.kt @@ -44,6 +44,7 @@ import java.nio.file.Files import java.time.LocalDateTime import codes.configKeys import org.tinylog.Logger + //import com.sun.security.auth.login.ConfigFile @@ -72,16 +73,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val path("/") { get { ctx -> // Serve the main page - ctx.cookie("aas-user","") + ctx.cookie("aas-user", "") //ctx.sessionAttribute("user", null) // Clear user session ctx.redirect("login.html") } } - path("logout"){ + path("logout") { get { ctx -> - println("Logout requested by user") - ctx.cookie("aas-user","") + ctx.cookie("aas-user", "") //ctx.sessionAttribute("user", null) // Clear user session ctx.redirect("login.html") } @@ -92,19 +92,20 @@ class WebApp(val listenPort: Int, val userlist: List>, val val username = it.formParam("username") val password = it.formParam("password") if (username == null || password == null) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Username and password are required"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Username and password are required"))) return@post } // Check if user exists in userlist val user = userlist.find { it.first == username && it.second == password } if (user == null) { - it.status(401).result(objectmapper.writeValueAsString(resultMessage("Invalid username or password"))) + it.status(401) + .result(objectmapper.writeValueAsString(resultMessage("Invalid username or password"))) return@post } // Set user session //it.sessionAttribute("user", user.first) it.cookie("aas-user", user.first) - //println("User ${user.first} logged in") // Redirect to home page it.redirect("home.html") } @@ -133,8 +134,8 @@ class WebApp(val listenPort: Int, val userlist: List>, val "getCPUStatus" -> { Somecodes.getCPUUsage { vv -> val sv = GetSensorsInfo() - if (sv.isNotEmpty()){ - SendReply(wsMessageContext, cmd.command, vv+"\n"+sv) + if (sv.isNotEmpty()) { + SendReply(wsMessageContext, cmd.command, vv + "\n" + sv) } else { SendReply(wsMessageContext, cmd.command, vv) } @@ -151,20 +152,33 @@ class WebApp(val listenPort: Int, val userlist: List>, val "getNetworkStatus" -> { Somecodes.GetNetworkStatus { nn -> - SendReply(wsMessageContext, cmd.command, objectmapper.writeValueAsString(nn)) + SendReply( + wsMessageContext, + cmd.command, + objectmapper.writeValueAsString(nn) + ) } } - "getPagingQueue" ->{ - SendReply(wsMessageContext, cmd.command, objectmapper.writeValueAsString(db.queuepagingDB.List)) + "getPagingQueue" -> { + SendReply( + wsMessageContext, + cmd.command, + objectmapper.writeValueAsString(db.queuepagingDB.List) + ) } - "getAASQueue" ->{ - SendReply(wsMessageContext, cmd.command, objectmapper.writeValueAsString(db.queuetableDB.List)) + "getAASQueue" -> { + SendReply( + wsMessageContext, + cmd.command, + objectmapper.writeValueAsString(db.queuetableDB.List) + ) } "getStreamerOutputs" -> { - val reply : List = StreamerOutputs.map { so -> StreamerOutputData.fromBarixConnection(so.value) } + val reply: List = + StreamerOutputs.map { so -> StreamerOutputData.fromBarixConnection(so.value) } SendReply(wsMessageContext, cmd.command, objectmapper.writeValueAsString(reply)) } @@ -177,9 +191,7 @@ class WebApp(val listenPort: Int, val userlist: List>, val } } -// ws.onConnect { wsConnectContext -> -// println("WebSocket connected: ${wsConnectContext.session.remoteAddress}") -// } + } } @@ -202,19 +214,19 @@ class WebApp(val listenPort: Int, val userlist: List>, val before { CheckUsers(it) } } path("api") { - path("VoiceType"){ - get{ + path("VoiceType") { + get { it.result(objectmapper.writeValueAsString(VoiceType.entries.map { vt -> vt.name })) } } path("Category") { get { - it.result(objectmapper.writeValueAsString(Category.entries.map { cat -> cat.name}) ) + it.result(objectmapper.writeValueAsString(Category.entries.map { cat -> cat.name })) } } path("Language") { get { - it.result(objectmapper.writeValueAsString(Language.entries.map { lang -> lang.name }) ) + it.result(objectmapper.writeValueAsString(Language.entries.map { lang -> lang.name })) } } path("ScheduleDay") { @@ -235,7 +247,7 @@ class WebApp(val listenPort: Int, val userlist: List>, val VoiceType.valueOf(voiceType), Category.valueOf(category) ) - if (Files.isDirectory(dir)){ + if (Files.isDirectory(dir)) { val list = ListAudioFiles(dir) ctx.result(objectmapper.writeValueAsString(list)) @@ -256,15 +268,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val get("ListFiles") { it.result(objectmapper.writeValueAsString(ListAudioFiles(Somecodes.Soundbank_directory))) } - get("GetPhrases/{Language}/{VoiceType}"){ + get("GetPhrases/{Language}/{VoiceType}") { val language = it.pathParam("Language") val voiceType = it.pathParam("VoiceType") if (ValidString(language) && Language.entries.any { lang -> lang.name == language }) { if (ValidString(voiceType) && VoiceType.entries.any { vt -> vt.name == voiceType }) { val phrases = db.soundDB.List .filter { sb -> sb.Language == language } - .filter {sb -> sb.VoiceType == voiceType} - .filter { sb -> sb.Category == Category.Phrase.name} + .filter { sb -> sb.VoiceType == voiceType } + .filter { sb -> sb.Category == Category.Phrase.name } .distinctBy { sb -> sb.TAG } .sortedBy { sb -> sb.TAG } it.result(objectmapper.writeValueAsString(phrases)) @@ -292,13 +304,17 @@ class WebApp(val listenPort: Int, val userlist: List>, val post("Add") { try { val addvalue = objectmapper.readValue(it.body(), Soundbank::class.java) - if (addvalue.isNotEmpty()){ + if (addvalue.isNotEmpty()) { // check apakah TAG sudah ada untuk language, category dan voicetype yang sama val exists = db.soundDB.List.any { sb -> sb.TAG == addvalue.TAG && sb.Language == addvalue.Language && sb.Category == addvalue.Category && sb.VoiceType == addvalue.VoiceType } if (!exists) { - val absolutepath = Somecodes.SoundbankDirectory(Language.valueOf(addvalue.Language), VoiceType.valueOf(addvalue.VoiceType), Category.valueOf(addvalue.Category)).resolve(addvalue.Path) + val absolutepath = Somecodes.SoundbankDirectory( + Language.valueOf(addvalue.Language), + VoiceType.valueOf(addvalue.VoiceType), + Category.valueOf(addvalue.Category) + ).resolve(addvalue.Path) if (Files.isRegularFile(absolutepath)) { addvalue.Path = absolutepath.toAbsolutePath().toString() if (db.soundDB.Add(addvalue)) { @@ -310,10 +326,12 @@ class WebApp(val listenPort: Int, val userlist: List>, val .result(objectmapper.writeValueAsString(resultMessage("Invalid Path, file does not exist"))) } else it.status(400) .result(objectmapper.writeValueAsString(resultMessage("TAG=${addvalue.TAG} already exists for the same Language=${addvalue.Language} and Category=${addvalue.Category}"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Some fields are empty"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Some fields are empty"))) } catch (e: Exception) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid request body, Message: ${e.message}"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid request body, Message: ${e.message}"))) } } delete("List") { @@ -322,7 +340,8 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.soundDB.Get() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to truncate soundbank table"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to truncate soundbank table"))) } } delete("DeleteByIndex/{index}") { @@ -334,23 +353,22 @@ class WebApp(val listenPort: Int, val userlist: List>, val if (db.soundDB.DeleteByIndex(index.toInt())) { db.soundDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - db.Add_Log("AAS","Deleted sound bank with index $index") + db.Add_Log("AAS", "Deleted sound bank with index $index") } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to delete soundbank with index $index"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to delete soundbank with index $index"))) } } } patch("UpdateByIndex/{index}") { // update by index val index = it.pathParam("index").toUIntOrNull() - if (index!=null){ + if (index != null) { val sb = db.soundDB.List.find { xx -> xx.index == index } - if (sb!=null){ - try{ - //println("index=$index, body=${it.body()}") + if (sb != null) { + try { val newsb = objectmapper.readValue(it.body(), Soundbank::class.java) - //println("newsb=$newsb") - if (newsb.isNotEmpty()){ + if (newsb.isNotEmpty()) { var varchanged = false if (newsb.Description != sb.Description) { sb.Description = newsb.Description @@ -361,59 +379,70 @@ class WebApp(val listenPort: Int, val userlist: List>, val varchanged = true } if (newsb.ValidCategory()) { - if (newsb.Category != sb.Category){ + if (newsb.Category != sb.Category) { sb.Category = newsb.Category varchanged = true } } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Category"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Category"))) return@patch } if (newsb.ValidLanguage()) { - if (newsb.Language != sb.Language){ + if (newsb.Language != sb.Language) { sb.Language = newsb.Language varchanged = true } } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Language"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Language"))) return@patch } if (newsb.ValidVoiceType()) { - if (newsb.VoiceType != sb.VoiceType){ + if (newsb.VoiceType != sb.VoiceType) { sb.VoiceType = newsb.VoiceType varchanged = true } } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid VoiceType"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid VoiceType"))) return@patch } - val newpath = Somecodes.SoundbankDirectory(newsb.Language, newsb.VoiceType, newsb.Category).resolve(newsb.Path) - if (Files.isRegularFile(newpath)){ + val newpath = Somecodes.SoundbankDirectory( + newsb.Language, + newsb.VoiceType, + newsb.Category + ).resolve(newsb.Path) + if (Files.isRegularFile(newpath)) { if (newpath.toAbsolutePath().toString() != sb.Path) { sb.Path = newpath.toAbsolutePath().toString() varchanged = true } } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid path"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid path"))) return@patch } if (varchanged) { - //println("Some fields changed for index=$index, updating...") if (db.soundDB.UpdateByIndex(index.toInt(), sb)) { db.soundDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - } else it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to update soundbank with index $index"))) + } else it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to update soundbank with index $index"))) } else it.status(400) .result(objectmapper.writeValueAsString(resultMessage("Nothing has changed for soundbank with index $index"))) } else Exception("Some fields are empty") - } catch(e: Exception){ - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Unable to parse request body to Soundbank, Message: ${e.message}"))) + } catch (e: Exception) { + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Unable to parse request body to Soundbank, Message: ${e.message}"))) } - } else it.status(404).result(objectmapper.writeValueAsString(resultMessage("Soundbank with index $index not found"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid index"))) + } else it.status(404) + .result(objectmapper.writeValueAsString(resultMessage("Soundbank with index $index not found"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid index"))) } get("ExportXLSX") { @@ -428,13 +457,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val xlsxdata.write(out) } } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to export soundbank to XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to export soundbank to XLSX"))) } } post("ImportXLSX") { val uploaded = it.uploadedFile("file") if (uploaded == null) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) return@post } try { @@ -443,10 +474,12 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.soundDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to import soundbank from XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to import soundbank from XLSX"))) } } catch (e: Exception) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) } } } @@ -470,23 +503,38 @@ class WebApp(val listenPort: Int, val userlist: List>, val val voice_type = json.get("Voice_Type")?.asText("") ?: "" val message_detail = json.get("Message_Detail")?.asText("") ?: "" val message_tags = json.get("Message_TAGS")?.asText("") ?: "" - if (description.isNotEmpty()){ - if (language.isNotEmpty() && Language.entries.any{ lang -> lang.name == language }){ - if (ann_id>0u){ - if (voice_type.isNotEmpty() && VoiceType.entries.any{ vt -> vt.name == voice_type }){ - if (message_detail.isNotEmpty()){ - if (message_tags.isNotEmpty()){ - val mb = Messagebank(0u, description, language, ann_id, voice_type, message_detail, message_tags) - if (db.messageDB.Add(mb)){ + if (description.isNotEmpty()) { + if (language.isNotEmpty() && Language.entries.any { lang -> lang.name == language }) { + if (ann_id > 0u) { + if (voice_type.isNotEmpty() && VoiceType.entries.any { vt -> vt.name == voice_type }) { + if (message_detail.isNotEmpty()) { + if (message_tags.isNotEmpty()) { + val mb = Messagebank( + 0u, + description, + language, + ann_id, + voice_type, + message_detail, + message_tags + ) + if (db.messageDB.Add(mb)) { db.messageDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - } else it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to add messagebank to database"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Message_TAGS"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Message_Detail"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Voice_Type"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid ANN_ID"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Language"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Description"))) + } else it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to add messagebank to database"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Message_TAGS"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Message_Detail"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Voice_Type"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid ANN_ID"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Language"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Description"))) } delete("List") { // truncate messagebank table @@ -494,7 +542,8 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.messageDB.Get() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to truncate messagebank table"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to truncate messagebank table"))) } } delete("DeleteByIndex/{index}") { @@ -506,9 +555,10 @@ class WebApp(val listenPort: Int, val userlist: List>, val if (db.messageDB.DeleteByIndex(index.toInt())) { db.messageDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - db.Add_Log("AAS","Deleted message bank with index $index") + db.Add_Log("AAS", "Deleted message bank with index $index") } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to delete messagebank with index $index"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to delete messagebank with index $index"))) } } } @@ -520,11 +570,13 @@ class WebApp(val listenPort: Int, val userlist: List>, val } else { val mb = db.messageDB.List.find { xx -> xx.index == index } if (mb == null) { - it.status(404).result(objectmapper.writeValueAsString(resultMessage("Messagebank with index $index not found"))) + it.status(404) + .result(objectmapper.writeValueAsString(resultMessage("Messagebank with index $index not found"))) } else { val json: JsonNode = objectmapper.readTree(it.body()) if (json.isEmpty) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) } else { val _description = json.get("Description").asText("") val _language = json.get("Language").asText("") @@ -551,7 +603,8 @@ class WebApp(val listenPort: Int, val userlist: List>, val mb.Voice_Type = _voice_type changed = true } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Voice_Type"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Voice_Type"))) return@patch } } @@ -587,13 +640,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val xlsxdata.write(out) } } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to export messagebank to XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to export messagebank to XLSX"))) } } post("ImportXLSX") { val uploaded = it.uploadedFile("file") if (uploaded == null) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) return@post } try { @@ -602,10 +657,12 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.messageDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to import messagebank from XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to import messagebank from XLSX"))) } } catch (e: Exception) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) } } } @@ -614,34 +671,33 @@ class WebApp(val listenPort: Int, val userlist: List>, val // get language link list it.result(MariaDB.ArrayListtoString(db.languageDB.List)) } - post("Add"){ + post("Add") { // Parse JSON from request body val json: JsonNode = objectmapper.readTree(it.body()) val tag = json.get("tag").asText("") val languages = json.get("language").asText("").split(";") - //println("Add Language Link, tag=$tag, languages=$languages") - if (ValidString(tag)){ - if (languages.all { xx -> Language.entries.any { yy -> yy.name.equals(xx,true)} }){ - if (!db.languageDB.List.any { ll -> ll.TAG.equals(tag,true) }) { + if (ValidString(tag)) { + if (languages.all { xx -> Language.entries.any { yy -> yy.name.equals(xx, true) } }) { + if (!db.languageDB.List.any { ll -> ll.TAG.equals(tag, true) }) { val newvalue = LanguageLink(0u, tag, languages.joinToString(";")) - if (db.languageDB.Add(newvalue)){ + if (db.languageDB.Add(newvalue)) { db.languageDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to add language link to database"))) - //println("Failed to add language link to database") + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to add language link to database"))) } } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("TAG=$tag already exists"))) - //println("TAG=$tag already exists") + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("TAG=$tag already exists"))) } } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Contains unsupported language"))) - println("Contains unsupported language") + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Contains unsupported language"))) } } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid tag or language"))) - println("Invalid tag") + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid tag or language"))) } } delete("List") { @@ -650,7 +706,8 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.languageDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to truncate language link table"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to truncate language link table"))) } } delete("DeleteByIndex/{index}") { @@ -662,9 +719,10 @@ class WebApp(val listenPort: Int, val userlist: List>, val if (db.languageDB.DeleteByIndex(index.toInt())) { db.languageDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - db.Add_Log("AAS","Deleted language link with index $index") + db.Add_Log("AAS", "Deleted language link with index $index") } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to delete language link with index $index"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to delete language link with index $index"))) } } } @@ -676,11 +734,13 @@ class WebApp(val listenPort: Int, val userlist: List>, val } else { val ll = db.languageDB.List.find { xx -> xx.index == index } if (ll == null) { - it.status(404).result(objectmapper.writeValueAsString(resultMessage("Language link with index $index not found"))) + it.status(404) + .result(objectmapper.writeValueAsString(resultMessage("Language link with index $index not found"))) } else { val json: JsonNode = objectmapper.readTree(it.body()) if (json.isEmpty) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) } else { val _tag = json.get("tag").asText("") val _language = json.get("language").asText("") @@ -717,13 +777,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val xlsxdata.write(out) } } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to export language link to XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to export language link to XLSX"))) } } post("ImportXLSX") { val uploaded = it.uploadedFile("file") if (uploaded == null) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) return@post } try { @@ -732,10 +794,12 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.languageDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to import language link from XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to import language link from XLSX"))) } } catch (e: Exception) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) } } } @@ -750,10 +814,11 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.scheduleDB.Get() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to truncate schedulebank table"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to truncate schedulebank table"))) } } - post("Add"){ + post("Add") { val json: JsonNode = objectmapper.readTree(it.body()) val description = json.get("Description")?.asText("") ?: "" val day = json.get("Day")?.asText("") ?: "" @@ -763,16 +828,22 @@ class WebApp(val listenPort: Int, val userlist: List>, val val enable = json.get("Enable")?.asBoolean() ?: false val broadcast_zones = json.get("BroadcastZones")?.asText("") ?: "" val language = json.get("Language")?.asText("") ?: "" - println("Add ScheduleBank, description=$description, day=$day, time=$time, soundpath=$soundpath, repeat=$repeat, enable=$enable, broadcast_zones=$broadcast_zones, language=$language") - if (ValidString(description)){ - if (ValidScheduleDay(day)){ - if (ValidScheduleTime(time)){ - if (ValidString(soundpath)){ - if (repeat in 0u..127u){ - if (ValidString(broadcast_zones)){ + if (ValidString(description)) { + if (ValidScheduleDay(day)) { + if (ValidScheduleTime(time)) { + if (ValidString(soundpath)) { + if (repeat in 0u..127u) { + if (ValidString(broadcast_zones)) { val zones = broadcast_zones.split(";") - if (zones.all { zz -> db.broadcastDB.List.any { xx -> xx.description.equals(zz,true) } }){ - if (ValidString(language)){ + if (zones.all { zz -> + db.broadcastDB.List.any { xx -> + xx.description.equals( + zz, + true + ) + } + }) { + if (ValidString(language)) { val newvalue = ScheduleBank( 0u, description, @@ -784,18 +855,33 @@ class WebApp(val listenPort: Int, val userlist: List>, val broadcast_zones, language ) - if (db.scheduleDB.Add(newvalue)){ + if (db.scheduleDB.Add(newvalue)) { db.scheduleDB.Resort() - it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - } else it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to add schedule to database"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Language"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Contains unsupported BroadcastZones"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid BroadcastZones"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Repeat, must be between 0-127"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Soundpath"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Time format, must be HH:mm"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Day format"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Description"))) + it.result( + objectmapper.writeValueAsString( + resultMessage( + "OK" + ) + ) + ) + } else it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to add schedule to database"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Language"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Contains unsupported BroadcastZones"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid BroadcastZones"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Repeat, must be between 0-127"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Soundpath"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Time format, must be HH:mm"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Day format"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Description"))) } delete("DeleteByIndex/{index}") { // delete by index @@ -806,93 +892,40 @@ class WebApp(val listenPort: Int, val userlist: List>, val if (db.scheduleDB.DeleteByIndex(index.toInt())) { db.scheduleDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - db.Add_Log("AAS","Deleted schedule bank with index $index") + db.Add_Log("AAS", "Deleted schedule bank with index $index") } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to delete schedule with index $index"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to delete schedule with index $index"))) } } } patch("UpdateByIndex/{index}") { // update by index val index = it.pathParam("index").toUIntOrNull() - if (index == null) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid index"))) - } else { + if (index!=null){ val sb = db.scheduleDB.List.find { xx -> xx.index == index } - if (sb == null) { - it.status(404).result(objectmapper.writeValueAsString(resultMessage("Schedule with index $index not found"))) - } else { - val json: JsonNode = objectmapper.readTree(it.body()) - if (json.isEmpty) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) - } else { - val _description = json.get("Description").asText("") - val _time = json.get("Time").asText("") - val _day = json.get("Day").asText("") - val _soundpath = json.get("Soundpath").asText("") - val _repeat = json.get("Repeat").asInt().toUByte() - val _enable = json.get("Enable").asBoolean() - val _broadcast_zones = json.get("BroadcastZones").asText("") - val _language = json.get("Language").asText("") - var changed = false - if (ValidString(_description) && _description != sb.Description) { - sb.Description = _description - changed = true - } - if (ValidString(_time) && _time != sb.Time) { - if (ValidScheduleTime(_time)) { - sb.Time = _time - changed = true - } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Time format, must be HH:mm"))) - return@patch - } - } - if (ValidString(_day) && _day != sb.Day) { - if (ValidScheduleDay(_day)) { - sb.Day = _day - changed = true - } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Day format"))) - return@patch - } - } - if (ValidString(_soundpath) && _soundpath != sb.Soundpath) { - sb.Soundpath = _soundpath - changed = true - } - if (_repeat != sb.Repeat) { - sb.Repeat = _repeat - changed = true - } - if (_enable != sb.Enable) { - sb.Enable = _enable - changed = true - } - if (ValidString(_broadcast_zones) && _broadcast_zones != sb.BroadcastZones) { - sb.BroadcastZones = _broadcast_zones - changed = true - } - if (ValidString(_language) && _language != sb.Language) { - if (Language.entries.any{ lang -> lang.name == _language }) { - sb.Language = _language - changed = true - } else { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Language"))) - return@patch - } - } - if (changed) { - if (db.scheduleDB.UpdateByIndex(index.toInt(), sb)) { + if (sb!=null){ + val json = objectmapper.readTree(it.body()) + val _description = json.get("Description").asText("") + val _time = json.get("Time").asText("") + val _day = json.get("Day").asText("") + val _soundpath = json.get("Soundpath").asText("") + val _repeat = json.get("Repeat").asInt().toUByte() + val _enable = json.get("Enable").asBoolean() + val _broadcast_zones = json.get("BroadcastZones").asText("") + val _language = json.get("Language").asText("") + val newsb = ScheduleBank(index, _description, _day, _time, _soundpath, _repeat, _enable, _broadcast_zones, _language) + if (newsb.isNotEmpty()){ + if (!sb.isEqual(newsb)){ + if (db.scheduleDB.UpdateByIndex(index.toInt(), newsb)){ db.scheduleDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - } else it.status(500) - .result(objectmapper.writeValueAsString(resultMessage("Failed to update schedule with index $index"))) - } else it.status(400) - .result(objectmapper.writeValueAsString(resultMessage("Nothing has changed for schedule with index $index"))) - } - } - } + } else it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to update schedule with index $index"))) + } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Nothing has changed for schedule with index $index"))) + } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Some fields are empty"))) + + } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Schedule with index $index not found"))) + } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid index"))) } get("ExportXLSX") { val xlsxdata = db.scheduleDB.Export_XLSX() @@ -906,13 +939,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val xlsxdata.write(out) } } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to export schedulebank to XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to export schedulebank to XLSX"))) } } post("ImportXLSX") { val uploaded = it.uploadedFile("file") if (uploaded == null) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) return@post } try { @@ -932,7 +967,7 @@ class WebApp(val listenPort: Int, val userlist: List>, val get("GetMessageAndBroadcastZones") { val result = object { val messages = db.messageDB.List - .filter { mb -> !mb.Message_Detail.contains("[") && !mb.Message_Detail.contains("]")} + .filter { mb -> !mb.Message_Detail.contains("[") && !mb.Message_Detail.contains("]") } .map { mb -> "${mb.Description} [${mb.ANN_ID}]" } val broadcastzones = db.broadcastDB.List } @@ -970,7 +1005,18 @@ class WebApp(val listenPort: Int, val userlist: List>, val val city_tags = json.get("city_tags").asText("") val messagebank_ann_id = json.get("messagebank_ann_id").asText("") val broadcastzones = json.get("broadcastzones").asText("") - if (ValidStrings(listOf(username, password, location, airline_tags, city_tags, messagebank_ann_id, broadcastzones))) { + if (ValidStrings( + listOf( + username, + password, + location, + airline_tags, + city_tags, + messagebank_ann_id, + broadcastzones + ) + ) + ) { if (!db.Username_exists(username)) { // check apakah ada airline tag yang tidak ada di soundbank val atags = airline_tags.split(";").map { it.trim() } @@ -1006,14 +1052,21 @@ class WebApp(val listenPort: Int, val userlist: List>, val ) if (db.userDB.Add(newuser)) { db.userDB.Resort() - ctx.result(objectmapper.writeValueAsString(resultMessage("OK") )) - } else ctx.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to add user to database"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Some ANN_ID not found in Messagebank") )) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Some broadcast zone tags not found in soundbank")) ) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Some city tags not found in soundbank"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Some airline tags not found in soundbank"))) - } else ctx.status(400).result(objectmapper.writeValueAsString("Username already exists")) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Not all fields have value"))) + ctx.result(objectmapper.writeValueAsString(resultMessage("OK"))) + } else ctx.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to add user to database"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Some ANN_ID not found in Messagebank"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Some broadcast zone tags not found in soundbank"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Some city tags not found in soundbank"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Some airline tags not found in soundbank"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString("Username already exists")) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Not all fields have value"))) } delete("DeleteByIndex/{index}") { // delete by index @@ -1025,17 +1078,18 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.userDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) db.Add_Log("AAS", "Deleted user with index $index") - } else it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to delete user with index $index"))) + } else it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to delete user with index $index"))) } } - patch("UpdateByIndex/{index}"){ ctx -> + patch("UpdateByIndex/{index}") { ctx -> // update by index val index = ctx.pathParam("index").toUIntOrNull() - if (index!=null){ + if (index != null) { val user = db.userDB.List.find { xx -> xx.index == index } - if (user!=null){ - val json : JsonNode = objectmapper.readTree(ctx.body()) - if (!json.isEmpty){ + if (user != null) { + val json: JsonNode = objectmapper.readTree(ctx.body()) + if (!json.isEmpty) { val _username = json.get("username").asText("") val _password = json.get("password").asText("") val _location = json.get("location").asText("") @@ -1043,14 +1097,36 @@ class WebApp(val listenPort: Int, val userlist: List>, val val _city_tags = json.get("city_tags").asText("") val _messagebank_ann_id = json.get("messagebank_ann_id").asText("") val _broadcastzones = json.get("broadcastzones").asText("") - if (ValidStrings(listOf(_username, _password, _location, _airline_tags, _city_tags, _messagebank_ann_id, _broadcastzones))) { - val _otherusername = db.userDB.List.find { xx -> xx.username.equals(_username, true) && xx.index != index } + if (ValidStrings( + listOf( + _username, + _password, + _location, + _airline_tags, + _city_tags, + _messagebank_ann_id, + _broadcastzones + ) + ) + ) { + val _otherusername = db.userDB.List.find { xx -> + xx.username.equals( + _username, + true + ) && xx.index != index + } if (_otherusername == null) { // belum ada user lain yang pakai username ini - val atags = _airline_tags.split(";").map { it.trim() }.filter { it.isNotEmpty() }.distinct() - val ctags = _city_tags.split(";").map { it.trim() }.filter { it.isNotEmpty() }.distinct() - val msgids = _messagebank_ann_id.split(";").map { it.trim() }.filter { it.isNotEmpty() }.distinct().mapNotNull { it.toUIntOrNull() } - val bzdesc = _broadcastzones.split(";").map { it.trim() }.filter { it.isNotEmpty() }.distinct() + val atags = _airline_tags.split(";").map { it.trim() } + .filter { it.isNotEmpty() }.distinct() + val ctags = + _city_tags.split(";").map { it.trim() }.filter { it.isNotEmpty() } + .distinct() + val msgids = _messagebank_ann_id.split(";").map { it.trim() } + .filter { it.isNotEmpty() }.distinct() + .mapNotNull { it.toUIntOrNull() } + val bzdesc = _broadcastzones.split(";").map { it.trim() } + .filter { it.isNotEmpty() }.distinct() val airline_tags = db.Get_AirlineCode_Tags() val city_tags = db.Get_City_Tags() @@ -1060,23 +1136,53 @@ class WebApp(val listenPort: Int, val userlist: List>, val if (ctags.all { tag -> city_tags.any { it == tag } }) { if (msgids.all { tag -> msgbankids.any { it == tag } }) { if (bzdesc.all { tag -> bzlist.any { it == tag } }) { - val editeduser = UserDB(index, _username, _password, _location, _airline_tags, _city_tags, _messagebank_ann_id, _broadcastzones) - if (!user.isEqual(editeduser)){ - if (db.userDB.UpdateByIndex(index.toInt(), editeduser)){ + val editeduser = UserDB( + index, + _username, + _password, + _location, + _airline_tags, + _city_tags, + _messagebank_ann_id, + _broadcastzones + ) + if (!user.isEqual(editeduser)) { + if (db.userDB.UpdateByIndex( + index.toInt(), + editeduser + ) + ) { db.userDB.Resort() - ctx.result(objectmapper.writeValueAsString(resultMessage("OK"))) + ctx.result( + objectmapper.writeValueAsString( + resultMessage("OK") + ) + ) - } else ctx.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to update user with index $index"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Nothing has changed for user with index $index"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Some broadcast zone is not found in Broadcast Zone list"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Some ANN_ID not found in Messagebank"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Some city tags not found in soundbank"))) - } else ctx.status(400).result(objectmapper.writeValueAsString("Some airline tags not found in soundbank")) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Username already exists for another user"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Not all fiels have value"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("User with index $index not found"))) - } else ctx.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid index"))) + } else ctx.status(500).result( + objectmapper.writeValueAsString(resultMessage("Failed to update user with index $index")) + ) + } else ctx.status(400).result( + objectmapper.writeValueAsString(resultMessage("Nothing has changed for user with index $index")) + ) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Some broadcast zone is not found in Broadcast Zone list"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Some ANN_ID not found in Messagebank"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Some city tags not found in soundbank"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString("Some airline tags not found in soundbank")) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Username already exists for another user"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Not all fiels have value"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("User with index $index not found"))) + } else ctx.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid index"))) } get("ExportXLSX") { val xlsxdata = db.userDB.Export_XLSX() @@ -1111,7 +1217,8 @@ class WebApp(val listenPort: Int, val userlist: List>, val .result(objectmapper.writeValueAsString(resultMessage("Failed to import user table from XLSX"))) } } catch (e: Exception) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) } } @@ -1140,19 +1247,18 @@ class WebApp(val listenPort: Int, val userlist: List>, val } } } else { - println("Invalid logdate=$logdate") - get1.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid logdate"))) + get1.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid logdate"))) } } get("ExportXLSX") { get1 -> val logdate = get1.queryParam("date") ?: "" val logfilter = get1.queryParam("filter") ?: "" - println("Export log to XLSX, date=$logdate, filter=$logfilter") if (ValiDateForLogHtml(logdate)) { val xlsxdata = if (ValidString(logfilter)) { - db.Export_Log_XLSX(logdate.replace('-','/'), logfilter) + db.Export_Log_XLSX(logdate.replace('-', '/'), logfilter) } else { - db.Export_Log_XLSX(logdate.replace('-','/'), "") + db.Export_Log_XLSX(logdate.replace('-', '/'), "") } if (xlsxdata != null) { get1.header( @@ -1164,12 +1270,14 @@ class WebApp(val listenPort: Int, val userlist: List>, val xlsxdata.write(out) } } else { - get1.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to export log to XLSX"))) + get1.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to export log to XLSX"))) } - } else get1.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid logdate"))) + } else get1.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid logdate"))) } } - path("BroadcastZones"){ + path("BroadcastZones") { get("List") { it.result(MariaDB.ArrayListtoString(db.broadcastDB.List)) } @@ -1185,28 +1293,34 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.broadcastDB.Get() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to truncate broadcast zones table"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to truncate broadcast zones table"))) } } post("Add") { - val json : JsonNode = objectmapper.readTree(it.body()) + val json: JsonNode = objectmapper.readTree(it.body()) val _description = json.get("description").asText("") val _soundchannel = json.get("SoundChannel").asText("") val _box = json.get("Box").asText("") val _relay = json.get("Relay").asText("") - if (ValidString(_description)){ - if (ValidString(_soundchannel)){ - if (ValidString(_box)){ - if (ValidString(_relay)){ - val newbp = BroadcastZones(0u,_description,_soundchannel,_box,_relay) - if (db.broadcastDB.Add(newbp)){ + if (ValidString(_description)) { + if (ValidString(_soundchannel)) { + if (ValidString(_box)) { + if (ValidString(_relay)) { + val newbp = BroadcastZones(0u, _description, _soundchannel, _box, _relay) + if (db.broadcastDB.Add(newbp)) { db.broadcastDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - } else it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to add broadcast zone to database"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Relay"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid Box"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid SoundChannel"))) - } else it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid description"))) + } else it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to add broadcast zone to database"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Relay"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid Box"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid SoundChannel"))) + } else it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid description"))) } delete("DeleteByIndex/{index}") { // delete by index @@ -1217,9 +1331,10 @@ class WebApp(val listenPort: Int, val userlist: List>, val if (db.broadcastDB.DeleteByIndex(index.toInt())) { db.broadcastDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) - db.Add_Log("AAS","Deleted broadcast zone with index $index") + db.Add_Log("AAS", "Deleted broadcast zone with index $index") } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to delete broadcast zone with index $index"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to delete broadcast zone with index $index"))) } } } @@ -1231,11 +1346,13 @@ class WebApp(val listenPort: Int, val userlist: List>, val } else { val bz = db.broadcastDB.List.find { xx -> xx.index == index } if (bz == null) { - it.status(404).result(objectmapper.writeValueAsString(resultMessage("Broadcast zone with index $index not found"))) + it.status(404) + .result(objectmapper.writeValueAsString(resultMessage("Broadcast zone with index $index not found"))) } else { val json: JsonNode = objectmapper.readTree(it.body()) if (json.isEmpty) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) } else { val _description = json.get("description").asText("") val _soundchannel = json.get("SoundChannel").asText("") @@ -1283,13 +1400,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val xlsxdata.write(out) } } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to export broadcast zones to XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to export broadcast zones to XLSX"))) } } post("ImportXLSX") { val uploaded = it.uploadedFile("file") if (uploaded == null) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) return@post } try { @@ -1298,16 +1417,18 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.broadcastDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to import broadcast zones from XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to import broadcast zones from XLSX"))) } } catch (e: Exception) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid XLSX file"))) } } } - path("SoundChannel"){ - get("List"){ + path("SoundChannel") { + get("List") { it.result(MariaDB.ArrayListtoString(db.soundchannelDB.List)) } get("SoundChannelDescriptions") { @@ -1319,10 +1440,11 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.soundchannelDB.Get() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to truncate sound channel table"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to truncate sound channel table"))) } } - patch("UpdateByIndex/{index}"){ + patch("UpdateByIndex/{index}") { val index = it.pathParam("index").toUIntOrNull() if (index == null) { @@ -1330,39 +1452,37 @@ class WebApp(val listenPort: Int, val userlist: List>, val } else { val sc = db.soundchannelDB.List.find { xx -> xx.index == index } if (sc == null) { - println("Sound channel with index $index not found") - it.status(404).result(objectmapper.writeValueAsString(resultMessage("Sound channel with index $index not found"))) + it.status(404) + .result(objectmapper.writeValueAsString(resultMessage("Sound channel with index $index not found"))) } else { val json: JsonNode = objectmapper.readTree(it.body()) - println("Received JSON: $json") if (json.isEmpty) { - println("UpdateByIndex with index=$index has empty body") - it.status(400).result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("UpdateByIndex with index=$index has empty body"))) } else { val _channel = json.get("description").asText("") val _ip = json.get("ip").asText("") - println("Update sound channel with index $index, channel=$_channel, ip=$_ip") - if (ValidString(_channel)){ - if (ValidIPV4(_ip)){ + if (ValidString(_channel)) { + if (ValidIPV4(_ip)) { if (_channel.equals(sc.channel) && _ip.equals(sc.ip)) { - println("Nothing has changed for sound channel with index $index") - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Nothing has changed for sound channel with index $index"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Nothing has changed for sound channel with index $index"))) return@patch } else { // cek apakah ada soundchannel lain yang pakai ip dan channel yang sama - val othersc = db.soundchannelDB.List.filter { sc -> sc.ip == _ip }.filter { sc -> sc.index != index } - if (othersc.isNotEmpty()){ - it.status(400).result(objectmapper.writeValueAsString(resultMessage("This IP address is already used by another sound channel"))) + val othersc = db.soundchannelDB.List.filter { sc -> sc.ip == _ip } + .filter { sc -> sc.index != index } + if (othersc.isNotEmpty()) { + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("This IP address is already used by another sound channel"))) } else { // ada sesuatu yang ganti val newsc = SoundChannel(0u, _channel, _ip) if (db.soundchannelDB.UpdateByIndex(index.toInt(), newsc)) { - println("Updated sound channel with index $index") db.soundchannelDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - println("Failed to update sound channel with index $index") it.status(500) .result(objectmapper.writeValueAsString(resultMessage("Failed to update sound channel with index $index"))) } @@ -1372,12 +1492,12 @@ class WebApp(val listenPort: Int, val userlist: List>, val } } else { - println("Invalid IP address") - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid IP address"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid IP address"))) } } else { - println("Invalid channel") - it.status(400).result(objectmapper.writeValueAsString(resultMessage("Invalid channel"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("Invalid channel"))) } } } @@ -1386,7 +1506,7 @@ class WebApp(val listenPort: Int, val userlist: List>, val } - get("ExportXLSX"){ + get("ExportXLSX") { val xlsxdata = db.soundchannelDB.Export_XLSX() if (xlsxdata != null) { it.header( @@ -1398,13 +1518,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val xlsxdata.write(out) } } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to export sound channel to XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to export sound channel to XLSX"))) } } - post("ImportXLSX"){ + post("ImportXLSX") { val uploaded = it.uploadedFile("file") if (uploaded == null) { - it.status(400).result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) return@post } try { @@ -1413,7 +1535,8 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.soundchannelDB.Resort() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to import sound channel from XLSX"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to import sound channel from XLSX"))) } } catch (e: Exception) { it.status(400) @@ -1422,17 +1545,18 @@ class WebApp(val listenPort: Int, val userlist: List>, val } } - path("QueuePaging"){ - get("List"){ + path("QueuePaging") { + get("List") { it.result(MariaDB.ArrayListtoString(db.queuepagingDB.List)) } - delete("List"){ + delete("List") { // truncate queue paging table if (db.queuepagingDB.Clear()) { db.queuepagingDB.Get() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to truncate queue paging table"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to truncate queue paging table"))) } } delete("DeleteByIndex/{index}") { @@ -1446,24 +1570,26 @@ class WebApp(val listenPort: Int, val userlist: List>, val it.result(objectmapper.writeValueAsString(resultMessage("OK"))) db.Add_Log("AAS", "Deleted queue paging with index $index") } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to delete queue paging with index $index"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to delete queue paging with index $index"))) } } } } - path("QueueTable"){ - get("List"){ + path("QueueTable") { + get("List") { it.result(MariaDB.ArrayListtoString(db.queuetableDB.List)) } - delete("List"){ + delete("List") { // truncate queue table if (db.queuetableDB.Clear()) { db.queuetableDB.Get() it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to truncate queue sound table"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to truncate queue sound table"))) } } delete("DeleteByIndex/{index}") { @@ -1478,21 +1604,22 @@ class WebApp(val listenPort: Int, val userlist: List>, val db.Add_Log("AAS", "Deleted queue sound with index $index") } else { - it.status(500).result(objectmapper.writeValueAsString(resultMessage("Failed to delete queue sound with index $index"))) + it.status(500) + .result(objectmapper.writeValueAsString(resultMessage("Failed to delete queue sound with index $index"))) } } } } - path("Settings"){ + path("Settings") { - get("SoundbankDirectory"){ + get("SoundbankDirectory") { val dir = _config.Get(configKeys.SOUNDBANK_DIRECTORY.key) it.result(objectmapper.writeValueAsString(resultMessage(dir))) } - post("SoundbankDirectory"){ - val json : JsonNode = objectmapper.readTree(it.body()) + post("SoundbankDirectory") { + val json: JsonNode = objectmapper.readTree(it.body()) val newdir = json.get("directory").asText("") - if (ValidString(newdir)){ + if (ValidString(newdir)) { _config.Set(configKeys.SOUNDBANK_DIRECTORY.key, newdir) _config.Save() Logger.info { "Changed Soundbank Directory to $newdir" } @@ -1504,20 +1631,21 @@ class WebApp(val listenPort: Int, val userlist: List>, val } - get("SoundbankResultList"){ + get("SoundbankResultList") { it.result(objectmapper.writeValueAsString(ListAudioFiles(Somecodes.SoundbankResult_directory))) } - get("SoundbankResultFile/{filename}"){ + get("SoundbankResultFile/{filename}") { //TODO recheck bener/gak cara downloadnya val filename = it.pathParam("filename") val filepath = Somecodes.SoundbankResult_directory.resolve(filename) - if (ValidFile(filename) && Files.isRegularFile(filepath)){ + if (ValidFile(filename) && Files.isRegularFile(filepath)) { it.header( - "Content-Disposition", - "attachment; filename=\"$filename\"") + "Content-Disposition", + "attachment; filename=\"$filename\"" + ) it.outputStream().use { out -> Files.newInputStream(filepath).use { inp -> inp.copyTo(out) @@ -1528,14 +1656,14 @@ class WebApp(val listenPort: Int, val userlist: List>, val } } - get("PagingResultList"){ + get("PagingResultList") { it.result(objectmapper.writeValueAsString(ListAudioFiles(Somecodes.PagingResult_directory))) } - get ("PagingResultFile/{filename}"){ + get("PagingResultFile/{filename}") { val filename = it.pathParam("filename") val filepath = Somecodes.PagingResult_directory.resolve(filename) - if (ValidFile(filename) && Files.isRegularFile(filepath)){ + if (ValidFile(filename) && Files.isRegularFile(filepath)) { it.header("Content-Disposition", "attachment; filename=\"$filename\"") it.outputStream().use { out -> Files.newInputStream(filepath).use { inp -> @@ -1547,12 +1675,7 @@ class WebApp(val listenPort: Int, val userlist: List>, val } } - get("Messages"){ - val messages = db.messageDB.List - it.result(objectmapper.writeValueAsString(messages)) - } - - get("FISCode"){ + get("FISCode") { //TODO get FIS code val value = object { //get from config file @@ -1565,15 +1688,15 @@ class WebApp(val listenPort: Int, val userlist: List>, val it.result(objectmapper.writeValueAsString(value)) } - post ("FISCode") { + post("FISCode") { //TODO set FIS code - val json : JsonNode = objectmapper.readTree(it.body()) + val json: JsonNode = objectmapper.readTree(it.body()) val _gop = json.get("GOP").asText("") val _gbd = json.get("GBD").asText("") val _gfc = json.get("GFC").asText("") val _fld = json.get("FLD").asText("") - if (ValidString(_gop) && ValidString(_gbd) && ValidString(_gfc) && ValidString(_fld)){ + if (ValidString(_gop) && ValidString(_gbd) && ValidString(_gfc) && ValidString(_fld)) { // save to config file _config.Set(configKeys.REMARK_GOP.key, _gop) _config.Set(configKeys.REMARK_GBD.key, _gbd) @@ -1581,12 +1704,68 @@ class WebApp(val listenPort: Int, val userlist: List>, val _config.Set(configKeys.REMARK_FLD.key, _fld) _config.Save() Logger.info { "Changed FIS Codes" } + db.Add_Log("AAS", "Save FIS Codes Message: GOP=$_gop, GBD=$_gbd, GFC=$_gfc, FLD=$_fld") it.result(objectmapper.writeValueAsString(resultMessage("OK"))) } else { it.status(400) .result(objectmapper.writeValueAsString(resultMessage("Invalid FIS code value"))) } } + post("UploadSoundbank/{language}/{voice}/{category}") { + val language = it.pathParam("language") + val voice = it.pathParam("voice") + val category = it.pathParam("category") + + val uploaded = it.uploadedFiles() + if (ValidString(language) && Language.entries.any{ lang -> lang.name == language}) { + if (ValidString(voice) && VoiceType.entries.any{ vtype -> vtype.name == voice}) { + if (ValidString(category) && Category.entries.any{ cat -> cat.name == category}) { + if (uploaded.isNotEmpty()) { + val targetdir = Somecodes.SoundbankDirectory( + Language.valueOf(language), + VoiceType.valueOf(voice), + Category.valueOf(category) + ) + if (!Files.isDirectory(targetdir)) Files.createDirectories(targetdir) + val successfiles = mutableListOf() + val failedfiles = mutableListOf() + uploaded.forEach { ff -> + val targetfile = targetdir.resolve(ff.filename()) + try { + Files.newOutputStream(targetfile).use { out -> + ff.content().use { inp -> + inp.copyTo(out) + } + } + Logger.info { "Uploaded soundbank file to ${targetfile.toAbsolutePath()}" } + successfiles.add(ff.filename()) + } catch (e: Exception) { + Logger.error { + "Failed to upload soundbank file to ${targetfile.toAbsolutePath()}: ${e.message}" + } + failedfiles.add(ff.filename()) + } + + } + if (successfiles.size==uploaded.size){ + it.result(objectmapper.writeValueAsString(resultMessage("All files uploaded successfully: ${successfiles.joinToString(", ")}"))) + } else { + it.result(objectmapper.writeValueAsString(resultMessage("Some files uploaded successfully: ${successfiles.joinToString(", ")}, failed: ${failedfiles.joinToString(", ")}"))) + } + } else { + it.status(400) + .result(objectmapper.writeValueAsString(resultMessage("No file uploaded"))) + } + } else { + it.status(400).result(objectmapper.writeValueAsString(resultMessage("Category parameter is invalid"))) + } + } else { + it.status(400).result(objectmapper.writeValueAsString(resultMessage("VoiceType parameter is invalid"))) + } + } else { + it.status(400).result(objectmapper.writeValueAsString(resultMessage("Language parameter is invalid"))) + } + } } } } @@ -1599,13 +1778,10 @@ class WebApp(val listenPort: Int, val userlist: List>, val //val user = ctx.sessionAttribute("user") val user = ctx.cookie("aas-user") if (user == null) { - println("Cookie user not found, redirecting to login.html") ctx.redirect("login.html") } val foundUser = userlist.find { it.first == user } - println("Checking user=$user, foundUser=$foundUser") if (foundUser == null) { - println("User not found in userlist, redirecting to login.html") ctx.redirect("login.html") } }