Private
Public Access
1
0

Update version to 0.2.1, add player color retrieval, and enhance train trip statistics

Performance improvments for power stats
This commit is contained in:
Jan Grießhaber
2026-01-04 01:37:25 +01:00
parent 9b608fc412
commit f40e219a2e
8 changed files with 108 additions and 15 deletions

View File

@@ -1,6 +1,6 @@
{ {
"Lua.workspace.userThirdParty": [ "Lua.workspace.userThirdParty": [
"c:\\Users\\jangr\\AppData\\Roaming\\Code\\User\\workspaceStorage\\d5b7556f3ceaa76c3801170429d1766d\\justarandomgeek.factoriomod-debug\\sumneko-3rd" "c:\\Users\\jangr\\AppData\\Roaming\\Code\\User\\workspaceStorage\\f0146bacf23a7548830b73867851c66a\\justarandomgeek.factoriomod-debug\\sumneko-3rd"
], ],
"Lua.workspace.checkThirdParty": "ApplyInMemory", "Lua.workspace.checkThirdParty": "ApplyInMemory",
"factorio.versions": [ "factorio.versions": [

View File

@@ -44,6 +44,7 @@ script.on_init(function ()
storage.constructedEntites = {} storage.constructedEntites = {}
storage.deconstructedEntities = {} storage.deconstructedEntities = {}
storage.trainStats = {} storage.trainStats = {}
storage.networkCache = {}
---@type LuaTrain[] ---@type LuaTrain[]
storage.trains = {} storage.trains = {}
@@ -102,6 +103,7 @@ script.on_configuration_changed(function()
storage.playerDeathCause = storage.playerDeathCause or {} storage.playerDeathCause = storage.playerDeathCause or {}
storage.constructedEntites = storage.constructedEntites or {} storage.constructedEntites = storage.constructedEntites or {}
storage.deconstructedEntities = storage.deconstructedEntities or{} storage.deconstructedEntities = storage.deconstructedEntities or{}
storage.networkCache =storage.networkCache or {}
storage.trains = storage.trains or {} storage.trains = storage.trains or {}
---@type table<uint, trainStat> ---@type table<uint, trainStat>
storage.trainStats = storage.trainStats or {} storage.trainStats = storage.trainStats or {}

View File

@@ -8,6 +8,17 @@ function GetMods()
helpers.send_udp(udpAddress, modstring,serverIndex) helpers.send_udp(udpAddress, modstring,serverIndex)
end end
function GetPlayerColors()
local colorParts = {}
colorParts[#colorParts+1] = "---player-colors---\n"
for index, player in pairs(game.players) do
local colorSettings = player.color
colorParts[#colorParts+1] = ("%d:%s:%d:%d:%d:%d"):format(index,player.name,colorSettings.r,colorSettings.g,colorSettings.b,colorSettings.a)
end
return table.concat(colorParts,"\n")
end
function GetPlayerKills() function GetPlayerKills()
local killParts = {} local killParts = {}
killParts[#killParts+1] = "---player-kills---\n" killParts[#killParts+1] = "---player-kills---\n"

View File

@@ -1,6 +1,6 @@
{ {
"name": "factorio-metrics-exporter", "name": "factorio-metrics-exporter",
"version": "0.2.0", "version": "0.2.1",
"title": "Prometheus Metrics Exporter", "title": "Prometheus Metrics Exporter",
"author": "Jan Grießhaber", "author": "Jan Grießhaber",
"contact": "jan@griesshaber.systems", "contact": "jan@griesshaber.systems",

View File

@@ -33,7 +33,10 @@ end
function SendLogisticStats() function SendLogisticStats()
if options.enableRobots then if options.enableRobots then
local send = GetAllLogisticGrids().."\n"..GetLogisticNetworkContents() local returnParts = {}
helpers.send_udp(udpAddress,send,serverIndex) returnParts[#returnParts+1] = GetAllLogisticGrids()
returnParts[#returnParts+1] = GetLogisticNetworkContents()
--local send = GetAllLogisticGrids().."\n"..GetLogisticNetworkContents()
helpers.send_udp(udpAddress,table.concat(returnParts,"\n"),serverIndex)
end end
end end

View File

@@ -1,7 +1,11 @@
function AddPowerPole(event) function AddPowerPole(event)
local e = event.entity local e = event.entity
if e and e.valid and e.type == "electric-pole" then if e then
storage.representativePoles[e.unit_number] = e storage.representativePoles[e.unit_number] = e
-- Update cache with new network
if e.electric_network_id then
storage.networkCache[e.electric_network_id] = e
end
end end
end end
@@ -9,31 +13,40 @@ function RemovePowerPole(event)
local e = event.entity local e = event.entity
if e then if e then
storage.representativePoles[e.unit_number] = nil storage.representativePoles[e.unit_number] = nil
-- Invalidate cache - force rebuild to find new representative if needed
storage.networkCache = nil
end end
end end
function GetNetworks() function GetNetworks()
local networks = {} -- Return cached networks if available, otherwise rebuild
if storage.networkCache then
return storage.networkCache
end
local networks = {}
for _, pole in pairs(storage.representativePoles) do for _, pole in pairs(storage.representativePoles) do
if pole.valid then if pole.valid then
local net = pole.electric_network_id local netID = pole.electric_network_id
if net then if netID then
networks[net] = pole networks[netID] = pole
end end
end end
end end
storage.networkCache = networks
return networks return networks
end end
function ScanNetworks() function ScanNetworks()
storage.representativePoles = {} storage.representativePoles = {}
storage.networkCache = {}
for _, surface in pairs(game.surfaces) do for _, surface in pairs(game.surfaces) do
for _, pole in pairs(surface.find_entities_filtered{type = "electric-pole"}) do for _, pole in pairs(surface.find_entities_filtered{type = "electric-pole"}) do
if pole.valid and pole.electric_network_id then if pole.valid and pole.electric_network_id then
storage.representativePoles[pole.unit_number] = pole storage.representativePoles[pole.unit_number] = pole
storage.networkCache[pole.electric_network_id] = pole
end end
end end
end end

View File

@@ -50,8 +50,11 @@ function GetEstimatedResearchTime()
local returnSpeed = "---research-speed---\n"..totalSpeed.."\n" local returnSpeed = "---research-speed---\n"..totalSpeed.."\n"
local returnTime = "---research-time---\n"..estimatedSeconds.."\n" local returnTime = "---research-time---\n"..estimatedSeconds.."\n"
local returnNameID = "---research-info---\n"..researchName.."\n" local returnNameID = "---research-info---\n"..researchName.."\n"
local returnProgress = "---research-progress---\n"..playerForce.research_progress.."\n"
return returnSpeed..returnTime..returnNameID log("Reseach remaining "..returnTime)
return returnSpeed..returnTime..returnNameID..returnProgress
end end
function UpdateLabInfos() function UpdateLabInfos()

View File

@@ -79,6 +79,8 @@ end
---@class trainStat ---@class trainStat
trainStat = { trainStat = {
trainID = 0,
trainName = "",
lastInventory={}, lastInventory={},
currentInventory={}, currentInventory={},
lastState = 0, lastState = 0,
@@ -87,7 +89,15 @@ trainStat = {
totalCargoCount = 0, totalCargoCount = 0,
totalCargo = {}, totalCargo = {},
lastArrivalTime = 0, lastArrivalTime = 0,
currentArrivalTime = 0 currentArrivalTime = 0,
---@type trip
trips = {}
}
---@class trip
trip = {
startStation= {},
endStation = {},
timeTaken = 0
} }
---@param inv table[] ---@param inv table[]
@@ -150,9 +160,13 @@ function onTrainStateChange(event)
local trainID = train.id local trainID = train.id
---@type trainStat ---@type trainStat
local stat = storage.trainStats[trainID] or {} local stat = storage.trainStats[trainID] or {}
stat.trips = stat.trips or {}
stat.trainID = trainID
stat.trainName = GetTrainName(train)
if event.train.state == defines.train_state.wait_station then if event.train.state == defines.train_state.wait_station then
if train.station.unit_number == stat.lastStationUnitNumber then return end
stat.lastStationUnitNumber = stat.currentStationUnitNumber stat.lastStationUnitNumber = stat.currentStationUnitNumber
stat.lastInventory = stat.currentInventory stat.lastInventory = stat.currentInventory
stat.lastArrivalTime = stat.currentArrivalTime stat.lastArrivalTime = stat.currentArrivalTime
@@ -161,11 +175,19 @@ function onTrainStateChange(event)
stat.currentInventory = train.get_contents() stat.currentInventory = train.get_contents()
stat.currentArrivalTime = game.tick stat.currentArrivalTime = game.tick
if stat.lastStationUnitNumber
and stat.currentStationUnitNumber then
local tripIdentifier = tostring(stat.lastStationUnitNumber) .. tostring(stat.currentStationUnitNumber)
stat.trips[tripIdentifier] = {
startStation = game.get_entity_by_unit_number(stat.lastStationUnitNumber),
endStation = game.get_entity_by_unit_number(stat.currentStationUnitNumber),
timeTaken = stat.currentArrivalTime-stat.lastArrivalTime}
end
if stat.currentInventory and stat.lastInventory then if stat.currentInventory and stat.lastInventory then
--Get Total Cargo --Get Total Cargo
for key, value in pairs(inventoryDiff(stat.lastInventory,stat.currentInventory)) do for key, value in pairs(inventoryDiff(stat.lastInventory,stat.currentInventory)) do
stat.totalCargoCount = (stat.totalCargoCount or 0) + value.delta stat.totalCargoCount = (stat.totalCargoCount or 0) + math.abs(value.delta)
end end
end end
@@ -174,25 +196,64 @@ function onTrainStateChange(event)
--log("inEvent") --log("inEvent")
end end
function GetTrainTripStats()
local tripParts = {}
tripParts[#tripParts+1] = "---train-trips---\n"
for trainID,stats in pairs(storage.trainStats) do
for _,trip in pairs(stats.trips or {}) do
tripParts[#tripParts+1] =
("%d:%s:%s:%s:%d"):format(
trainID,
stats.trainName,
trip.startStation.backer_name,
trip.endStation.backer_name,
trip.timeTaken)
end
end
return table.concat(tripParts,"\n")
end
function GetTrainStatistics() function GetTrainStatistics()
local trainParts = {} local trainParts = {}
trainParts[#trainParts+1] = "---train-total-statistics---\n" trainParts[#trainParts+1] = "---train-total-statistics---\n"
for trainID, stat in pairs(storage.trainStats) do for trainID, stat in pairs(storage.trainStats) do
trainParts[#trainParts+1] = ("%d:%s:%d"):format(trainID,GetTrainName(storage.trains[trainID]),stat.totalCargoCount or 0) trainParts[#trainParts+1] = ("%d:%s:%d"):format(trainID,stat.trainName,stat.totalCargoCount or 0)
end end
return table.concat(trainParts,"\n") return table.concat(trainParts,"\n")
end end
---Purges stats for trains that no longer exist
---@param trainID integer|nil If provided, purges only that train. If nil, purges all dead trains.
function PurgeDeadTrainStats(trainID)
if trainID then
-- Purge a specific train if it doesn't exist
if not storage.trains[trainID] then
storage.trainStats[trainID] = nil
return true
end
else
-- Purge all trains not in storage.trains
for statTrainID in pairs(storage.trainStats) do
if not storage.trains[statTrainID] then
storage.trainStats[statTrainID] = nil
end
end
end
return false
end
function SendTrainStats() function SendTrainStats()
if options.enableTrains then if options.enableTrains then
ScanTrains() ScanTrains()
PurgeDeadTrainStats()
local returnParts = {} local returnParts = {}
returnParts[#returnParts+1] = GetTrainPlayerKills() returnParts[#returnParts+1] = GetTrainPlayerKills()
returnParts[#returnParts+1] = GetTrainTotalKills() returnParts[#returnParts+1] = GetTrainTotalKills()
returnParts[#returnParts+1] = GetTrainStates() returnParts[#returnParts+1] = GetTrainStates()
returnParts[#returnParts+1] = GetTrainStatistics() returnParts[#returnParts+1] = GetTrainStatistics()
returnParts[#returnParts+1] = GetTrainsInDepot() returnParts[#returnParts+1] = GetTrainsInDepot()
returnParts[#returnParts+1] = GetTrainTripStats()
helpers.send_udp(udpAddress,table.concat(returnParts,"\n"),serverIndex) helpers.send_udp(udpAddress,table.concat(returnParts,"\n"),serverIndex)
end end
end end