
Привет, Хабр!
Apache Ignite - это высокопроизводительная, распределённая in-memory платформа, которая предназначена для хранения и обработки больших объёмов данных с ультранизкой задержкой. Основная фича Ignite заключается в его способности обеспечивать молниеносный доступ к данным, распределённым по горизонтально масштабируемому кластеру.
Apache Ignite поддерживает множество функций:
Распределённое кэширование: Ignite позволяет кэшировать данные в памяти.
SQL-совместимость: Ignite предоставляет возможность работы с данными через SQL-запросы.
Транзакции с гарантией ACID.
Настройка и конфигурация Apache Ignite как кэширующего
Для начала нужно определить конфигурацию кэша в Ignite. Это можно сделать через XML или программно в Java. Пример конфигурации кэша в XML:
<bean class="org.apache.ignite.configuration.IgniteConfiguration">
<property name="cacheConfiguration">
<bean class="org.apache.ignite.configuration.CacheConfiguration">
<property name="name" value="myCache"/>
<property name="cacheMode" value="PARTITIONED"/>
<!-- другие параметры -->
</bean>
</property>
</bean>
Ignite можно развернуть в кластере, используя стандартные скрипты запуска, которые входят в его дистрибутив. Для запуска узла Ignite с Java 11 и выше необходимо установить переменную окружения JAVA_HOME
и запустить скрипт ignite.sh
или ignite.bat
с необходимыми параметрами JVM для доступа к некоторым внутренним API JDK.
Для интеграции Ignite с существующими БД через JDBC нужно настроить Ignite как read-through и/или write-through кэш. Так Ignite может автоматически загружать и синхронизировать данные с БД. Можно использовать Ignite как первичное хранилище данных или как кэширующий слой между приложением и БД. Настройка JDBC происходит через определение соединений в конфигурации Ignite и настройки кэша для работы с базой данных, используя соответствующие ключи и параметры SQL.
Пример кода для настройки кэша JDBC:
CacheConfiguration cacheCfg = new CacheConfiguration("SQLPublicPersonCache");
cacheCfg.setIndexedTypes(Long.class, Person.class);
cacheCfg.setCacheMode(CacheMode.PARTITIONED);
cacheCfg.setSqlSchema("PUBLIC");
IgniteConfiguration igniteCfg = new IgniteConfiguration();
igniteCfg.setCacheConfiguration(cacheCfg);
igniteCfg.setJdbcUrl("jdbc:mysql://[hostname]:[port]/[database]");
// Запуск узла Ignite
Ignition.start(igniteCfg);
Код настроит кэш для объектов типа Person
, используемый для SQL-запросов, и указывает параметры подключения к базе данных через JDBC.
Стратегии кэширования данных в Apache Ignite
Стратегия read-through предполагает, что при запросе данных, которых нет в кэше, кэш автоматически загружает данные из БД и сохраняет их в кэше для будущих запросов. Это уменьшает количество обращений к базе данных и ускоряет чтение данных, т.к при последующих запросах данные будут извлекаться непосредственно из кэша.
CacheConfiguration<String, MyData> cacheCfg = new CacheConfiguration<>("myCache");
cacheCfg.setCacheMode(CacheMode.PARTITIONED);
cacheCfg.setReadThrough(true);
cacheCfg.setWriteThrough(true);
IgniteCache<String, MyData> cache = ignite.getOrCreateCache(cacheCfg);
// при отсутствии ключа в кэше, Ignite автоматически загрузит данные из БД
MyData data = cache.get("key");
Write-through обеспечивает синхронизацию данных с базой данных в реальном времени при их изменении в кэше. Каждая операция записи в кэш сопровождается мгновенной записью в базу данных.
CacheConfiguration<String, MyData> cacheCfg = new CacheConfiguration<>("myCache");
cacheCfg.setCacheMode(CacheMode.PARTITIONED);
cacheCfg.setWriteThrough(true);
IgniteCache<String, MyData> cache = ignite.getOrCreateCache(cacheCfg);
// при выполнении put, данные также будут синхронизированы с БД
cache.put("key", new MyData());
Cache-aside требует, чтобы приложение самостоятельно управляло загрузкой данных в кэш и их обновлением. Кэш при этом не взаимодействует напрямую с базой данных. Приложение сначала проверяет наличие данных в кэше, и если они отсутствуют, загружает их из базы данных и помещает в кэш для будущего использования.
IgniteCache<String, MyData> cache = ignite.getOrCreateCache("myCache");
MyData data = cache.get("key");
if (data == null) {
// загрузка данных из БД, если их нет в кэше
data = myDatabase.loadData("key");
cache.put("key", data);
}
Интеграция и API Apache Ignite
Apache Ignite поддерживает распределенный SQL и Key-Value API, позволяющие работать как с традиционными SQL-запросами, так и с простыми операциями на ключах и значениях. SQL API Ignite позволяет выполнять сложные запросы с объединением, агрегацией и группированием данных, которые хранятся в памяти или на диске
Пример SQL запроса:
IgniteCache<Long, City> cityCache = ignite.getOrCreateCache("City");
String sql = "SELECT name, MAX(population) as maxPop FROM City GROUP BY name ORDER BY maxPop DESC";
QueryCursor<List<?>> cursor = cityCache.query(new SqlFieldsQuery(sql));
for (List<?> row : cursor) {
System.out.println("City: " + row.get(0) + ", Population: " + row.get(1));
}
Compute API Ignite позволяет распределенно выполнять задачи на узлах кластера. Сервисы Ignite позволяют развертывать и управлять долгоживущими бизнес-логиками в кластере, пример:
IgniteCompute compute = ignite.compute(ignite.cluster().forServers());
compute.broadcast(() -> System.out.println("Hello from node: " + ignite.cluster().localNode().id()));
Apache Ignite предоставляет API для машинного обучения, позволяя тренировать модели непосредственно на кластере, избегая дорогостоящей передачи данных. Real-Time Streaming API поддерживает интеграцию с системами потоковой обработки данных, такими как Apache Kafka и Apache Flink, для обработки потоков событий в реальном времени, пример:
KNNClassificationTrainer trainer = new KNNClassificationTrainer().withK(3);
KNNClassificationModel mdl = trainer.fit(
ignite,
dataCache,
(k, v) -> new double[] {k.doubleValue()},
(k, v) -> v.doubleValue()
);
double prediction = mdl.predict(new double[]{someValue});
Пример для кэширования данных веб-приложения
Сначала необходимо настроить и запустить узел Ignite. Для этого понадобится файлик конфигурации ignite.xml
:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="ignite.cfg" class="org.apache.ignite.configuration.IgniteConfiguration">
<!-- Включаем кеширование. -->
<property name="cacheConfiguration">
<list>
<bean class="org.apache.ignite.configuration.CacheConfiguration">
<!-- Название кеша -->
<property name="name" value="myCache"/>
<!-- Политика замещения -->
<property name="evictionPolicy">
<bean class="org.apache.ignite.cache.eviction.lru.LruEvictionPolicy">
<property name="maxSize" value="10000"/>
</bean>
</property>
<!-- Режим кеширования -->
<property name="cacheMode" value="PARTITIONED"/>
</bean>
</list>
</property>
</bean>
</beans>
Запусаем узел Ignite, используя этот конфигурационный файл.
Подключите приложение к кешу Apache Ignite. В Java это можно сделать так:
IgniteConfiguration cfg = new IgniteConfiguration();
// устанавливаем конфигурацию кеша
CacheConfiguration cacheCfg = new CacheConfiguration("myCache");
cacheCfg.setCacheMode(CacheMode.PARTITIONED);
cfg.setCacheConfiguration(cacheCfg);
// запуск Ignite node.
Ignite ignite = Ignition.start(cfg);
// получение доступа к кешу.
IgniteCache<Integer, String> cache = ignite.getOrCreateCache("myCache");
// пример работы с кешем.
if (cache.get(1) == null)
cache.put(1, "data");
Таким образом можно кэшировать результаты сложных запросов к БД или часто запрашиваемые пользовательские данные.
С Apache Ignite можно существенно повысить производительность приложений и уменьшить время отклика.
В завершение хочу пригласить вас на бесплатный вебинар курса Data Engineer. Подробнее по ссылке.