As the title says I am having trouble reducing the server load for my game, which is hero reworks for Wreckingball, Widowmaker, and Mercy. This is my code:: 1H643
For starters, let me say I am by NO MEANS fluent in programming. HOWEVER, I have been tinkering with the Workshop since it’s initial release in OW1 2017/2018? & have made several games using this. Including my main i’ve worked on since the start. With a total Element Count maxed out ~32,600.
Anyways, something I learned a while ago is, the workshop doesn’t like to execute multiple actions in the same frame. Now with that being said, not all actions are created equal. Some “weight” more than others. Setting a Variable/Array is far less resource intensive then say Creating an effect or any action that physically manipulate the characters in the game. (Start Accelerating, Start Scaling, Set Status, etc…)
My rule of thumb is, try to throw in a Wait action every 5 - 10 actions (depending on what those 5-10 actions are “their weight”) This Wait actions doesn’t have to be long. [.016s] is enough to have the following Actions execute on a new frame.
For example. you have 3 rules near the top:
Display list of mercy changes
“” Ball changes
“” Widow changes
where IN these rules, you have 12+ Destroy HUD Text immediately followed by 4 Create HUD Text (+ the variable to save Last Text ID). So essentially, you have ~20 actions per Rule, TIMES 3 rules, so 60 actions happening all in the same frame. I’m honestly amazed it doesn’t crash the second you Call the rules (is comm Voice line 1 + is button held). And keep in mind, these Rules are all Ongoing Each Player, so now take that 60 actions and multiply it by the number of players in the match…
My suggestion, go through ALL your Rules, and wherever you have more then 10 actions executing in a row, throw a Wait action. Do keep in mind, several Rules can execute at the same time, so even thou any 1 Rule is (after you add the Wait actions that is) limited to 10 actions, several other Rules can be triggered at very instance, thus the Workshop Server is executing upteen actions w/in that single Frame (.016s).
It’s a tedious process if playing around w/ the code, and seeing what works. I’ve found what works for me. Best of luck! Cheers.
It was May 2019, around 2018 the Custom Game browser was released without scripting functionality. There are several guidelines of reducing server load, from the workshop devs team perspective, and if some are dwelling in programming and IT, as they got aware of problems regarding multiple execution on a single frame causes some stress on server load, they introduced a year or so later in 2020, a new Rule/Event type called subroutines, they allow execution of code instruction asynchronously or in parallel and in context it means though some action may still be problematic at executing in one frame, subroutines allow us to execute the subroutine and 1 regular rule in parallel which mimics in a thread-safe manner to run the same or different weigthed actions in one frame.
i DO remember them saying something about the Subroutines being “more efficient”. & i have used them in the own games. However, i find them more confusing to use. And for someone who’s either New to the workshop OR doesn’t play with it much, Subroutines just add another layer of confusion. But YES, you are correct, everything you said.
I just find throwing in the Wait actions far more simple to grasp, w/ decant working results. Thanks. Cheers!
You know… things are suddenly making A LOT more sense.
I always was intrigued by that problem of yours, as unless you’re using large data structures, having a script of this size is already greater of a challenge than making it run.
You really managed to kill my interest in your problem with the phrasing of that post alone.
Also important to know, after subroutines at 2021 or a bit earlier, i don’t remember excactly they gave us even more supoort in reducing execution steps for loop iterations that invovle arrays and their for large amount of data well i consider 999 elemnts not as large but for the devs it is a limit, speaking of element count and bandwith size. In the end the high order function Mapped Array with the help of SIMD instruction, Current Array Element and Current Array Index (lambda captures), we can mutate for example numeric elemnts of an array with one instruction at the same time without using any loop, or create interactions between two arrays (adding them together) and get a resulting array in one go with it.
PS: Warning if the arrays of different sizes are multiplied or divided by each other, the resulting array may multiply or divide elements with 0 from the smaller sized array.
Problem? What problem? & you were interested in something of mine in the 1st place? Lol i feel…honored?
If you’re laughing at the number of wait actions i use, all i can say is, it made a difference way back when i Didn’t do that. I know nothing on the “proper” ways to code. I trial and error test to see what works, & what doesn’t. Adding Waits worked, & my game hasn’t crashed since…
I started my whole tangent off with a disclaimer. So everything i say Should be taken with a grain of salt.
You were literally on here several times already looking for alternative ways to do the things you did. Options were brought up, many were hit with the problem of size compared to your active solution.
I wish I could…
But all I can do now it tremble at the thought of having to deal with the nightmare that would be untangling that mess of asynchronous execution to maintain reasonable performance as well as intended behavior while reducing the total element count.
I am not surprised about the result,
just absolutely gutted at the thought of making changes or adding pieces to existing things because they’re frequently desynchronizing if not kept in check.
But yes, I was, until I read that.
I always find it interesting going through others peoples scripts to see maybe even rework how they achieved something within the confines of the Workshop either out of own interest to to make genuine improvements.
Having you post about something and then mention the size always made me wonder how you managed to reach that total element count as you didn’t seem to mention any large sets of data you were storing to work with in the script, that’s where my initial intrigue came from.
(“Were you just severely inefficient or did you achieve something genuinely complex within the workshop which on it’s own is heavy on the element count?”)
…Just out of curiosity, what are you expecting a bunch of random scripts, each with its own unique task/effect, to be “in sync” with? Is there some server clock cycle these little scripts are ‘supposed’ to line up with?
You honestly telling me, that most people playing around with the Workshop, aim for the possibility that IF ALL rules executed at the same time, the server would be able to handle it? Or rather, that all the Rules that make up someone’s game, should in somehow influence one another w/out bottle necking the server’s ability to process the events?
Idk about you, but my goal (and i’d assume for most others on this forum) is to create some unique little mini game as a fun way to escape the frustration that IS inherent with an Online FPS. It’s not perfect, nor do i have the time to invest in, what it would take to learn Blizzard’s game engine. How it handles instructions & to what extent that’s carried over to the Workshop. Or general…umm “programming theory”? I already waist enough time playing this game as it is…
Anyways, i’m truly sorry to GreenArcane for unintentionally taking over your thread, on what should have been a fairly simple answer;
“There’s a dedicated PINED thread all about server load with Dev’s input on proper techniques. Read through it & go F&%K yourself” lol.
I never considered my 2cents would bother someone to the extent they felt the need to hijack an unrelated discussion to them, to point out flaws in how I answered this guy. OR how dare I ask questions in the first place IF I’m not proficient in coding. My Bad…
Any who, best of luck GreenArcane! Cheers!
Never be afraid of refactoring the code
Depends.
Honestly with a script of that size, I’d expect at least a couple of things being solved across several rules, be it individual assertions leading to a single end and or several rules governing individual aspects due to either simpler re-usability and or server performance.
Server performance rarely is a point of consideration for the average workshoper.
Which is how we ended up here in the first place, the server said “No”.
Obviously the server won’t be able to handle executing many complex rules at once, but it ain’t an issue most of the time anyway.
Unless you yourself build infinite loops, even worse wait-less, the server can take a decent hit.
Yes it is possible to TKO the server with a single loop-less rule, even if you have such a rule which single-handedly takes a massive dump on the server, it is unlikely the entire script consists of just those.
If you yourself can work with that and running all you need in a single rule / order while avoiding conflicts of assertions being set later than required within a different rule, that’s fine. To me that just felt excessively hard to work with because of the constraint on needing to do most if not all in a single rule to avoid these issues.
Past me would’ve said to gladly take a look at it to see if I can help with that, but knowing what I know now, heavily regretted to do so.
Not everyone enjoys every way code is written, that extends to outside the workshop as well.
For me that would make your project hard to work with, but it isn’t my project is it?
As a permanent solution it is excessive and avoids the root issue.
Instead of finding the part of the script that causes this large server load spike it just spreads the issue out a bit and maybe causes more issues later down the line if you happen to have other rules start up during those waits while partly or fully relying on information that either isn’t present yet or already becomes outdated by the time it is used / reused.
While it is a valid solution it isn’t one without its own noteworthy issues.
Usual culprit, excessive looping.
I’d recommend going with a minimum wait length of .25 for things that proceed to wait for the Condition to become false, 0.5 probably also still works fine for most cases without being too slow in effect cleansing etc.
Alternatively you could also look into using Wait Until to not have to loop at all, though that might be an annoyance with the size of some of these condition sets.