You CAN'T trust the client, anyone skilled enough can hack the JS to display the widget, or subvert any "in memory" objects.
To summarize the best I can, first you MUST check permissions of RPC on the server side. You can use the J2EE roles, but I found that hard to make very dynamic, it's a Pain, really. I store a users "Access Rules" in a Database, In order to not fall into the many many problems of storing too much data in the Session scope, I store them in the Application scope in a map based on userid. (There are possibly dozens, or hundreds per user, right down to individually licensed data- sets ). I populate the map when they sign in, and clear via a SessionListener when they sign out or the session expires ). There is a simple way to query the Access Rules that is very fast. Now, may try to use a Servlet Filter to check the user ID, but thats nasty to map to individual RPC calls, or to return a proper Throwable via RPC. So, to make a long story short, I overloaded RemoteServiceServlet, specifically processCall(), more specifically, I copied the code into my subclass and modified it so that, from the RPCRequest I could get the Method, and on the Methods, I placed custom Annotations that enumerated the Access Rules there, processCall() then got the Annotations from the Method, and checked it against the in memory Rules for the user. It's relatively easy to throw back a proper Exception from processCall() also. You can log the Method name here too, for usage stats. I'm sure you can use things like Spring AOP, but that got sloppy fast, too much configuration for my taste, and hard to fit in with returning "Permission Denied" kind of exceptions. Each "Screen" in the app is associated with a "token" ( the app is Token History Driven ), and when a Screen is created, I do an RPC call, passing the token. The token must be in the "Access Rules" list, each token is associated with a map of properties that is returned for that users Access Rule Set. The map is consulted when adding certain permissioned components, but I do not store that in memory, to reduce the attack surface. The extra RPC call takes a small amount of time, but it also is a good place for us to log more usage stats, which I had to do anyway... Creating 2 compile "permutations", Admin and Non-Admin is helpful ONLY because it reduces the size of the app for non-admin users, not much for safety if you do not somehow protect access to the admin version of the Bootstrap JS. It's trivial if you know it's path to subvert the HTML stream to load it instead. There are many ways to get around this stuff... enough to make you paranoid. I would even create two DB connection pools, with different DB id's, and restrict table access on the Administrative Tables to only the Admin Pool, and get connections from the Admin Pool only for Admin users. Also, we use IP subnet filtering, people we give Admin access to are required to give us their IP ranges. AND, Admin changes do not go live immediately, they get queued and ANOTHER Admin has to approve them. I'm sure there are things I haven't thought of. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Google Web Toolkit" group. To post to this group, send email to [email protected] To unsubscribe from this group, send email to [email protected] For more options, visit this group at http://groups.google.com/group/Google-Web-Toolkit?hl=en -~----------~----~----~----~------~----~------~--~---
