当前位置: 首页 > 知识库问答 >
问题:

Apache Ignite 2. x-我可以利用离堆存储并且仍然具有基于时间的驱逐(从

宫俊才
2023-03-14

我正在使用Apache Ignite 2.8.1

我有一个特定的缓存,需要存储在堆外(否则我将面临内存不足的问题)。我还需要分发缓存。

但我还需要一个基于时间的逐出策略来逐出开/关内存缓存中的条目。

Apache Ignite 2是否可能做到这一点。十、

请参见此处的代码片段。我尝试过以各种方式对此进行配置,但除了手动执行之外,没有任何操作会将这些条目从缓存中逐出。

当我运行下面的测试方法时,所有条目都保留在缓存中。

import java.time.LocalDateTime;
import java.util.Arrays;
import java.util.concurrent.TimeUnit;

import javax.cache.expiry.CreatedExpiryPolicy;
import javax.cache.expiry.Duration;

import org.apache.ignite.Ignite;
import org.apache.ignite.Ignition;
import org.apache.ignite.cache.CacheAtomicityMode;
import org.apache.ignite.cache.CacheMode;
import org.apache.ignite.cache.eviction.lru.LruEvictionPolicyFactory;
import org.apache.ignite.configuration.CacheConfiguration;
import org.apache.ignite.configuration.DataRegionConfiguration;
import org.apache.ignite.configuration.DataStorageConfiguration;
import org.apache.ignite.configuration.IgniteConfiguration;
import org.apache.ignite.configuration.NearCacheConfiguration;
import org.apache.ignite.spi.discovery.tcp.TcpDiscoverySpi;
import org.apache.ignite.spi.discovery.tcp.ipfinder.vm.TcpDiscoveryVmIpFinder;
    
public class IgniteCache {
    private static final String ORG_CACHE = IgniteCache.class.getSimpleName() + "Organizations";

    private static Ignite ignite;
    
    private static org.apache.ignite.IgniteCache cache;
    
    public void start() {

        IgniteConfiguration igniteConfiguration = new IgniteConfiguration();
        DataStorageConfiguration dsCfg = new DataStorageConfiguration();
        DataRegionConfiguration dfltDataRegConf = new DataRegionConfiguration();
        dfltDataRegConf.setPersistenceEnabled(true);
        dsCfg.setDefaultDataRegionConfiguration(dfltDataRegConf);
        dsCfg.setStoragePath("E:\\igniteStorage");
        igniteConfiguration.setDataStorageConfiguration(dsCfg);

        TcpDiscoverySpi tcpDiscoverySpi = new TcpDiscoverySpi();
        TcpDiscoveryVmIpFinder ipFinder = new TcpDiscoveryVmIpFinder();
        ipFinder.setAddresses(Arrays.asList("127.0.0.1:47500..47509"));
        tcpDiscoverySpi.setIpFinder(ipFinder);

        igniteConfiguration.setDiscoverySpi(tcpDiscoverySpi);

        ignite = Ignition.start(igniteConfiguration);
        
        ignite.active(true);

        CacheConfiguration<Long, X12File> cacheCfg = new CacheConfiguration<>(ORG_CACHE);

        cacheCfg.setCacheMode(CacheMode.REPLICATED);
        cacheCfg.setAtomicityMode(CacheAtomicityMode.ATOMIC);
        cacheCfg.setBackups(1);
        
        cacheCfg.setEvictionPolicyFactory(new LruEvictionPolicyFactory<>(50000, 40, 5050)); // this doesn't do anything.
        cacheCfg.setNearConfiguration(
                new NearCacheConfiguration<Long, X12File>()
                .setNearEvictionPolicyFactory(new LruEvictionPolicyFactory<>(1_000_000))); // this doesn't do anything.
        
        cache = ignite.getOrCreateCache(cacheCfg);      
        
        for (long i = 0; i < 4_000_000; i++) {
            if (i > 0 && i % 10_000 == 0) {
                System.out.println("Done: " + i);
            }
            cache.withExpiryPolicy(new CreatedExpiryPolicy(new Duration(TimeUnit.SECONDS, 1))) // this expiry policy doesn't do anything
                .put(i, new X12File("x12file" + i, LocalDateTime.now().toString()));
        }
    }
    
    public void test() {
        System.out.println("Checking if cache entries are being properly evicted ...");

        int matches = 0;
        for (long i = 0; i < 4_000_000; i++) {
            if (cache.get(i) != null) {
                ++matches;
            }
        }
        System.out.println("Matches: " + matches);
    }   
}

这只是Apache Ignite 2的一个缺点吗。x在我的特定用例中?

共有2个答案

卫嘉谊
2023-03-14

简而言之:

  • 驱逐是基于内存的。删除一些记录,因为我有太多的行或者它使用了太多的空间
  • 过期是基于时间的。此记录在指定时间段内未被触及,因此应将其删除

所有缓存都脱离堆。您可以为缓存配置到期策略,如下所示:

<bean class="org.apache.ignite.configuration.CacheConfiguration">
    <property name="name" value="myCache"/>
    <property name="expiryPolicyFactory">
        <bean class="javax.cache.expiry.CreatedExpiryPolicy" factory-method="factoryOf">
            <constructor-arg>
                <bean class="javax.cache.expiry.Duration">
                    <constructor-arg value="MINUTES"/>
                    <constructor-arg value="5"/>
                </bean>
            </constructor-arg>
        </bean>
   </property>
</bean>

(近堆/堆内缓存确实起到了一定的作用。但这并不是您所期望的!它们都在堆内,并且在堆外缓存之外工作。)

左丘耀
2023-03-14

正如我从你的代码和解释中了解到的,看起来你对驱逐政策和到期政策有点困惑。

  1. 逐出策略确定在RAM耗尽时应从RAM中删除哪些数据

在您的情况下,您只需要过期策略。看看我的例子:

private static final String ORG_CACHE = IgniteCache.class.getSimpleName() + "Organizations";

public static void main(String[] args) throws Exception {
    DataRegionConfiguration dfltDataRegConf = new DataRegionConfiguration();
    dfltDataRegConf.setPersistenceEnabled(true);

    DataStorageConfiguration dsCfg = new DataStorageConfiguration();
    dsCfg.setDefaultDataRegionConfiguration(dfltDataRegConf);
    dsCfg.setStoragePath("/home/kazakov/tmp");

    IgniteConfiguration igniteConfiguration = new IgniteConfiguration();
    igniteConfiguration.setDataStorageConfiguration(dsCfg);

    TcpDiscoverySpi tcpDiscoverySpi = new TcpDiscoverySpi();
    TcpDiscoveryVmIpFinder ipFinder = new TcpDiscoveryVmIpFinder();
    ipFinder.setAddresses(Arrays.asList("127.0.0.1:47500..47509"));
    tcpDiscoverySpi.setIpFinder(ipFinder);

    igniteConfiguration.setDiscoverySpi(tcpDiscoverySpi);

    try(Ignite ignite = Ignition.start(igniteConfiguration)) {
        ignite.active(true);

        CacheConfiguration<Long, X12File> cacheCfg = new CacheConfiguration<>(ORG_CACHE);

        cacheCfg.setCacheMode(CacheMode.REPLICATED);
        cacheCfg.setAtomicityMode(CacheAtomicityMode.ATOMIC);
        cacheCfg.setBackups(1);
        cacheCfg.setOnheapCacheEnabled(true);

        IgniteCache<Long, X12File> cache = ignite.getOrCreateCache(cacheCfg).withExpiryPolicy(new CreatedExpiryPolicy(new Duration(TimeUnit.SECONDS, 1)));

        for (long i = 0; i < 4_000_000; i++) {
            if (i > 0 && i % 10_000 == 0)
                System.out.println("Done: " + i);

            cache.put(i, new X12File("x12file" + i, LocalDateTime.now().toString()));
        }

        Thread.sleep(5000);

        int matches = 0;
        for (long i = 0; i < 4_000_000; i++) {
            if (cache.get(i) != null)
                ++matches;
        }
        System.out.println("Matches: " + matches);
    }
}
 类似资料:
  • 就像Hazelcast在Listener上有基于时间的驱逐一样,Apache的Ignite缓存中是否有这样的策略。 我试过了, 但这是缓存级逐出,我需要入门级逐出状态。 你能给我提些政策或其他建议吗。

  • 我试图使用和实现以下缓存逻辑: 如果过期时间已经过去,条件(需要计算和I/O)被评估为TRUE,然后强制获取数据并更新缓存。 如果过期时间已经过去,条件(需要计算和I/O)被计算为FALSE,那么不要使缓存数据无效,并从缓存中检索值。 如果过期时间未过,则从缓存中检索该值。 我按照这个指南工作:https://www.baeldung.com/spring-boot-caffeine-cache

  • 对不起,我对反应范式还不熟悉。可以使用AtomicReference来获取Mono的值,因为反应式代码可以异步运行,并且不同的事件可以在不同的线程上运行。请参见下面的示例。我也不确定这段代码是否被认为是被动的 示例代码:

  • 主要内容:src/runoob/heap/MaxHeap.java 文件代码:一、概念及其介绍 堆(Heap)是计算机科学中一类特殊的数据结构的统称。 堆通常是一个可以被看做一棵完全二叉树的数组对象。 堆满足下列性质: 堆中某个节点的值总是不大于或不小于其父节点的值。 堆总是一棵完全二叉树。 二、适用说明 堆是利用完全二叉树的结构来维护一组数据,然后进行相关操作,一般的操作进行一次的时间复杂度在 O(1)~O(logn) 之间,堆通常用于动态分配和释放程序所使用的对象。 若

  • 对于my Identity Server 4,我们设置了两个不同的服务器来承载应用程序。我要求我们的运营团队在两台服务器上安装相同的证书。但是,它们都收到了不同的指纹,并且在以下字段中,证书中的值是不同的:kid、x5t、n,当我加载时,x5c链中的值在两者之间也是不同的。众所周知的/openid配置/jwks地址。我已经把钥匙贴在下面了。这样行吗?我以为x5c的值是一样的。0值,如果它们基于相同

  • 问题内容: 我将最大堆设置为8 GB。当我的程序开始使用约6.4 GB(如VisualVM中所述)时,垃圾回收器开始占用大部分CPU,并且在分配约100 MB时,该程序因OutOfMemory崩溃。我在Windows上使用Oracle Java 1.7.0_21。 我的问题是是否有GC选项可以帮助解决此问题。除-Xmx8g外,我什么也没有传递。 我的猜测是堆越来越碎片化,但是GC是否不应该压缩它?