You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

能否在ComputeJob中访问模型类及反序列化IgniteCache值?

问题:ComputeJob中反序列化IgniteCache值遇到ClassNotFoundException,UriDeploymentSpi是否适用?

能否在ComputeJob中反序列化IgniteCache中的值?尝试操作时,我遇到了Marshaller相关的ClassNotFoundException。目前仅能通过使用BinaryObject(例如IgniteCache<BinaryObject, BinaryObject>),或在Ignite节点上安装包含模型的jar包(需重启节点)来实现可靠反序列化。

我希望将集群作为计算任务的通用资源池,以支持同一应用的多个版本使用该集群。由于每个应用实例会加载各自的数据,我并不希望在节点上安装单一版本的“模型实体”jar包。使用UriDeploymentSpi进行代码部署会是理想方案,请问这是否可行?或者我的Ignite使用方式不符合预期?

附ComputeJob代码:

public class FetchAtivoStatsNovoJob implements ComputeJob, IgniteCallable<Map<String, Integer>> {

    @IgniteInstanceResource
    private Ignite ignite;

    private List<Long> filterIds;

    private String ativosNovoCache;

    public FetchAtivoStatsNovoJob(List<Long> filterIds, String ativosNovoCache) {
        this.ativosNovoCache = ativosNovoCache;
        this.filterIds = filterIds;
    }

    @Override
    public Object execute() throws IgniteException {
        try {
            return call();
        } catch (Exception e) {
            throw new IgniteException("Failed to fetch posts.", e);
        }
    }

    @Override
    public Map<String, Integer> call() throws Exception {

        IgniteCache<AtivoKeyNovo, AtivoNovo> cache = ignite.getOrCreateCache(ativosNovoCache);

        ScanQuery<AtivoKeyNovo, AtivoNovo> query = new ScanQuery<>();
        query.setLocal(true);
        query.setFilter((k, ativo) -> filterIds.contains(k.getSubdominioId()));

        Map<String, Integer> result = new HashMap<String, Integer>();

        try (QueryCursor<Cache.Entry<AtivoKeyNovo, AtivoNovo>> cursor = cache.query(query)) {
            for (Cache.Entry<AtivoKeyNovo, AtivoNovo> entry : cursor) {

                AtivoKeyNovo key = entry.getKey();
                AtivoNovo value = entry.getValue();

                // do some calculation, put on the result Map or insert a new record on another IgniteCache
            }
        }
        return result;
    }

    @Override
    public void cancel() {
    }

}

回答

1. UriDeploymentSpi完全可行,匹配你的需求

UriDeploymentSpi正是为动态类部署场景设计的,能完美解决你不想在节点提前安装固定版本jar包的问题:

  • 只需将包含AtivoKeyNovo、AtivoNovo实体类以及ComputeJob的jar包,上传到所有集群节点可访问的URI路径(如共享文件目录、HTTP服务器)
  • 配置Ignite节点启用UriDeploymentSpi并指定上述URI,节点会自动拉取并加载对应类,无需重启
  • 提交任务时,Ignite会自动处理类的分发与隔离,不同应用版本的类通过类加载器隔离,不会产生冲突,直接解决ClassNotFoundException问题

2. 其他可选方案

如果UriDeploymentSpi的配置成本较高,还可以考虑:

  • Peer Class Loading机制:提交ComputeJob时,将实体类字节码随任务一同发送到节点,Ignite自动加载依赖类。需注意为不同应用版本配置独立的类加载器,避免类版本冲突。
  • BinaryObject按需反序列化:继续使用IgniteCache<BinaryObject, BinaryObject>,在需要业务逻辑处理时,通过binaryObject.deserialize()方法将其转换为具体实体类,无需提前部署类,但代码中需额外处理类型转换逻辑。

3. 代码调整建议

你的FetchAtivoStatsNovoJob代码本身没有问题,但需注意:

  • 确保AtivoKeyNovo和AtivoNovo实现Serializable接口,或更推荐的IgniteBinarylizable接口(序列化效率更高)
  • 如果使用UriDeploymentSpi,需确保jar包包含所有依赖类,且节点能正常拉取到该jar包

4. 你的Ignite使用方式符合设计目标

将集群作为通用计算资源池、支持多版本应用共享的思路,完全契合Ignite分布式计算+缓存的核心设计定位,不存在使用方式不符合预期的问题。


内容的提问来源于stack exchange,提问作者user19903

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.13 03:33:14