| /* |
| * Licensed to the Apache Software Foundation (ASF) under one or more contributor license |
| * agreements. See the NOTICE file distributed with this work for additional information regarding |
| * copyright ownership. The ASF licenses this file to you under the Apache License, Version 2.0 (the |
| * "License"); you may not use this file except in compliance with the License. You may obtain a |
| * copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software distributed under the License |
| * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express |
| * or implied. See the License for the specific language governing permissions and limitations under |
| * the License. |
| */ |
| package org.apache.geode.security; |
| |
| import static org.apache.geode.internal.AvailablePort.*; |
| import static org.apache.geode.security.SecurityTestUtils.*; |
| import static org.apache.geode.test.dunit.Assert.*; |
| import static org.apache.geode.test.dunit.IgnoredException.*; |
| import static org.apache.geode.test.dunit.LogWriterUtils.*; |
| |
| import java.util.ArrayList; |
| import java.util.Collection; |
| import java.util.Iterator; |
| import java.util.List; |
| import java.util.Properties; |
| |
| import org.apache.geode.internal.AvailablePortHelper; |
| import org.junit.Test; |
| import org.junit.experimental.categories.Category; |
| import org.junit.runner.RunWith; |
| import org.junit.runners.Parameterized; |
| |
| import org.apache.geode.cache.operations.OperationContext.OperationCode; |
| import org.apache.geode.internal.cache.tier.sockets.ServerConnection; |
| import org.apache.geode.security.generator.AuthzCredentialGenerator; |
| import org.apache.geode.security.generator.CredentialGenerator; |
| import org.apache.geode.security.generator.DummyCredentialGenerator; |
| import org.apache.geode.security.generator.XmlAuthzCredentialGenerator; |
| import org.apache.geode.security.templates.UserPasswordAuthInit; |
| import org.apache.geode.test.dunit.Host; |
| import org.apache.geode.test.dunit.VM; |
| import org.apache.geode.test.dunit.standalone.VersionManager; |
| import org.apache.geode.test.junit.categories.DistributedTest; |
| import org.apache.geode.test.junit.categories.SecurityTest; |
| import org.apache.geode.test.junit.runners.CategoryWithParameterizedRunnerFactory; |
| |
| /** |
| * Tests for authorization from client to server. This tests for authorization of all operations |
| * with both valid and invalid credentials/modules with pre-operation callbacks. It also checks for |
| * authorization in case of failover. |
| * |
| * @since GemFire 5.5 |
| */ |
| @Category({DistributedTest.class, SecurityTest.class}) |
| @RunWith(Parameterized.class) |
| @Parameterized.UseParametersRunnerFactory(CategoryWithParameterizedRunnerFactory.class) |
| public class ClientAuthorizationDUnitTest extends ClientAuthorizationTestCase { |
| @Parameterized.Parameters |
| public static Collection<String> data() { |
| List<String> result = VersionManager.getInstance().getVersions(); |
| if (result.size() < 1) { |
| throw new RuntimeException("No older versions of Geode were found to test against"); |
| } else { |
| System.out.println("running against these versions: " + result); |
| } |
| return result; |
| } |
| |
| public ClientAuthorizationDUnitTest(String version) { |
| super(); |
| clientVersion = version; |
| } |
| |
| |
| @Override |
| public final void preTearDownClientAuthorizationTestBase() throws Exception { |
| closeCache(); |
| } |
| |
| @Test |
| public void testAllowPutsGets() { |
| AuthzCredentialGenerator gen = getXmlAuthzGenerator(); |
| CredentialGenerator cGen = gen.getCredentialGenerator(); |
| Properties extraAuthProps = cGen.getSystemProperties(); |
| Properties javaProps = cGen.getJavaProperties(); |
| Properties extraAuthzProps = gen.getSystemProperties(); |
| String authenticator = cGen.getAuthenticator(); |
| String authInit = cGen.getAuthInit(); |
| String accessor = gen.getAuthorizationCallback(); |
| |
| getLogWriter().info("testAllowPutsGets: Using authinit: " + authInit); |
| getLogWriter().info("testAllowPutsGets: Using authenticator: " + authenticator); |
| getLogWriter().info("testAllowPutsGets: Using accessor: " + accessor); |
| |
| // Start servers with all required properties |
| Properties serverProps = |
| buildProperties(authenticator, accessor, false, extraAuthProps, extraAuthzProps); |
| |
| int port1 = createServer1(javaProps, serverProps); |
| int port2 = createServer2(javaProps, serverProps); |
| |
| // Start client1 with valid CREATE credentials |
| Properties createCredentials = gen.getAllowedCredentials( |
| new OperationCode[] {OperationCode.PUT}, new String[] {regionName}, 1); |
| javaProps = cGen.getJavaProperties(); |
| |
| getLogWriter().info("testAllowPutsGets: For first client credentials: " + createCredentials); |
| |
| createClient1NoException(javaProps, authInit, port1, port2, createCredentials); |
| |
| // Start client2 with valid GET credentials |
| Properties getCredentials = gen.getAllowedCredentials(new OperationCode[] {OperationCode.GET}, |
| new String[] {regionName}, 2); |
| javaProps = cGen.getJavaProperties(); |
| |
| getLogWriter().info("testAllowPutsGets: For second client credentials: " + getCredentials); |
| |
| createClient2NoException(javaProps, authInit, port1, port2, getCredentials); |
| |
| // Perform some put operations from client1 |
| client1.invoke(() -> doPuts(2, NO_EXCEPTION)); |
| |
| // Verify that the gets succeed |
| client2.invoke(() -> doGets(2, NO_EXCEPTION)); |
| } |
| |
| @Test |
| public void testPutAllWithSecurity() { |
| AuthzCredentialGenerator gen = getXmlAuthzGenerator(); |
| CredentialGenerator cGen = gen.getCredentialGenerator(); |
| Properties extraAuthProps = cGen.getSystemProperties(); |
| Properties javaProps = cGen.getJavaProperties(); |
| Properties extraAuthzProps = gen.getSystemProperties(); |
| String authenticator = cGen.getAuthenticator(); |
| String authInit = cGen.getAuthInit(); |
| String accessor = gen.getAuthorizationCallback(); |
| |
| // this test registers a PDX type and needs the servers to accept it without |
| // credentials in old clients |
| if (clientVersion.compareTo("130") < 0 && !VersionManager.isCurrentVersion(clientVersion)) { |
| server1.invoke(() -> ServerConnection.allowInternalMessagesWithoutCredentials = true); |
| server2.invoke(() -> ServerConnection.allowInternalMessagesWithoutCredentials = true); |
| } |
| |
| getLogWriter().info("testPutAllWithSecurity: Using authinit: " + authInit); |
| getLogWriter().info("testPutAllWithSecurity: Using authenticator: " + authenticator); |
| getLogWriter().info("testPutAllWithSecurity: Using accessor: " + accessor); |
| |
| // Start servers with all required properties |
| Properties serverProps = |
| buildProperties(authenticator, accessor, false, extraAuthProps, extraAuthzProps); |
| |
| int port1 = createServer1(javaProps, serverProps); |
| int port2 = createServer2(javaProps, serverProps); |
| |
| // Start client1 with valid CREATE credentials |
| Properties createCredentials = gen.getAllowedCredentials( |
| new OperationCode[] {OperationCode.PUTALL}, new String[] {regionName}, 1); |
| javaProps = cGen.getJavaProperties(); |
| |
| getLogWriter() |
| .info("testPutAllWithSecurity: For first client credentials: " + createCredentials); |
| |
| createClient1NoException(javaProps, authInit, port1, port2, createCredentials); |
| |
| // Perform some put all operations from client1 |
| client1.invoke(() -> doPutAllP()); |
| } |
| |
| @Test |
| public void testDisallowPutsGets() { |
| AuthzCredentialGenerator gen = getXmlAuthzGenerator(); |
| CredentialGenerator cGen = gen.getCredentialGenerator(); |
| Properties extraAuthProps = cGen.getSystemProperties(); |
| Properties javaProps = cGen.getJavaProperties(); |
| Properties extraAuthzProps = gen.getSystemProperties(); |
| String authenticator = cGen.getAuthenticator(); |
| String authInit = cGen.getAuthInit(); |
| String accessor = gen.getAuthorizationCallback(); |
| |
| getLogWriter().info("testDisallowPutsGets: Using authinit: " + authInit); |
| getLogWriter().info("testDisallowPutsGets: Using authenticator: " + authenticator); |
| getLogWriter().info("testDisallowPutsGets: Using accessor: " + accessor); |
| |
| // Check that we indeed can obtain valid credentials not allowed to do gets |
| Properties createCredentials = gen.getAllowedCredentials( |
| new OperationCode[] {OperationCode.PUT}, new String[] {regionName}, 1); |
| Properties createJavaProps = cGen.getJavaProperties(); |
| |
| getLogWriter().info("testDisallowPutsGets: For first client credentials: " + createCredentials); |
| |
| Properties getCredentials = gen.getDisallowedCredentials( |
| new OperationCode[] {OperationCode.GET}, new String[] {regionName}, 2); |
| Properties getJavaProps = cGen.getJavaProperties(); |
| |
| getLogWriter().info( |
| "testDisallowPutsGets: For second client disallowed GET credentials: " + getCredentials); |
| |
| // Start servers with all required properties |
| Properties serverProps = |
| buildProperties(authenticator, accessor, false, extraAuthProps, extraAuthzProps); |
| |
| int port1 = createServer1(javaProps, serverProps); |
| int port2 = createServer2(javaProps, serverProps); |
| |
| createClient1NoException(createJavaProps, authInit, port1, port2, createCredentials); |
| |
| createClient2NoException(getJavaProps, authInit, port1, port2, getCredentials); |
| |
| // Perform some put operations from client1 |
| client1.invoke(() -> doPuts(2, NO_EXCEPTION)); |
| |
| // Gets as normal user should throw exception |
| client2.invoke(() -> doGets(2, NOTAUTHZ_EXCEPTION)); |
| |
| // Try to connect client2 with reader credentials |
| getCredentials = gen.getAllowedCredentials(new OperationCode[] {OperationCode.GET}, |
| new String[] {regionName}, 5); |
| getJavaProps = cGen.getJavaProperties(); |
| |
| getLogWriter() |
| .info("testDisallowPutsGets: For second client with GET credentials: " + getCredentials); |
| |
| createClient2NoException(getJavaProps, authInit, port1, port2, getCredentials); |
| |
| // Verify that the gets succeed |
| client2.invoke(() -> doGets(2, NO_EXCEPTION)); |
| |
| // Verify that the puts throw exception |
| client2.invoke(() -> doNPuts(2, NOTAUTHZ_EXCEPTION)); |
| } |
| |
| @Test |
| public void testInvalidAccessor() { |
| AuthzCredentialGenerator gen = getXmlAuthzGenerator(); |
| CredentialGenerator cGen = gen.getCredentialGenerator(); |
| Properties extraAuthProps = cGen.getSystemProperties(); |
| Properties javaProps = cGen.getJavaProperties(); |
| Properties extraAuthzProps = gen.getSystemProperties(); |
| String authenticator = cGen.getAuthenticator(); |
| String authInit = cGen.getAuthInit(); |
| String accessor = gen.getAuthorizationCallback(); |
| |
| getLogWriter().info("testInvalidAccessor: Using authinit: " + authInit); |
| getLogWriter().info("testInvalidAccessor: Using authenticator: " + authenticator); |
| |
| // Start server1 with invalid accessor |
| Properties serverProps = |
| buildProperties(authenticator, "org.apache.none", false, extraAuthProps, extraAuthzProps); |
| |
| int port1 = createServer1(javaProps, serverProps); |
| int port2 = getRandomAvailablePort(SOCKET); |
| |
| // Client creation should throw exceptions |
| Properties createCredentials = gen.getAllowedCredentials( |
| new OperationCode[] {OperationCode.PUT}, new String[] {regionName}, 3); |
| Properties createJavaProps = cGen.getJavaProperties(); |
| |
| getLogWriter() |
| .info("testInvalidAccessor: For first client CREATE credentials: " + createCredentials); |
| |
| Properties getCredentials = gen.getAllowedCredentials(new OperationCode[] {OperationCode.GET}, |
| new String[] {regionName}, 7); |
| Properties getJavaProps = cGen.getJavaProperties(); |
| |
| getLogWriter() |
| .info("testInvalidAccessor: For second client GET credentials: " + getCredentials); |
| |
| client1.invoke(() -> ClientAuthenticationTestUtils.createCacheClient(authInit, |
| createCredentials, createJavaProps, port1, port2, 0, false, false, NO_EXCEPTION)); |
| client1.invoke(() -> doPuts(1, AUTHFAIL_EXCEPTION)); |
| |
| client2.invoke(() -> ClientAuthenticationTestUtils.createCacheClient(authInit, getCredentials, |
| getJavaProps, port1, port2, 0, false, false, NO_EXCEPTION)); |
| client2.invoke(() -> doPuts(1, AUTHFAIL_EXCEPTION)); |
| |
| // Now start server2 that has valid accessor |
| getLogWriter().info("testInvalidAccessor: Using accessor: " + accessor); |
| serverProps = buildProperties(authenticator, accessor, false, extraAuthProps, extraAuthzProps); |
| createServer2(javaProps, serverProps, port2); |
| server1.invoke(() -> closeCache()); |
| |
| createClient1NoException(createJavaProps, authInit, port1, port2, createCredentials); |
| createClient2NoException(getJavaProps, authInit, port1, port2, getCredentials); |
| |
| // Now perform some put operations from client1 |
| client1.invoke(() -> doPuts(4, NO_EXCEPTION)); |
| |
| // Verify that the gets succeed |
| client2.invoke(() -> doGets(4, NO_EXCEPTION)); |
| } |
| |
| @Test |
| public void testPutsGetsWithFailover() { |
| AuthzCredentialGenerator gen = getXmlAuthzGenerator(); |
| CredentialGenerator cGen = gen.getCredentialGenerator(); |
| Properties extraAuthProps = cGen.getSystemProperties(); |
| Properties javaProps = cGen.getJavaProperties(); |
| Properties extraAuthzProps = gen.getSystemProperties(); |
| String authenticator = cGen.getAuthenticator(); |
| String authInit = cGen.getAuthInit(); |
| String accessor = gen.getAuthorizationCallback(); |
| |
| getLogWriter().info("testPutsGetsWithFailover: Using authinit: " + authInit); |
| getLogWriter().info("testPutsGetsWithFailover: Using authenticator: " + authenticator); |
| getLogWriter().info("testPutsGetsWithFailover: Using accessor: " + accessor); |
| |
| // Start servers with all required properties |
| Properties serverProps = |
| buildProperties(authenticator, accessor, false, extraAuthProps, extraAuthzProps); |
| |
| int port1 = createServer1(javaProps, serverProps); |
| |
| // Get a port for second server but do not start it. This forces the clients to connect to the |
| // first server |
| int port2 = getRandomAvailablePort(SOCKET); |
| |
| // Start client1 with valid CREATE credentials |
| Properties createCredentials = gen.getAllowedCredentials( |
| new OperationCode[] {OperationCode.PUT}, new String[] {regionName}, 1); |
| Properties createJavaProps = cGen.getJavaProperties(); |
| |
| getLogWriter() |
| .info("testPutsGetsWithFailover: For first client credentials: " + createCredentials); |
| |
| createClient1NoException(createJavaProps, authInit, port1, port2, createCredentials); |
| |
| // Start client2 with valid GET credentials |
| Properties getCredentials = gen.getAllowedCredentials(new OperationCode[] {OperationCode.GET}, |
| new String[] {regionName}, 5); |
| Properties getJavaProps = cGen.getJavaProperties(); |
| |
| getLogWriter() |
| .info("testPutsGetsWithFailover: For second client credentials: " + getCredentials); |
| |
| createClient2NoException(getJavaProps, authInit, port1, port2, getCredentials); |
| |
| // Perform some put operations from client1 |
| client1.invoke(() -> doPuts(2, NO_EXCEPTION)); |
| |
| // Verify that the puts succeeded |
| client2.invoke(() -> doGets(2, NO_EXCEPTION)); |
| |
| createServer2(javaProps, serverProps, port2); |
| server1.invoke(() -> closeCache()); |
| |
| // Perform some put operations from client1 |
| client1.invoke(() -> doNPuts(4, NO_EXCEPTION)); |
| |
| // Verify that the puts succeeded |
| client2.invoke(() -> doNGets(4, NO_EXCEPTION)); |
| |
| // Now re-connect with credentials not allowed to do gets |
| Properties noGetCredentials = gen.getDisallowedCredentials( |
| new OperationCode[] {OperationCode.GET}, new String[] {regionName}, 9); |
| getJavaProps = cGen.getJavaProperties(); |
| |
| getLogWriter().info("testPutsGetsWithFailover: For second client disallowed GET credentials: " |
| + noGetCredentials); |
| |
| createClient2NoException(getJavaProps, authInit, port1, port2, noGetCredentials); |
| |
| // Perform some put operations from client1 |
| client1.invoke(() -> doPuts(4, NO_EXCEPTION)); |
| |
| // Gets as normal user should throw exception |
| client2.invoke(() -> doGets(4, NOTAUTHZ_EXCEPTION)); |
| |
| // force a failover and do the drill again |
| server1.invoke(() -> ClientAuthorizationTestCase.createCacheServer(getLocatorPort(), port1, |
| serverProps, javaProps)); |
| server2.invoke(() -> closeCache()); |
| |
| // Perform some put operations from client1 |
| client1.invoke(() -> doNPuts(4, NO_EXCEPTION)); |
| |
| // Gets as normal user should throw exception |
| client2.invoke(() -> doNGets(4, NOTAUTHZ_EXCEPTION)); |
| |
| createClient2NoException(getJavaProps, authInit, port1, port2, getCredentials); |
| |
| // Verify that the gets succeed |
| client2.invoke(() -> doNGets(4, NO_EXCEPTION)); |
| |
| // Verify that the puts throw exception |
| client2.invoke(() -> doPuts(4, NOTAUTHZ_EXCEPTION)); |
| } |
| |
| @Test |
| public void testUnregisterInterestWithFailover() throws InterruptedException { |
| OperationWithAction[] unregisterOps = unregisterOpsForTestUnregisterInterestWithFailover(); |
| |
| AuthzCredentialGenerator gen = new XmlAuthzCredentialGenerator(); |
| CredentialGenerator cGen = new DummyCredentialGenerator(); |
| cGen.init(); |
| gen.init(cGen); |
| Properties extraAuthProps = cGen.getSystemProperties(); |
| Properties javaProps = cGen.getJavaProperties(); |
| Properties extraAuthzProps = gen.getSystemProperties(); |
| String authenticator = cGen.getAuthenticator(); |
| String authInit = cGen.getAuthInit(); |
| String accessor = gen.getAuthorizationCallback(); |
| |
| getLogWriter().info("testAllOpsWithFailover: Using authinit: " + authInit); |
| getLogWriter().info("testAllOpsWithFailover: Using authenticator: " + authenticator); |
| getLogWriter().info("testAllOpsWithFailover: Using accessor: " + accessor); |
| |
| // Start servers with all required properties |
| Properties serverProps = |
| buildProperties(authenticator, accessor, false, extraAuthProps, extraAuthzProps); |
| |
| // Get ports for the servers |
| int[] randomAvailableTCPPorts = AvailablePortHelper.getRandomAvailableTCPPorts(2); |
| int port1 = randomAvailableTCPPorts[0]; |
| int port2 = randomAvailableTCPPorts[1]; |
| |
| // Perform all the ops on the clients |
| List opBlock = new ArrayList(); |
| for (int opNum = 0; opNum < unregisterOps.length; ++opNum) { |
| |
| // Start client with valid credentials as specified in OperationWithAction |
| OperationWithAction currentOp = unregisterOps[opNum]; |
| if (currentOp.equals(OperationWithAction.OPBLOCK_END) |
| || currentOp.equals(OperationWithAction.OPBLOCK_NO_FAILOVER)) { |
| |
| // End of current operation block; execute all the operations on the servers with/without |
| // failover |
| if (opBlock.size() > 0) { |
| // Start the first server and execute the operation block |
| server1.invoke(() -> ClientAuthorizationTestCase.createCacheServer(getLocatorPort(), |
| port1, serverProps, javaProps)); |
| server2.invoke(() -> closeCache()); |
| |
| executeRIOpBlock(opBlock, port1, port2, authInit, extraAuthProps, extraAuthzProps, |
| javaProps); |
| |
| if (!currentOp.equals(OperationWithAction.OPBLOCK_NO_FAILOVER)) { |
| createServer2(javaProps, serverProps, port2); |
| server1.invoke(() -> closeCache()); |
| |
| executeRIOpBlock(opBlock, port1, port2, authInit, extraAuthProps, extraAuthzProps, |
| javaProps); |
| } |
| opBlock.clear(); |
| } |
| |
| } else { |
| currentOp.setOpNum(opNum); |
| opBlock.add(currentOp); |
| } |
| } |
| } |
| |
| @Test |
| public void testAllOpsWithFailover() throws InterruptedException { |
| addIgnoredException("Read timed out"); |
| runOpsWithFailOver(allOpsForAllOpsWithFailover(), "testAllOpsWithFailover"); |
| } |
| |
| private OperationWithAction[] unregisterOpsForTestUnregisterInterestWithFailover() { |
| return new OperationWithAction[] { |
| // Register interest in all KEYS using one key at a time |
| new OperationWithAction(OperationCode.REGISTER_INTEREST, OperationCode.UNREGISTER_INTEREST, |
| 3, OpFlags.NONE, 4), |
| new OperationWithAction(OperationCode.REGISTER_INTEREST, 2), |
| // UPDATE and test with GET |
| new OperationWithAction(OperationCode.PUT), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.LOCAL_OP, 4), |
| |
| // Unregister interest in all KEYS using one key at a time |
| new OperationWithAction(OperationCode.UNREGISTER_INTEREST, 3, |
| OpFlags.USE_OLDCONN | OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.UNREGISTER_INTEREST, 2, OpFlags.USE_OLDCONN, 4), |
| // UPDATE and test with GET for no updates |
| new OperationWithAction(OperationCode.PUT, 1, OpFlags.USE_OLDCONN | OpFlags.USE_NEWVAL, 4), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.LOCAL_OP, 4), |
| |
| OperationWithAction.OPBLOCK_END, |
| |
| // Register interest in all KEYS using list |
| new OperationWithAction(OperationCode.REGISTER_INTEREST, OperationCode.UNREGISTER_INTEREST, |
| 3, OpFlags.USE_LIST, 4), |
| new OperationWithAction(OperationCode.REGISTER_INTEREST, 1, OpFlags.USE_LIST, 4), |
| // UPDATE and test with GET |
| new OperationWithAction(OperationCode.PUT, 2), |
| new OperationWithAction(OperationCode.GET, 1, OpFlags.USE_OLDCONN | OpFlags.LOCAL_OP, 4), |
| |
| // Unregister interest in all KEYS using list |
| new OperationWithAction(OperationCode.UNREGISTER_INTEREST, 3, |
| OpFlags.USE_OLDCONN | OpFlags.USE_LIST | OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.UNREGISTER_INTEREST, 1, |
| OpFlags.USE_OLDCONN | OpFlags.USE_LIST, 4), |
| // UPDATE and test with GET for no updates |
| new OperationWithAction(OperationCode.PUT, 2, OpFlags.USE_OLDCONN | OpFlags.USE_NEWVAL, 4), |
| new OperationWithAction(OperationCode.GET, 1, OpFlags.USE_OLDCONN | OpFlags.LOCAL_OP, 4), |
| |
| OperationWithAction.OPBLOCK_END, |
| |
| // Register interest in all KEYS using regular expression |
| new OperationWithAction(OperationCode.REGISTER_INTEREST, OperationCode.UNREGISTER_INTEREST, |
| 3, OpFlags.USE_REGEX, 4), |
| new OperationWithAction(OperationCode.REGISTER_INTEREST, 2, OpFlags.USE_REGEX, 4), |
| // UPDATE and test with GET |
| new OperationWithAction(OperationCode.PUT), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.LOCAL_OP, 4), |
| |
| // Unregister interest in all KEYS using regular expression |
| new OperationWithAction(OperationCode.UNREGISTER_INTEREST, 3, |
| OpFlags.USE_OLDCONN | OpFlags.USE_REGEX | OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.UNREGISTER_INTEREST, 2, |
| OpFlags.USE_OLDCONN | OpFlags.USE_REGEX, 4), |
| // UPDATE and test with GET for no updates |
| new OperationWithAction(OperationCode.PUT, 1, OpFlags.USE_OLDCONN | OpFlags.USE_NEWVAL, 4), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.LOCAL_OP, 4), |
| |
| OperationWithAction.OPBLOCK_END}; |
| } |
| |
| private OperationWithAction[] allOpsForAllOpsWithFailover() { |
| return new OperationWithAction[] { |
| // Test CREATE and verify with a GET |
| new OperationWithAction(OperationCode.PUT, 3, OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.PUT), |
| new OperationWithAction(OperationCode.GET, 3, OpFlags.CHECK_NOKEY | OpFlags.CHECK_NOTAUTHZ, |
| 4), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.CHECK_NOKEY, 4), |
| |
| // OPBLOCK_END indicates end of an operation block; the above block of three operations will |
| // be first executed on server1 and then on server2 after failover |
| OperationWithAction.OPBLOCK_END, |
| |
| // Test PUTALL and verify with GETs |
| new OperationWithAction(OperationCode.PUTALL, 3, |
| OpFlags.USE_NEWVAL | OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.PUTALL, 1, OpFlags.USE_NEWVAL, 4), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.USE_NEWVAL, 4), |
| OperationWithAction.OPBLOCK_END, |
| |
| // Test UPDATE and verify with a GET |
| new OperationWithAction(OperationCode.PUT, 3, OpFlags.USE_NEWVAL | OpFlags.CHECK_NOTAUTHZ, |
| 4), |
| new OperationWithAction(OperationCode.PUT, 1, OpFlags.USE_NEWVAL, 4), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.USE_NEWVAL, 4), |
| |
| OperationWithAction.OPBLOCK_END, |
| |
| // Test DESTROY and verify with a GET and that key should not exist |
| new OperationWithAction(OperationCode.DESTROY, 3, |
| OpFlags.USE_NEWVAL | OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.DESTROY), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.CHECK_FAIL, 4), |
| // Repopulate the region |
| new OperationWithAction(OperationCode.PUT, 1, OpFlags.USE_NEWVAL, 4), |
| |
| OperationWithAction.OPBLOCK_END, |
| |
| // Check CONTAINS_KEY |
| new OperationWithAction(OperationCode.CONTAINS_KEY, 3, OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.CONTAINS_KEY), |
| // Destroy the KEYS and check for failure in CONTAINS_KEY |
| new OperationWithAction(OperationCode.DESTROY, 2), |
| new OperationWithAction(OperationCode.CONTAINS_KEY, 3, |
| OpFlags.CHECK_FAIL | OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.CONTAINS_KEY, 1, |
| OpFlags.USE_OLDCONN | OpFlags.CHECK_FAIL, 4), |
| // Repopulate the region |
| new OperationWithAction(OperationCode.PUT), |
| |
| OperationWithAction.OPBLOCK_END, |
| |
| // Check KEY_SET |
| new OperationWithAction(OperationCode.KEY_SET, 3, OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.KEY_SET, 2), |
| |
| OperationWithAction.OPBLOCK_END, |
| |
| // Check QUERY |
| new OperationWithAction(OperationCode.QUERY, 3, OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.QUERY), |
| |
| OperationWithAction.OPBLOCK_END, |
| |
| // Register interest in all KEYS using one key at a time |
| new OperationWithAction(OperationCode.REGISTER_INTEREST, 3, OpFlags.CHECK_NOTAUTHZ, 4), |
| new OperationWithAction(OperationCode.REGISTER_INTEREST, 2), |
| // UPDATE and test with GET |
| new OperationWithAction(OperationCode.PUT), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.LOCAL_OP, 4), |
| |
| // Unregister interest in all KEYS using one key at a time |
| new OperationWithAction(OperationCode.UNREGISTER_INTEREST, 2, OpFlags.USE_OLDCONN, 4), |
| // UPDATE and test with GET for no updates |
| new OperationWithAction(OperationCode.PUT, 1, OpFlags.USE_OLDCONN | OpFlags.USE_NEWVAL, 4), |
| new OperationWithAction(OperationCode.GET, 2, OpFlags.USE_OLDCONN | OpFlags.LOCAL_OP, 4), |
| |
| OperationWithAction.OPBLOCK_END, |
| |
| // Test GET_ENTRY inside a TX, see #49951 |
| new OperationWithAction(OperationCode.GET, 2, |
| OpFlags.USE_GET_ENTRY_IN_TX | OpFlags.CHECK_FAIL, 4), |
| |
| OperationWithAction.OPBLOCK_END}; |
| |
| } |
| |
| private Properties getUserPassword(final String userName) { |
| Properties props = new Properties(); |
| props.setProperty(UserPasswordAuthInit.USER_NAME, userName); |
| props.setProperty(UserPasswordAuthInit.PASSWORD, userName); |
| return props; |
| } |
| |
| private void executeRIOpBlock(final List<OperationWithAction> opBlock, final int port1, |
| final int port2, final String authInit, final Properties extraAuthProps, |
| final Properties extraAuthzProps, final Properties javaProps) throws InterruptedException { |
| for (Iterator opIter = opBlock.iterator(); opIter.hasNext();) { |
| // Start client with valid credentials as specified in OperationWithAction |
| OperationWithAction currentOp = (OperationWithAction) opIter.next(); |
| OperationCode opCode = currentOp.getOperationCode(); |
| int opFlags = currentOp.getFlags(); |
| int clientNum = currentOp.getClientNum(); |
| VM clientVM = null; |
| boolean useThisVM = false; |
| |
| switch (clientNum) { |
| case 1: |
| clientVM = client1; |
| break; |
| case 2: |
| clientVM = client2; |
| break; |
| case 3: |
| useThisVM = true; |
| break; |
| default: |
| fail("executeRIOpBlock: Unknown client number " + clientNum); |
| break; |
| } |
| |
| getLogWriter().info("executeRIOpBlock: performing operation number [" + currentOp.getOpNum() |
| + "]: " + currentOp); |
| if ((opFlags & OpFlags.USE_OLDCONN) == 0) { |
| Properties opCredentials = null; |
| String currentRegionName = '/' + regionName; |
| if ((opFlags & OpFlags.USE_SUBREGION) > 0) { |
| currentRegionName += ('/' + SUBREGION_NAME); |
| } |
| String credentialsTypeStr; |
| OperationCode authOpCode = currentOp.getAuthzOperationCode(); |
| |
| if ((opFlags & OpFlags.CHECK_NOTAUTHZ) > 0 || (opFlags & OpFlags.USE_NOTAUTHZ) > 0 |
| || !authOpCode.equals(opCode)) { |
| credentialsTypeStr = " unauthorized " + authOpCode; |
| if (authOpCode.isRegisterInterest()) { |
| opCredentials = getUserPassword("reader7"); |
| } else if (authOpCode.isUnregisterInterest()) { |
| opCredentials = getUserPassword("reader6"); |
| } else { |
| fail("executeRIOpBlock: cannot determine credentials for" + credentialsTypeStr); |
| } |
| |
| } else { |
| credentialsTypeStr = " authorized " + authOpCode; |
| if (authOpCode.isRegisterInterest() || authOpCode.isUnregisterInterest()) { |
| opCredentials = getUserPassword("reader5"); |
| } else if (authOpCode.isPut()) { |
| opCredentials = getUserPassword("writer1"); |
| } else if (authOpCode.isGet()) { |
| opCredentials = getUserPassword("reader1"); |
| } else { |
| fail("executeRIOpBlock: cannot determine credentials for" + credentialsTypeStr); |
| } |
| } |
| |
| Properties clientProps = |
| concatProperties(new Properties[] {opCredentials, extraAuthProps, extraAuthzProps}); |
| |
| // Start the client with valid credentials but allowed or disallowed to perform an operation |
| getLogWriter().info("executeRIOpBlock: For client" + clientNum + credentialsTypeStr |
| + " credentials: " + opCredentials); |
| if (useThisVM) { |
| createCacheClientWithDynamicRegion(authInit, clientProps, javaProps, |
| new int[] {port1, port2}, 0, false, NO_EXCEPTION); |
| } else { |
| clientVM.invoke(() -> createCacheClient(authInit, clientProps, javaProps, |
| new int[] {port1, port2}, 0, false, NO_EXCEPTION)); |
| } |
| |
| } |
| |
| int expectedResult; |
| if ((opFlags & OpFlags.CHECK_NOTAUTHZ) > 0) { |
| expectedResult = NOTAUTHZ_EXCEPTION; |
| } else if ((opFlags & OpFlags.CHECK_EXCEPTION) > 0) { |
| expectedResult = OTHER_EXCEPTION; |
| } else { |
| expectedResult = NO_EXCEPTION; |
| } |
| |
| // Perform the operation from selected client |
| if (useThisVM) { |
| doOp(opCode, currentOp.getIndices(), opFlags, expectedResult); |
| |
| } else { |
| int[] indices = currentOp.getIndices(); |
| clientVM.invoke( |
| () -> ClientAuthorizationTestCase.doOp(opCode, indices, opFlags, expectedResult)); |
| } |
| } |
| } |
| |
| private void createClient2NoException(final Properties javaProps, final String authInit, |
| final int port1, final int port2, final Properties getCredentials) { |
| client2.invoke(() -> ClientAuthenticationTestUtils.createCacheClient(authInit, getCredentials, |
| javaProps, port1, port2, 0, NO_EXCEPTION)); |
| } |
| |
| private void createClient1NoException(final Properties javaProps, final String authInit, |
| final int port1, final int port2, final Properties createCredentials) { |
| client1.invoke(() -> ClientAuthenticationTestUtils.createCacheClient(authInit, |
| createCredentials, javaProps, port1, port2, 0, NO_EXCEPTION)); |
| } |
| |
| private int createServer2(final Properties javaProps, final Properties serverProps) { |
| return server2.invoke(() -> ClientAuthorizationTestCase.createCacheServer(getLocatorPort(), |
| serverProps, javaProps)); |
| } |
| |
| private int createServer1(final Properties javaProps, final Properties serverProps) { |
| return server1.invoke(() -> ClientAuthorizationTestCase.createCacheServer(getLocatorPort(), |
| serverProps, javaProps)); |
| } |
| |
| private void createServer2(Properties javaProps, Properties serverProps, int port2) { |
| server2.invoke(() -> ClientAuthorizationTestCase.createCacheServer(getLocatorPort(), port2, |
| serverProps, javaProps)); |
| } |
| } |