I found that the more than 60% of the javaScript code generated by GWT on my application is for RPC serializers. Also I found that serializers are not shared between service
GWT's RPC generation code builds several classes to do its work as you've noted: a *_FieldSerializer
for each type that goes over the wire, and a *_Proxy
class for the RemoteService async type. That proxy type requires a *_TypeSerializer
, which is the root of your problem - for some reason, GWT wires up all of the serialization/deserialization methods in a string->js function map, probably to facilitate fast lookups - but this setup code comes at the cost of lines of code that need to be in the final build. A more optimized approach could have each FieldSerializer
have a registration method where it adds its methods to the static map owned by the Proxy - this is plagued, however, but GWT's optimization of attempting to not reference instantiate()
, deserialize()
and serialize()
methods if it doesnt appear they will be called.
Your issue stems from having many types that can be serialized, and from your having attempted to build out RemoteService
types that each describe specific units of functionality, but re-use many model types. Admirable goal, especially as it will probably make your server-side code look nicer, but apparently GWT bites you for it.
The solution I attempted to offer you on freenode (as niloc132) was to build a single large RemoteService
type, which you named GeneralService
, and a matching GeneralServiceAsync
, each extending all of the existing rpc service types. My first thought was to use a
to tell the generator system that when you want each RemoteService type to replace it with GeneralService
, but as Tahir points out, this doesn't make sense - GWT doesn't pass rebind results back into itself to keep doing lookups. Instead, I would suggest that when you want a service async type, do the following:
AccountingServiceAsync service = (AccountingServiceAsync) GWT.create(GeneralService.class)
The rebind result from GeneralService
will implement GeneralServiceAsync
, which is itself assignable to AccountingServiceAsync
. If memory serves, you said that you have static methods/fields that provide these services - change those sites to always create a GeneralServiceAsync
instance. As long as you do not invoke GWT.create
on any RemoteService
subtype but GeneralService
, you will limit the number of TypeSerializers
to one.
As a side note, the RemoteServiceProxy
subtypes are stateless, so ensuring that you create only one instance might make it easier to build consistently, but saves no runtime memory or time, as they are almost certainly compiled out to static methods. The *_TypeSerializer
classes do have state however, but there is only one instance of each, so combining all of your RemoteService
s might save a very small amount of working memory.