keycloak-uncached

Details

diff --git a/core/src/main/java/org/keycloak/representations/AccessToken.java b/core/src/main/java/org/keycloak/representations/AccessToken.java
index efa736e..eea0ed6 100755
--- a/core/src/main/java/org/keycloak/representations/AccessToken.java
+++ b/core/src/main/java/org/keycloak/representations/AccessToken.java
@@ -24,6 +24,7 @@ import org.keycloak.representations.idm.authorization.Permission;
 
 import java.io.Serializable;
 import java.util.Collection;
+import java.util.Collections;
 import java.util.HashMap;
 import java.util.HashSet;
 import java.util.Map;
@@ -123,7 +124,7 @@ public class AccessToken extends IDToken {
     protected Access realmAccess;
 
     @JsonProperty("resource_access")
-    protected Map<String, Access> resourceAccess = new HashMap<String, Access>();
+    protected Map<String, Access> resourceAccess;
 
     @JsonProperty("authorization")
     protected Authorization authorization;
@@ -134,8 +135,9 @@ public class AccessToken extends IDToken {
     @JsonProperty("scope")
     protected String scope;
 
+    @JsonIgnore
     public Map<String, Access> getResourceAccess() {
-        return resourceAccess;
+        return resourceAccess == null ? Collections.<String, Access>emptyMap() : resourceAccess;
     }
 
     public void setResourceAccess(Map<String, Access> resourceAccess) {
@@ -172,10 +174,14 @@ public class AccessToken extends IDToken {
 
     @JsonIgnore
     public Access getResourceAccess(String resource) {
-        return resourceAccess.get(resource);
+        return resourceAccess == null ? null : resourceAccess.get(resource);
     }
 
     public Access addAccess(String service) {
+        if (resourceAccess == null) {
+            resourceAccess = new HashMap<>();
+        }
+
         Access access = resourceAccess.get(service);
         if (access != null) return access;
         access = new Access();
diff --git a/core/src/test/java/org/keycloak/SkeletonKeyTokenTest.java b/core/src/test/java/org/keycloak/SkeletonKeyTokenTest.java
index ff11936..3834333 100755
--- a/core/src/test/java/org/keycloak/SkeletonKeyTokenTest.java
+++ b/core/src/test/java/org/keycloak/SkeletonKeyTokenTest.java
@@ -118,6 +118,27 @@ public class SkeletonKeyTokenTest {
         ois.close();
     }
 
+
+    @Test
+    public void testTokenWithoutResourceAccess() throws Exception {
+        AccessToken token = new AccessToken();
+        token.id("111");
+        token.issuer("http://localhost:8080/auth/acme");
+
+        String json = JsonSerialization.writeValueAsString(token);
+
+        // Assert JSON doesn't contain "realm_access" or "resource_access" fields as it doesn't have any roles specified
+        Assert.assertFalse(json.contains("realm_access"));
+        Assert.assertFalse(json.contains("resource_access"));
+
+        token = JsonSerialization.readValue(json, AccessToken.class);
+
+        Assert.assertNull(token.getRealmAccess());
+        Assert.assertTrue(token.getResourceAccess() != null && token.getResourceAccess().isEmpty());
+        Assert.assertNull(token.getResourceAccess("foo"));
+    }
+
+
     private AccessToken createSimpleToken() {
         AccessToken token = new AccessToken();
         token.id("111");
diff --git a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/oauth/OIDCProtocolMappersTest.java b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/oauth/OIDCProtocolMappersTest.java
index 87f931e..416a743 100644
--- a/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/oauth/OIDCProtocolMappersTest.java
+++ b/testsuite/integration-arquillian/tests/base/src/test/java/org/keycloak/testsuite/oauth/OIDCProtocolMappersTest.java
@@ -27,6 +27,7 @@ import org.keycloak.admin.client.resource.ProtocolMappersResource;
 import org.keycloak.admin.client.resource.RealmResource;
 import org.keycloak.admin.client.resource.UserResource;
 import org.keycloak.common.util.UriUtils;
+import org.keycloak.jose.jws.JWSInput;
 import org.keycloak.models.AccountRoles;
 import org.keycloak.protocol.oidc.OIDCLoginProtocol;
 import org.keycloak.protocol.oidc.OIDCLoginProtocolFactory;
@@ -50,6 +51,8 @@ import org.keycloak.testsuite.util.OAuthClient;
 import org.keycloak.testsuite.util.ProtocolMapperUtil;
 
 import javax.ws.rs.core.Response;
+
+import java.nio.charset.StandardCharsets;
 import java.util.Arrays;
 import java.util.List;
 import java.util.Map;
@@ -402,6 +405,11 @@ public class OIDCProtocolMappersTest extends AbstractKeycloakTest {
             Assert.assertNull(accessToken.getRealmAccess());
             Assert.assertTrue(accessToken.getResourceAccess().isEmpty());
 
+            // KEYCLOAK-8481 Assert that accessToken JSON doesn't have "realm_access" or "resource_access" fields in it
+            String accessTokenJson = new String(new JWSInput(response.getAccessToken()).getContent(), StandardCharsets.UTF_8);
+            Assert.assertFalse(accessTokenJson.contains("realm_access"));
+            Assert.assertFalse(accessTokenJson.contains("resource_access"));
+
             // Assert both realm and client roles on the new position. Hardcoded role should be here as well
             Map<String, Object> cst1 = (Map<String, Object>) accessToken.getOtherClaims().get("custom");
             List<String> roles = (List<String>) cst1.get("roles");