My web export has a memory leak.

Godot Version

4.3

Question

I created a game and it has been running fine as a windows executable using around 170 MB of memory. I exported to a web version to make the game more accessible to people and started getting messages about constantly crashing. After some testing of my own it seems that the game was using up to the limit of memory available (around 2.4 GB). I have looked at the profiler in the IDE and it shows no orphaned nodes, the number of nodes and objects stays pretty much the same, and the memory usage is very stable.

Is there some difference when you export the web version that is causing space to not get freed?

I was able to figure out the SFX in my game were causing it. I’m not entirely sure why but whenever I started spawning balls it would go up (this was from a bounce sound). I also tested with pressing some buttons and that made it go up. To be sure I made a version that just played the SFX every frame and sure enough when running in the browser the memory usage immediately shot up to 1 GB. For now I have the SFX disabled in the browser version of my game but if anyone knows why they would be causing this that would still help so I can re-enable them.

Can you share some code on how you use/play sound effects?

Yes I have an AudioStreamPlayer called AudioButtons in each place I need for the button sound and a AudioStreamPlayer called AudioBalls for the ball bouncing sound. Each AudioStreamPlayer has an mp3 for the sound file. For example I have a scene for upgrade buttons and at the end of the _on_pressed function it plays the sound for a button press.

func _on_pressed():
	# Collect info and emit upgrade signal
	$AudioButtons.play()

Playing the sound effect was the only thing the balls being on screen and the button clicking had in common. Since I knew both were causing the memory usage to go up I added playing both sound effects in the _process function of my main scene.

func _process(delta):
	$AudioButtons.play()
	$AudioBalls.play()

When this made the memory usage skyrocket I added a check to each of the places the sound effects were used so they wouldn’t be played in the web version

func _on_pressed():
	# Collect info and emit upgrade signal
	if !OS.has_feature("wasm"):
		$AudioButtons.play()

Now the web version seems to stay around 400 MB of memory usage pretty consistently.