OpenLayers官方setTileLoadFunction示例未调用revokeObjectURL致内存泄漏,如何修复?
Fixing Memory Leaks in OpenLayers' setTileLoadFunction Example
Yep, you're totally right about the memory leak issue in the official OpenLayers example for setTileLoadFunction() that uses URL.createObjectURL(). The problem is that this method creates a persistent object that doesn't get cleaned up automatically—even when the map tile is destroyed, those URL objects hang around in memory, which can lead to steadily increasing memory usage over time.
Let's look at the corrected implementation that properly cleans up these objects to avoid leaks:
import TileState from 'ol/TileState'; source.setTileLoadFunction(function(tile, src) { const xhr = new XMLHttpRequest(); xhr.responseType = 'blob'; let objectUrl; // Handle successful/finished request xhr.addEventListener('loadend', function (evt) { const data = this.response; if (data !== undefined) { objectUrl = URL.createObjectURL(data); const img = tile.getImage(); // Clean up the object URL once the image loads img.onload = function() { URL.revokeObjectURL(objectUrl); }; // Also clean up if the image fails to load img.onerror = function() { URL.revokeObjectURL(objectUrl); tile.setState(TileState.ERROR); }; img.src = objectUrl; } else { tile.setState(TileState.ERROR); } }); // Handle request errors xhr.addEventListener('error', function () { tile.setState(TileState.ERROR); }); // Add a dispose listener to clean up if the tile is destroyed before loading finishes tile.addEventListener('dispose', function() { if (objectUrl) { URL.revokeObjectURL(objectUrl); } xhr.abort(); // Also abort the XHR to avoid unnecessary network activity }); xhr.open('GET', src); xhr.send(); });
Key Fixes Explained:
- We store the created
objectUrlin a variable so we can reference it later for cleanup. - We add
onloadandonerrorhandlers to the tile's image: as soon as the image finishes loading (successfully or not), we revoke the object URL to free up memory. - We listen for the tile's
disposeevent: if the tile gets destroyed before the request completes, we revoke any existing object URL and abort the XHR to prevent wasted network resources and leftover memory references.
This way, we make sure every object URL we create gets properly cleaned up, eliminating the memory leak from the original example.
内容的提问来源于stack exchange,提问作者Brian B
相关产品推荐
相关产品推荐

