[Beta] Deferred Lua Event Handling

If events are hooked in via Event:Connect(), they should all process as intended in the correct order, just not at the exact moment they occured.

2 Likes

I think Roblox has severely underestimated the impact that this change will have on so many different types of code. This isn’t just a minor change that will only affect a few people, this is literally changing the execution order of all event-based code that has ever been written on the Roblox platform, and this change needs to be treated with a lot more weight.

This is bound to break/alter so many things, and it is extremely difficult to narrow down every single piece of code that will be affected in some way. Even in cases where it won’t necessarily cause errors, this will introduce so much undefined and untested behavior in many existing games.

I have spent so much time writing the logic for my existing games and making sure that it all runs exactly the way I intended it to. But with this, Roblox would just be throwing a wrench into all of that and saying “well, tough, now you need to revisit all of your code and debug it all over again.”

There needs to be a way for us to maintain backwards compatibility. Roblox cannot force such a broad change that will have so many unintended consequences, placing the burden on us to audit and fix all of our existing code that we’ve ever written on the platform.

47 Likes

I’m pretty sure you’re correct on this, I’m just not confident it is the intended impact. Granted it’s a corner case, and my projects are small enough that I should be able to get rid of my usage that is similar to this, but I worry for others.

2 Likes

but you can opt-in by changing SignalBehavior on workspace to ‘Deferred’. Eventually we plan to phase out the existing behavior and change the default behavior to deferred, but we haven’t set a date just yet as we know this change is likely to affect some of you.

That’s why this is an opt-in change, the default behavior will eventually change but if this is a big deal, you can change a property of workspace (assuming it wouldn’t already maintain ‘immediate’ for older games)

@TripTrapp84 doubt on that one, with the old way you can operate under the assmumption that it will be firing consistently fast. lua rarely slows down, the scheduler will though due to throttling and abuse, if anything it’s going to be more unpredictable with deferred lol

@Cindering

It seems like this is only a temporary option and that they’re planning to completely remove the existing behavior at a later point:

:ok_hand:

2 Likes

It seems like this is only a temporary option and that they’re planning to completely remove the existing behavior at a later point:

7 Likes

Setting the SignalBehavior to Deferred causes off-by-one frame errors in the core camera scripts itself! It’s hard to quantify, but I’ve created steps to reproduce an experiment that shows this is happening:

It feels really sluggish to pan the camera on mobile devices if the framerate drops below 30 FPS.

5 Likes

This right here in almost perfect wording is why I left this platform years ago & only participate in the DevForum. The amount of times that I’ve had to rewrite a game over stuff like this that changes out of nowhere and I, as a developer, am forced to deal with it is quite annoying.

Even though it’s opt-in, it’s going to replace current functionality eventually. So, regardless of when someone decides to change it, I’d still have to look back at my code and fix it.

The theory the possible positives behind this is actually really good considering that it’ll make larger servers much more manageable, prevent frame latency, etc but, it’s highly frustrating that there’s no backwards-compatibility which would’ve been nice.

10 Likes

I read one of the comments which explained something to me, I thought this delayed until renderstepped since it was #1 on their list of defered-to events, but now I see it will defer to the end of your event connected lua code almost always. I agree now, this is definitely a bad change, not having snappy code execution is worse when the alternative is code execution at the end always. It’s the same thing but removes any guarantee that what you wanted to happen has happened. Along with lag being a much bigger issue now because of the change

2 Likes

It’s kind of difficult to prioritize making sure our code is compatible with this change if don’t know when the change will occur. Can we get any sort of rough timeline of when this will be rolled out? Days, weeks, months, years?

1 Like

Honestly, I’m not sure where I got the idea from, but I have always thought this was how events worked :flushed:

I have personally never had this happen to me, but knowing that Roblox does this is why I know I won’t always stay on Roblox. On other engines, the only way for an update to break your game is for you to do it yourself. But on Roblox, if you don’t touch your game for years it will end up broken in one way or another just because of even extremely small behavior changes. Not to mention that it will look completely different because of graphics updates (such as the removal of outlines, the recent AO changes, and the new materials that they plan to force onto existing games soon). I like developing on Roblox, but you kind of don’t get as much of a say in your game as you do on other engines.

Also, what’s kind of funny about this update is that, aside from breaking a lot of games, it even breaks some of the Core scripts.

6 Likes

How does this affect Remotes?

local remote = game.ReplicatedStorage:WaitForChild("RemoteEvent")
print("A")
-- Assuming queued events.
remote.OnClientEvent:Connect(function()
	print("B")
end)
print("C")

With Immediate mode, this would print A, B, C. I assume that, with Deferred mode, this will print A, C, B?

Answer: Yes, queued remote events are deferred.


What about the following?

local remote = game.ReplicatedStorage:WaitForChild("RemoteEvent")
print("A")
remote.OnClientEvent:Connect(function()
	print("B")
end)
remote.OnClientEvent:Connect(function()
	print("C")
end)
print("D")

With Deferred, will the remote’s queue be flushed before listener C is connected, or will both listeners receive queued events?

Answer: The queue is flushed by the first connected listener; listener C will not receive events.


Moreover, when do deferred threads run in relation to non-deferred threads? Consider threads A and B. A produces a deferred thread AD, and B produces BD. There are several ways these threads could be ordered:

Per-thread defer:

A
AD
B
BD

Cumulative defer:

A
B
AD
BD

Answer: Deferred threads are accumulated.

15 Likes

Ouch. Care to share more details? Maybe there are options?

1 Like

I’ve proposed a way to maintain backwards compatibility in existing places, while still allowing this new behavior:

This change is about as breaking as enabling StreamingEnabled on a place that wasn’t designed for it, and therefore I think should be re-considered to be a boolean property, rather than an enum with a “Default” option that can suddenly break existing games.

17 Likes

I just tested this change to see how much it affected my game. It’s unplayable now.

As somebody else mentioned, this feels very similar to forcing a game to use StreamingEnabled.

I’m sure this update has many benefits that go over my head, but backwards compatibility would be a nice thing to keep for projects developers don’t necessarily want to rewrite code for.

10 Likes

Honestly, you know what, I think I may just want to say that, understanding the applications, understanding the benefits, understanding the system:

This is a bad update.

There is no reason whatsoever that this change should come about like this. Sure, maybe it gives some minor performance benefits in the long run, sure, maybe it helps clean up some messy part of the engine. But the lack of backwards compatibility and the sheer impact of this change makes it one I think should never, ever, ever be made. I understand you guys want to improve the engine in new and exciting ways, but there is a limit to what you can do. Businesses don’t tear down an office to replace the floors, and that’s what this is. Ripping out basic core functionality and replacing it, just to get some small benefits. This update breaks, and I don’t think I’m overstating this, probably every existing use of an event on Roblox. At the very least, it adds unintended behavior. Heck, this update breaks the core scripts, one of the most universal pieces of Roblox games.

The existing functionality is fine. Better yet, it’s already in use. Everyone understands and accepts how it works. Don’t change that, please.

13 Likes

Edit: I’ve read zeuxcg’s update and feel better about this now, however I am still not super happy.

Here’s a suggestion. Stop forcing these updates on us. Not all code that will be affected by this is “bad code that just needs updating”. In addition, this has the potential to break plenty of games in ways that will be very difficult to debug for less experienced programmers.

These kinds of updates throw us under the bus because Roblox is basically saying “We made a change, now you have to opt out to give yourself a month to fix all of your games before we force this change”

This is not a critical update. It’s not like filteringenabled.

How can you refuse to give us more advanced settings and features because it would be “too difficult for new users and kids” yet you constantly make these changes and expect inexperienced kids to work around problems you create?

Forcing this on is is an unprofessional and naïve move.

27 Likes

As someone said above it broke PlayerAdded. I can’t test as much as my game doesn’t begin setting up players because of this. Probably should be fixed soonish. Also gonna have to say that this should be optional. I don’t understand forcing updates like these where it doesn’t seem like it needs to be mandatory? It looks like more needless work for us to keep up with updates a lot of us don’t need/want.

I think you guys would get better feedback if you explain reasoning a bit more as to why you make these things mandatory? Give developers the freedom to play around with their stuff and not have to keep up with whatever it being pushed all the time.

7 Likes

Great. Imagine telling people that Roblox broke their code and it’s their job to fix it and that they need to add their own modules for fast spawning and to fix player added. How hard is it for Roblox to just let us have a permanent toggle? Oh, boo hoo they have to maintain some extra code. Who cares. We’re the source of income on the platform. Quit making us suffer please and let us decide for ourselves how our code should work.

15 Likes

I just tried this on my experience and well, 1/3 of our game became unplayable. I hope this stays opt-in permanently because it’s a bit tiresome trying to adapt and constantly make a workaround for behaviour changes when this vital development time should be spent on making features.

18 Likes

This change temporarily broke many modules I use that I myself do not maintain. I hope this stays opt-in in the case that old, usable code can “expire”. What other option do I have other than to rewrite all the broken code from scratch?

2 Likes