Easy to use service wrapper around esri-loader?
See original GitHub issueHi Guys, not really an issue…but more a request for guidance. I’m getting around to upgrading an angular app to cli 6.x and moving away from esri-system-js. It’s basically a map and some menus and has heaps of esri dependencies through out.
As such it would be a real pain to have to load modules using this pattern everywhere:
loadModules(['esri/views/MapView', 'esri/Map'])
.then(([MapView, Map]) => {
// do stuff
});
Even using await
it’s not so nice to have scattered everywhere.
I’ve created a service to inject around that can encapsulate this and a list of modules I’ll want to load straight away or lazily. They’re in this gist - https://gist.github.com/nickcam/162f3a375206737e5b5e42fc638c0fd8
This will allow creating a new arcgis object like so where the service is injected:
let map = new this.esri.Map({ //whatever params// });
To lazy load:
await this.esri.load(["SimpleMarkerSymbol"]);
let sms = new this.esri.SimpleMarkerSymbol();
This seems ok-ish, the overhead is adding every module to the modules list and creating a property on the service for each module (for typings and ease of calling).
I can’t help but feel it’s a bit shit though…so before I crack on and rewrite a bunch of stuff wanted to check if you have any better ideas?? I have checked out the other issues in this repo - particularly this one, https://github.com/Esri/esri-loader/issues/71, which I think is similar, but not quite as succinct as I would have hoped.
Also any examples of using typescript 2.9 import() yet? Thanks heaps!
Issue Analytics
- State:
- Created 5 years ago
- Comments:5 (3 by maintainers)
Top GitHub Comments
Hi @tomwayson - awesome, thanks for the detailed write up! Being used to the ease of import statements and instantiating from them might have spoiled me…the arguments against them are compelling though.
Maybe this app is a bit of rare case, but I know that I’ll need about 80% of the modules I want to use loaded up front just to get the initial view, the flexibility to lazy load when required is a cool thing to have up the sleeve though.
I thought about using void functions to expose/use the modules, and after looking at the example again I can see this app basically already does. Currently there’s multiple services that relate to a particular app function or area each that import esri modules and they contain the sorts of functions you have in your example, so there’s no esri module bleed into views or outside these services. “Theoretically” we could swap out arcigis api for something else…although in reality it’s not practical without basically rewriting the app.
Some of these services are quite involved and could probably be refactored (hindsight, lessons learned etc…), what I was hoping for was easier instantiation within these services by wrapping the loader with module defs to sit behind them. Also have some classes that extend esri modules, haven’t looked at refactoring those yet though so not sure how that will go??
Thanks for your help, plenty to consider as I go about refactoring this thing 😃!
Here’s another variant on the pattern I suggested above.
In your fn that calls
loadModules()
load all classes that your app needs to work w/ the map. Then resolve the promise w/ one or more fns that close over the map/scene view and the classes. Callers can then use those functions to work w/ the map. Here’s an example:I have a
newMap()
fn that resolves with arefreshGraphics()
fn after the map loads:https://github.com/tomwayson/create-arcgis-app/blob/fefb171c2ebaaae90292e6ba981c3aff65b340b5/src/utils/map.js#L38-L41
Then in the component that calls
newMap()
, it holds on torefreshGraphics()
for later use:https://github.com/tomwayson/create-arcgis-app/blob/fefb171c2ebaaae90292e6ba981c3aff65b340b5/src/components/ExtentsMap.js#L30-L38
Whenever that component receives a new array of items (JSON), it calls
refreshGraphics()
.https://github.com/tomwayson/create-arcgis-app/blob/fefb171c2ebaaae90292e6ba981c3aff65b340b5/src/components/ExtentsMap.js#L12-L27
For good measure I
delete
the map component’s refernece torefreshGraphics()
before the component is destroyed:https://github.com/tomwayson/create-arcgis-app/blob/fefb171c2ebaaae90292e6ba981c3aff65b340b5/src/components/ExtentsMap.js#L45-L49