Открытый семинар для студентов в компании CUSTIS (23 мая 2013 года).
Лектор: Сергей Кошель, ведущий разработчик Java, аналитик.
Аннотация: Из этого семинара вы узнаете о практическом применении паттерна Dependency Injection в мире Java и предоставляемых им возможностях на примере развития DI-фреймворков: от Spring и Guice до CDI/Weld. Формат встречи – динамичный с элементами Live Coding и демонстрацией особенностей реализации.
Видеозапись семинара: https://vimeo.com/67125102.
Аспектно-ориентированное программирование в распределенных системах для java ...Igor Suhorukov
Про использование AspectJ Scripting для модификации существующего java приложения без его перекомпиляции и пересборки.
Основные преимущества:
* написание аспектов только за счет конфигурации агента на java подобном языке MVEL;
* использовании в скриптах любых классов и ресурсов из maven репозитариев с их динамической загрузкой во время выполнения;
* возможность загрузки конфигурации агента при старте jvm как с файловой системы, так и с веб сервера
* сочетание jvm агента AspectJ и привычного синтаксиса pointcut выражений упрощают изучение: существует подробная официальная документация AspectJ и публикации в интернет.
* open source/apache license, наличие исходного кода на github и сборки агента на central.maven.org
Область применения jvm агента - микросервисы и приложения для jvm(в том числе и распределенные). AspectJ Scripting позволяет собирать метрики приложения и jvm, выполнять трассировку распределенного приложения, делать дампы запросов/ответов, изменять поведение существующего приложения.
У вас древний проект? Все зовут его «Legacy», а вас «неудачник»? Возможно они даже смеются над вами.
Давайте взглянем на ситуацию с другого ракурса. Все (все, Карл!) успешные проекты рано или поздно превращаются в Legacy-проекты.
Я затрону тему Legacy не просто как явление, а как возможность быть постоянно в тренде, прослыть супер-спецом (даже если ты знаешь всего два фреймворка), сделать карьеру, как делать, то что ты хочешь, а не то что тебя просят. Ладно, ладно, я наврал про два фреймворка, но все остальное чистая правда. Я покажу, что вы можете творить, имея правильный подход к Legacy коду.
Суть в том, что Legacy — это не грустно/уныло/немодно, это просто/клево/весело, если с умом подойти к задаче!
CDI Best Practices with Real-Life Examples - TUT3287Ahmad Gohar
As the adoption of Contexts and Dependency Injection (CDI) for Java EE API grows, it is important to understand how to use CDI effectively to maximize the benefits of using a loosely coupled, type-safe, annotation-driven dependency injection solution. This session outlines the best practices for using CDI, such as annotations versus XML, @Named as a qualifier, qualifier type safety versus verbosity, effective use of producers/disposers, using scopes properly, best practices for using conversations, defining effective stereotypes, interceptors versus decorators, static versus dynamic injection/lookup, CDI versus Java EE resource injection, using CDI with EJB 3.1, CDI/JSF 2 integration patterns, and CDI/JPA 2 usage patterns.
Аспектно-ориентированное программирование в распределенных системах для java ...Igor Suhorukov
Про использование AspectJ Scripting для модификации существующего java приложения без его перекомпиляции и пересборки.
Основные преимущества:
* написание аспектов только за счет конфигурации агента на java подобном языке MVEL;
* использовании в скриптах любых классов и ресурсов из maven репозитариев с их динамической загрузкой во время выполнения;
* возможность загрузки конфигурации агента при старте jvm как с файловой системы, так и с веб сервера
* сочетание jvm агента AspectJ и привычного синтаксиса pointcut выражений упрощают изучение: существует подробная официальная документация AspectJ и публикации в интернет.
* open source/apache license, наличие исходного кода на github и сборки агента на central.maven.org
Область применения jvm агента - микросервисы и приложения для jvm(в том числе и распределенные). AspectJ Scripting позволяет собирать метрики приложения и jvm, выполнять трассировку распределенного приложения, делать дампы запросов/ответов, изменять поведение существующего приложения.
У вас древний проект? Все зовут его «Legacy», а вас «неудачник»? Возможно они даже смеются над вами.
Давайте взглянем на ситуацию с другого ракурса. Все (все, Карл!) успешные проекты рано или поздно превращаются в Legacy-проекты.
Я затрону тему Legacy не просто как явление, а как возможность быть постоянно в тренде, прослыть супер-спецом (даже если ты знаешь всего два фреймворка), сделать карьеру, как делать, то что ты хочешь, а не то что тебя просят. Ладно, ладно, я наврал про два фреймворка, но все остальное чистая правда. Я покажу, что вы можете творить, имея правильный подход к Legacy коду.
Суть в том, что Legacy — это не грустно/уныло/немодно, это просто/клево/весело, если с умом подойти к задаче!
CDI Best Practices with Real-Life Examples - TUT3287Ahmad Gohar
As the adoption of Contexts and Dependency Injection (CDI) for Java EE API grows, it is important to understand how to use CDI effectively to maximize the benefits of using a loosely coupled, type-safe, annotation-driven dependency injection solution. This session outlines the best practices for using CDI, such as annotations versus XML, @Named as a qualifier, qualifier type safety versus verbosity, effective use of producers/disposers, using scopes properly, best practices for using conversations, defining effective stereotypes, interceptors versus decorators, static versus dynamic injection/lookup, CDI versus Java EE resource injection, using CDI with EJB 3.1, CDI/JSF 2 integration patterns, and CDI/JPA 2 usage patterns.
Будущее omni-channel маркетинга: инструменты, кейсы и цифрыCUSTIS
Выступление Артема Казакова, директора по маркетингу Retail Rocket, на бизнес-завтраке «К 2017 готовы: продвинутые инструменты маркетинга для интернет-магазинов» (13 декабря 2016 года, Москва).
JavaOne 2011: Migrating Spring Applications to Java EE 6Bert Ertman
The Spring Framework has no-doubt played a major role in evolving the way we write enterprise applications on the Java platform today. However, it is still a proprietary framework owned by a single company. The age of having to rely on such proprietary frameworks in order to develop decent enterprise applications is now over and Java EE 6 has become an even easier way to develop enterprise applications based on standards which makes it the best choice for any enterprise application. In this session you will experience how to migrate a typical full stack Spring application to a standards based, completely portable, Java EE 6 application including integration tests.
[Note that this talk is not available outside some very specific settings but this deck is here for you as a basic resource to form a basis for your own analysis based on my reasonably objective extensive professional experience using both technology sets in the real world]
Java EE 7 has been one of the most significant overhauls of the platform. Just some of the changes include retiring EJB 2 entity beans and JAX-RPC, greater alignment with CDI, WebSocket/HTML 5 support, a standard API for JSON processing, the next version of JAX-RS, an overhaul of JMS, long-awaited concurrency utilities, batch processing in Java EE and much, much more. In order to make educated choices for adoption, one should understand how the widely-used Spring Framework aligns with Java EE.
This session will compare and contrast the Spring Framework with Java EE 7. We will focus on key areas that include the component development model, dependency injection, persistence, UI, REST, messaging, security and testing. Beyond API/features, the analysis will take a holistic view in covering concerns such as ease-of-use, manageability, ecosystem and vendor-neutrality.
Секрет производства: программный продукт, за который не будет стыдноCUSTIS
Открытый семинар для студентов в компании CUSTIS (15 октября 2015 года).
Лектор: Виктор Крапивин, архитектор.
Аннотация: В программном проекте разработчику постоянно приходится работать с унаследованным кодом созданных ранее программ, которые предстоит доделать, исправить или сделать источником примеров в дальнейшей практике. В процессе изучения такого исходного кода программисты часто возмущаются, порой не без оснований заявляя: «Ну кто же так пишет?!». Многочисленные непонятные решения, срочные заплаты для исправления критических ошибок, «костыли» — во всем этом непросто разобраться даже при наличии документации, а ведь иногда она уже не актуальна или ее нет совсем.
Создавая программный продукт, который может «дожить» до промышленной эксплуатации, необходимо помнить, что рано или поздно он попадет в руки программистов, не имеющих отношения к его первоначальной разработке. В ходе этого семинара мы на примерах из мира Java продемонстрируем, как создать этот продукт таким образом, чтобы «потомки» остались довольны.
Видеозапись семинара: https://vimeo.com/142895727.
Сергей Константинов — Что интересного готовит нам W3CYandex
2014 год обещает нам множество интересных нововведений. Помимо новинок в HTML5, нас ждут глобальные изменения в самой веб-платформе. Promises и модули — революция в стандартах разработки стандартов. Service Workers — новый подход к решению проблемы офлайновых веб-приложений. @@create — отнаследуйся от HTMLElement! Обо всём этом и пойдёт речь в докладе.
Бодрящий микс из Selenium и TestNG- регрессионное тестирование руками разрабо...Andrey Rebrov
Как-то так происходит, что “на 10 девчонок по статистике 9 ребят”, а точнее на группу из 5-7 разработчиков – 1 тестировщик. Или его нет совсем. Так что очень часто приходится и код писать, и тестировать, а дата релиза все ближе и ближе.
В тех случаях, когда мы пишем веб-приложение, помочь в нашей нелегкой судьбе может бодрящий микс из Selenium и TestNG... Как это сделали мы, какие потом получили выводы и результаты — все это я и хочу рассказать и показать
Ловля сетями. Инструменты отладки сетевых запросов приложений / Дмитрий Рыбак...Ontico
РИТ++ 2017, AppsConf
Зал Найроби + Касабланка, 5 июня, 11:00
Тезисы:
http://appsconf.ru/2017/abstracts/2584.html
Большинство современных мобильных приложений так или иначе работает с каким-то API (а зачастую и не с одним). Количество запросов при этом может достигать десятков в минуту и понимание того, что сейчас происходит в сетевом слое вашего приложения, становится непростой задачей.
Я расскажу и покажу весь диапазон современных средств для мониторинга и отладки сетевых запросов: от самых простых до узкоспециальных - с плюсами/минусами каждого из инструментов и областями их применения.
Практические основы тестирования на php Unit-test: понятия, тонкости, пути решения, вопросы для проработки.
PHPUnittest fast start
Разработано http://webgloss.ru
Java 8, самой заметной фичей которой стало появление лямбд, вышла два года назад, а в этом году мы даже начали её использовать в продакшен коде Идеи. Такое заметное нововведение в языке вызывает множество вопросов. Какие возможности перед нами открываются и какие проблемы при неаккуратном использовании лямбд могут возникнуть, как лямбды устроены внутри, во что они компилируются и как исполняются — вот темы, которые мы обсудим на докладе.
Выступление Владимира Рахтеенко, нашего генерального директора, и Германа Алексеева, ИТ-директора ГК «Спортмастер», на Неделе российского ритейла (7 июня 2017 года, Москва).
Будущее уже наступило: от Agile к бирюзовым организациямCUSTIS
Выступление Максима Цепкова, нашего главного архитектора дирекции развития решений, на форуме «Дни PR и маркетинга на Юге» (1 июня 2017 года, Ростов-на-Дону).
Диаграммы учета как средство для наглядного и целостного отображения правил у...CUSTIS
Выступление Максима Цепкова, нашего главного архитектора дирекции развития решений, на конференции «Соколовские чтения «Бухгалтерский учет: взгляд из прошлого в будущее» (22 апреля 2017 года, Санкт-Петербург).
Опыт построения микросервисной архитектуры в цифровом банкеCUSTIS
Выступление Андрея Солощака, ведущего архитектора «Бинбанка», на профессиональной встрече CUSTIS Meetup: Микросервисы в Enterprise (16 марта 2017 года, Москва).
Золотая лихорадка MSA: почему нам не подошли микросервисы?CUSTIS
Выступление Юрия Веретельникова, сооснователя и технического директора Solit Clouds, на профессиональной встрече CUSTIS Meetup: Микросервисы в Enterprise (16 марта 2017 года, Москва).
Выступление Игоря Беспальчука, нашего руководителя проектов, на профессиональной встрече CUSTIS Meetup: Микросервисы в Enterprise (16 марта 2017 года, Москва).
От монолитных моделей предметной области — к модульнымCUSTIS
Выступление Максима Цепкова, нашего главного архитектора дирекции развития решений, на World Information Architecture Day (18 февраля 2017 года, Санкт-Петербург).
Опыт применения метода ATAM для оценки архитектурыCUSTIS
Выступление Игоря Беспальчука, нашего руководителя проектов дирекции архитектуры, на заседании русского отделения INCOSE (9 ноября 2016 года, Москва).
Видеозапись выступления:
https://vimeo.com/190918892
Process и Case Management в информационной системе: от автоматизации As Is к ...CUSTIS
Выступление Максима Цепкова, нашего главного архитектора дирекции развития решений, на ежегодной конференции CEE-SECR – 2016 (29 октября 2016 года, Москва).
4. Первая версия
+ Работать будет
− Невозможно написать unit-тест
public class Adapter {
public void processMessage() {
final FileSource fileSource = new FileSource();
final SimpleConverter simpleConverter = new SimpleConverter();
final DatabaseStorage databaseStorage = new DatabaseStorage();
final Message inputMessage = fileSource.getMessage();
final Message convertedMessage = simpleConverter.convert(inputMessage);
databaseStorage.store(convertedMessage);
}
}
4/36
6. И добавляем фабрики
public class Adapter {
public void processMessage() {
final Source source = SourceFactory.getSource();
final Converter converter = ConverterFactory.getConverter();
final Storage storage = StorageFactory.getStorage();
final Message inputMessage = source.getMessage();
final Message convertedMessage = converter.convert(inputMessage);
storage.store(convertedMessage);
}
}
6/36
7. Пишем тест
@Test
public void processMessage() throws Exception {
SourceFactory.setSource(new MockSource("Hello from test!"));
StorageFactory.setStorage(new MockStorage());
final Adapter adapter = new Adapter();
adapter.processMessage();
// assert that...
}
+ Получилось написать тест
− Статический (глобальный) контекст
− Много бойлерплейта
− Зависимости неочевидны
7/36
8. Избавляемся от фабрик
public class Adapter {
private Source source;
private Converter converter;
private Storage storage;
public void setSource(Source source) {…}
public void setConverter(Converter converter) {…}
public void setStorage(Storage storage) {…}
public void processMessage() {
final Message inputMessage = source.getMessage();
final Message convertedMessage = converter.convert(inputMessage);
storage.store(convertedMessage);
}
}
8/36
9. Переписываем тест
@Test
public void processMessage() throws Exception {
final Adapter adapter = new Adapter();
adapter.setSource(new MockSource("Hello from test!"));
adapter.setConverter(new SimpleConverter());
adapter.setStorage(new MockStorage());
adapter.processMessage();
// assert that...
}
+ Получилось:
Setter based Dependency Injection by Hand
9/36
10. Последний штрих
public class Adapter {
private final Source source;
private final Converter converter;
private final Storage storage;
public Adapter(Source source, Converter converter, Storage storage) {
this.source = source;
this.converter = converter;
this.storage = storage;
}
public void processMessage() {…}
}
10/36
11. Dependency Injection (DI)
Паттерн проектирования (design pattern)
О компонентах и их зависимостях
Позволяет отделить объявление
зависимости от разрешения зависимости
(и в пространстве, и во времени)
Является частью более общего принципа
Inversion of Control (Hollywood principle –
«Don't call us, we'll call you».)
11/36
12. Причем тут тесты?
Тесты не самоцель, но…
С одной стороны, практически,
DI позволяет проще писать
тестопригодный код
А с другой стороны, концептуально,
тесторигодность кода является
индикатором хорошей слабосвязанной
архитектуры (loose coupling)
В конечном итоге DI помогает удобнее
писать слабосвязный код
12/36
13. Можно было пойти другим путем
public class Adapter {
public void processMessage() {
final Source source = UniversalFactory.get("source", Source.class);
final Converter converter = UniversalFactory.get("converter",
Converter.class);
final Storage storage = UniversalFactory.get("storage", Storage.class);
final Message inputMessage = source.getMessage();
final Message convertedMessage = converter.convert(inputMessage);
storage.store(convertedMessage);
}
}
+ Получилось: Service Locator
13/36
14. Паттерны DI и SL
часто противопоставляются
DI зависимости определяет статически
Проще разобраться в связях
Компилятор многое может проверить
и подсказать
Но иногда это является ограничением
SL – динамически
Взаимосвязи запутаны, проще ошибиться
Но иногда без этого не обойтись
14/36
15. IoC-контейнер
Автоматизирует DI
Разрешает граф зависимостей
Конструирует компоненты по метаописанию
зависимостей
И привносит еще много полезностей
Управление жизненным циклом
Управление конфигурацией
AOP
…
15/36
16. Disclaimer
Автор не в коем случае не имеет
цели принизить один фреймворк
за счет другого
16/36
19. Запускаем контейнер
final ApplicationContext applicationContext
= new ClassPathXmlApplicationContext("spring-config.xml");
adapter = applicationContext.getBean("adapter", Adapter.class);
+ Код адаптера не изменился
+ …нет зависимости от Spring’а
+ …не надо его писать в каком-либо
специальном стиле
19/36
21. Lifecycle Management
singleton – создается один экземпляр
prototype – создается отдельный экземпляр
при каждом обращении
<bean id="adapter" class="custis.seminars.diinjava.autowiring.Adapter"
autowire="byType"
scope="singleton"
init-method="init"
destroy-method="close" />
[…]
applicationContext.destroy();
21/36
22. Метаданные в компоненте
@Scope(SCOPE_SINGLETON)
public class Adapter {
private Source source;
private Converter converter;
private Storage storage;
@Autowired
public void setSource(Source source) {…}
@Autowired
public void setConverter(Converter converter) {…}
@Autowired(required = false)
public void setStorage(Storage storage) {…}
@PostConstruct
public void init() {…}
@PreDestroy
public void close() {…}
} 22/36
23. Выбор
между несколькими реализациями
23/36
<bean id="source" class="custis.seminars.diinjava.autowiring.FileSource" />
@Autowired
@Qualifier("source")
public void setSource(Source source) {…}
− Легко ошибиться, и проявится это только в рантайме
25. Pure Java config
public class AdapterModule extends AbstractModule {
@Override
protected void configure() {
bind(SimpleConverter.class);
bind(Source.class).to(FileSource.class);
bind(Storage.class).toInstance(new DatabaseStorage());
}
}
final Injector injector = Guice.createInjector(new AdapterModule());
adapter = injector.getInstance(Adapter.class);
25/36
26. Annotation based
@Singleton
public class Adapter {
private final Source source;
private final Converter converter;
private final Storage storage;
@Inject
public Adapter(Source source, Converter converter, Storage storage) {
this.source = source;
this.converter = converter;
this.storage = storage;
}
public void processMessage() {…}
}
* Зависимость от аннотаций, но они стандартные
26/36
27. Pure Java config
public class AdapterModule extends AbstractModule {
@Override
protected void configure() {…}
@Provides
Source fileSource() {
return new FileSource();
}
}
* В Spring 3.0 появился JavaConfig
27/36
28. Provider interface
public interface Provider <T> {
T get();
}
bind(Validator.class).to(SimpleValidator.class);
public class Adapter {
private Provider<Validator> validator;
@Inject
public void setValidator(Provider<Validator> validator) {…}
public void processMessage() {
...
validator.get().validate(inputMessage);
...
}
}
28/36
29. Provider interface
Когда нужно…
отложить создание (тяжелое, условное)
много экземпляров (the new «new»)
вложить более узкий скоуп в широкий
29/36
30. Выбор
между несколькими реализациями
30/36
@BindingAnnotation
@Target({ FIELD, PARAMETER, METHOD }) @Retention(RUNTIME)
public @interface FileBased {}
@Inject
public Adapter(@FileBased Source source, Converter converter, Storage storage) {…}
bind(Source.class).annotatedWith(FileBased.class).to(FileSource.class);
+ Typesafe – компилятор проверит
31. CDI/Weld
JSR 299: Contexts and Dependency Injection
for the Java EE platform
Weld – reference implementation
for JSR-299
31/36
32. CDI
Конфигурация похожа на Guice
Нет DSL — используется @Produce
и сканирование classpath
Стандартизирует @Inject, @Sengleton,
Provider<T> и т. д.
Тесно интегрируется с EJB-контейнером
32/36
33. Instance – Provider на стероидах
Расширяет возможности Provider
Instance<T> extends Provider<T>
…опциональные зависимости
if (instance.isUnsatisfied()) {…}
…многозначные зависимости
if (instance.isAmbiguous()) {
for (T t : instance) {...}
}
…динамическое разрешение зависимостей (SL)
adapter = instance.select(Adapter.class).get();
33/36
34. Event<T>
public class Adapter {
@Inject
Event<AdapterStarted> adapterStartedEvent;
@PostConstruct
public void init() {
adapterStartedEvent.fire(new AdapterStarted());
}
}
public class AnyOtherManagedBean{
public void onAdapterStart(
@Observes AdapterStarted adapterStarted) {…}
}
34/36
35. О чем не рассказал
AOP и method intercepting
Генерализованные типы зависимостей
Многозначные зависимости
Scopes
…
35/36