[
https://issues.apache.org/jira/browse/IGNITE-23977?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
]
Mikhail Petrov updated IGNITE-23977:
------------------------------------
Description:
Reproducer:
{code:java}
/*
* 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.ignite.internal.processors.security;
import java.security.Permissions;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.TimeUnit;
import org.apache.ignite.Ignition;
import org.apache.ignite.client.ClientCache;
import org.apache.ignite.client.IgniteClient;
import org.apache.ignite.client.IgniteClientFuture;
import org.apache.ignite.configuration.CacheConfiguration;
import org.apache.ignite.configuration.ClientConfiguration;
import org.apache.ignite.configuration.ClientConnectorConfiguration;
import org.apache.ignite.configuration.IgniteConfiguration;
import org.apache.ignite.internal.IgniteEx;
import org.apache.ignite.internal.TestRecordingCommunicationSpi;
import
org.apache.ignite.internal.processors.cache.distributed.GridCacheModuloAffinityFunction;
import org.apache.ignite.internal.processors.security.impl.TestSecurityData;
import
org.apache.ignite.internal.processors.security.impl.TestSecurityPluginProvider;
import org.apache.ignite.plugin.security.SecurityPermissionSet;
import org.apache.ignite.testframework.junits.common.GridCommonAbstractTest;
import org.junit.Test;
import static java.util.Collections.singletonMap;
import static org.apache.ignite.cache.CacheAtomicityMode.TRANSACTIONAL;
import static
org.apache.ignite.internal.processors.cache.distributed.GridCacheModuloAffinityFunction.IDX_ATTR;
import static
org.apache.ignite.plugin.security.SecurityPermission.ADMIN_CLUSTER_STATE;
import static org.apache.ignite.plugin.security.SecurityPermission.CACHE_CREATE;
import static org.apache.ignite.plugin.security.SecurityPermission.CACHE_PUT;
import static org.apache.ignite.plugin.security.SecurityPermission.CACHE_READ;
import static org.apache.ignite.plugin.security.SecurityPermission.CACHE_REMOVE;
import static
org.apache.ignite.plugin.security.SecurityPermission.JOIN_AS_SERVER;
import static
org.apache.ignite.plugin.security.SecurityPermissionSetBuilder.NO_PERMISSIONS;
import static
org.apache.ignite.plugin.security.SecurityPermissionSetBuilder.create;
/** */
public class SecurityContextInternalFuturePropagationTest extends
GridCommonAbstractTest {
/** {@inheritDoc} */
@Override protected IgniteConfiguration getConfiguration(String
igniteInstanceName) throws Exception {
return super.getConfiguration(igniteInstanceName)
.setCommunicationSpi(new TestRecordingCommunicationSpi())
.setUserAttributes(singletonMap(IDX_ATTR,
getTestIgniteInstanceIndex(igniteInstanceName)))
.setClientConnectorConfiguration(new ClientConnectorConfiguration()
.setThreadPoolSize(1))
.setPluginProviders(new TestSecurityPluginProvider(
igniteInstanceName,
"",
create()
.defaultAllowAll(false)
.appendSystemPermissions(JOIN_AS_SERVER,
ADMIN_CLUSTER_STATE)
.appendCachePermissions(DEFAULT_CACHE_NAME, CACHE_CREATE)
.build(),
null,
false,
userData("forbidden_client", NO_PERMISSIONS),
userData("allowed_client", create()
.defaultAllowAll(false)
.appendCachePermissions(DEFAULT_CACHE_NAME, CACHE_READ,
CACHE_PUT, CACHE_REMOVE)
.build())
));
}
/** {@inheritDoc} */
@Override protected void afterTest() throws Exception {
super.afterTest();
stopAllGrids();
}
/** */
@Test
public void testSecurityContextInternalFuturePropagation() throws Exception
{
IgniteEx ignite = startGrids(2);
prepareCache(ignite);
try (
IgniteClient allowedCli = startClient("allowed_client");
IgniteClient forbiddenCli = startClient("forbidden_client")
) {
ClientCache<Object, Object> allowedCliCache =
allowedCli.cache(DEFAULT_CACHE_NAME);
ClientCache<Object, Object> forbiddenCliCache =
forbiddenCli.cache(DEFAULT_CACHE_NAME);
List<IgniteClientFuture<?>> ops = new ArrayList<>();
for (int i = 0; i < 100; i++) {
ops.add(forbiddenCliCache.removeAllAsync());
ops.add(allowedCliCache.removeAllAsync());
}
for (IgniteClientFuture<?> fut : ops) {
try {
fut.get(getTestTimeout(), TimeUnit.MILLISECONDS);
}
catch (Exception e) {
// ignored.
}
}
}
}
/** */
private void prepareCache(IgniteEx ignite) throws Exception {
ignite.createCache(new CacheConfiguration<>()
.setName(DEFAULT_CACHE_NAME)
.setAtomicityMode(TRANSACTIONAL)
.setBackups(1)
.setAffinity(new GridCacheModuloAffinityFunction(2, 1)));
awaitPartitionMapExchange();
try (IgniteClient cli = startClient("allowed_client")) {
for (int i = 0; i < 10000; i++) {
cli.cache(DEFAULT_CACHE_NAME).put(i, i);
}
}
}
/** */
private static IgniteClient startClient(String login) {
return Ignition.startClient(new ClientConfiguration()
.setAddresses("127.0.0.1:10800")
.setUserName(login)
.setUserPassword(""));
}
/** */
private static TestSecurityData userData(String login,
SecurityPermissionSet perms) {
return new TestSecurityData(
login,
"",
perms,
new Permissions()
);
}
}
{code}
The reproducer mentioned above does not reproduce the problem consistently. But
eventually it will hang on waiting for operations to complete.
> Concurrent ClientCache#removeAllAsync calls can hang if authorization failed
> for some of them
> ---------------------------------------------------------------------------------------------
>
> Key: IGNITE-23977
> URL: https://issues.apache.org/jira/browse/IGNITE-23977
> Project: Ignite
> Issue Type: Bug
> Reporter: Mikhail Petrov
> Priority: Major
> Labels: ise
>
> Reproducer:
> {code:java}
> /*
> * 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.ignite.internal.processors.security;
> import java.security.Permissions;
> import java.util.ArrayList;
> import java.util.List;
> import java.util.concurrent.TimeUnit;
> import org.apache.ignite.Ignition;
> import org.apache.ignite.client.ClientCache;
> import org.apache.ignite.client.IgniteClient;
> import org.apache.ignite.client.IgniteClientFuture;
> import org.apache.ignite.configuration.CacheConfiguration;
> import org.apache.ignite.configuration.ClientConfiguration;
> import org.apache.ignite.configuration.ClientConnectorConfiguration;
> import org.apache.ignite.configuration.IgniteConfiguration;
> import org.apache.ignite.internal.IgniteEx;
> import org.apache.ignite.internal.TestRecordingCommunicationSpi;
> import
> org.apache.ignite.internal.processors.cache.distributed.GridCacheModuloAffinityFunction;
> import org.apache.ignite.internal.processors.security.impl.TestSecurityData;
> import
> org.apache.ignite.internal.processors.security.impl.TestSecurityPluginProvider;
> import org.apache.ignite.plugin.security.SecurityPermissionSet;
> import org.apache.ignite.testframework.junits.common.GridCommonAbstractTest;
> import org.junit.Test;
> import static java.util.Collections.singletonMap;
> import static org.apache.ignite.cache.CacheAtomicityMode.TRANSACTIONAL;
> import static
> org.apache.ignite.internal.processors.cache.distributed.GridCacheModuloAffinityFunction.IDX_ATTR;
> import static
> org.apache.ignite.plugin.security.SecurityPermission.ADMIN_CLUSTER_STATE;
> import static
> org.apache.ignite.plugin.security.SecurityPermission.CACHE_CREATE;
> import static org.apache.ignite.plugin.security.SecurityPermission.CACHE_PUT;
> import static org.apache.ignite.plugin.security.SecurityPermission.CACHE_READ;
> import static
> org.apache.ignite.plugin.security.SecurityPermission.CACHE_REMOVE;
> import static
> org.apache.ignite.plugin.security.SecurityPermission.JOIN_AS_SERVER;
> import static
> org.apache.ignite.plugin.security.SecurityPermissionSetBuilder.NO_PERMISSIONS;
> import static
> org.apache.ignite.plugin.security.SecurityPermissionSetBuilder.create;
> /** */
> public class SecurityContextInternalFuturePropagationTest extends
> GridCommonAbstractTest {
> /** {@inheritDoc} */
> @Override protected IgniteConfiguration getConfiguration(String
> igniteInstanceName) throws Exception {
> return super.getConfiguration(igniteInstanceName)
> .setCommunicationSpi(new TestRecordingCommunicationSpi())
> .setUserAttributes(singletonMap(IDX_ATTR,
> getTestIgniteInstanceIndex(igniteInstanceName)))
> .setClientConnectorConfiguration(new
> ClientConnectorConfiguration()
> .setThreadPoolSize(1))
> .setPluginProviders(new TestSecurityPluginProvider(
> igniteInstanceName,
> "",
> create()
> .defaultAllowAll(false)
> .appendSystemPermissions(JOIN_AS_SERVER,
> ADMIN_CLUSTER_STATE)
> .appendCachePermissions(DEFAULT_CACHE_NAME, CACHE_CREATE)
> .build(),
> null,
> false,
> userData("forbidden_client", NO_PERMISSIONS),
> userData("allowed_client", create()
> .defaultAllowAll(false)
> .appendCachePermissions(DEFAULT_CACHE_NAME, CACHE_READ,
> CACHE_PUT, CACHE_REMOVE)
> .build())
> ));
> }
> /** {@inheritDoc} */
> @Override protected void afterTest() throws Exception {
> super.afterTest();
> stopAllGrids();
> }
> /** */
> @Test
> public void testSecurityContextInternalFuturePropagation() throws
> Exception {
> IgniteEx ignite = startGrids(2);
> prepareCache(ignite);
> try (
> IgniteClient allowedCli = startClient("allowed_client");
> IgniteClient forbiddenCli = startClient("forbidden_client")
> ) {
> ClientCache<Object, Object> allowedCliCache =
> allowedCli.cache(DEFAULT_CACHE_NAME);
> ClientCache<Object, Object> forbiddenCliCache =
> forbiddenCli.cache(DEFAULT_CACHE_NAME);
> List<IgniteClientFuture<?>> ops = new ArrayList<>();
> for (int i = 0; i < 100; i++) {
> ops.add(forbiddenCliCache.removeAllAsync());
> ops.add(allowedCliCache.removeAllAsync());
> }
> for (IgniteClientFuture<?> fut : ops) {
> try {
> fut.get(getTestTimeout(), TimeUnit.MILLISECONDS);
> }
> catch (Exception e) {
> // ignored.
> }
> }
> }
> }
> /** */
> private void prepareCache(IgniteEx ignite) throws Exception {
> ignite.createCache(new CacheConfiguration<>()
> .setName(DEFAULT_CACHE_NAME)
> .setAtomicityMode(TRANSACTIONAL)
> .setBackups(1)
> .setAffinity(new GridCacheModuloAffinityFunction(2, 1)));
> awaitPartitionMapExchange();
> try (IgniteClient cli = startClient("allowed_client")) {
> for (int i = 0; i < 10000; i++) {
> cli.cache(DEFAULT_CACHE_NAME).put(i, i);
> }
> }
> }
> /** */
> private static IgniteClient startClient(String login) {
> return Ignition.startClient(new ClientConfiguration()
> .setAddresses("127.0.0.1:10800")
> .setUserName(login)
> .setUserPassword(""));
> }
> /** */
> private static TestSecurityData userData(String login,
> SecurityPermissionSet perms) {
> return new TestSecurityData(
> login,
> "",
> perms,
> new Permissions()
> );
> }
> }
> {code}
> The reproducer mentioned above does not reproduce the problem consistently.
> But eventually it will hang on waiting for operations to complete.
--
This message was sent by Atlassian Jira
(v8.20.10#820010)