public void OnUpdate(NodeGeometry nodeGeometry)
        {
#if DEBUG
            Log._Debug($"TrafficLightSimulation: OnUpdate @ node {NodeId} ({nodeGeometry.NodeId})");
#endif

            if (!IsManualLight() && !IsTimedLight())
            {
                return;
            }

            if (!nodeGeometry.IsValid())
            {
                // node has become invalid. Remove manual/timed traffic light and destroy custom lights
                Constants.ManagerFactory.TrafficLightSimulationManager.RemoveNodeFromSimulation(NodeId, false, false);
                return;
            }

            if (!Flags.mayHaveTrafficLight(NodeId))
            {
                Log._Debug($"Housekeeping: Node {NodeId} has traffic light simulation but must not have a traffic light!");
                Constants.ManagerFactory.TrafficLightSimulationManager.RemoveNodeFromSimulation(NodeId, false, true);
                return;
            }

            ICustomSegmentLightsManager customTrafficLightsManager = Constants.ManagerFactory.CustomSegmentLightsManager;

            foreach (SegmentEndGeometry end in nodeGeometry.SegmentEndGeometries)
            {
                if (end == null)
                {
                    continue;
                }

#if DEBUG
                Log._Debug($"TrafficLightSimulation: OnUpdate @ node {NodeId}: Adding live traffic lights to segment {end.SegmentId}");
#endif

                // add custom lights

                /*if (!customTrafficLightsManager.IsSegmentLight(end.SegmentId, end.StartNode)) {
                 *      customTrafficLightsManager.AddSegmentLights(end.SegmentId, end.StartNode);
                 * }*/

                // housekeep timed light
                ICustomSegmentLights lights = customTrafficLightsManager.GetSegmentLights(end.SegmentId, end.StartNode);
                if (lights == null)
                {
                    Log.Warning($"TrafficLightSimulation.OnUpdate() @ node {NodeId}: Could not retrieve live segment lights for segment {end.SegmentId} @ start {end.StartNode}.");
                    continue;
                }
                lights.Housekeeping(true, true);
            }

            // ensure there is a physical traffic light
            Constants.ServiceFactory.NetService.ProcessNode(NodeId, delegate(ushort nodeId, ref NetNode node) {
                Constants.ManagerFactory.TrafficLightManager.AddTrafficLight(NodeId, ref node);
                return(true);
            });

            TimedLight?.OnGeometryUpdate();
            TimedLight?.Housekeeping();
        }