Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- /**
- * This version is:
- * - not using DI, generator and formatter are created **inside the EventSender**
- * - has tight coupling with "RandomGenerator" and "JsonFormatter" specific classes
- */
- public class TightCoupling {
- public static void main(String[] args) throws ExecutionException, InterruptedException {
- var eventSender = new EventSender();
- eventSender.send().get();
- }
- @Data
- public static class Event {
- private final String id;
- private final BigDecimal value;
- }
- public static class EventSender {
- private final RandomGenerator generator;
- private final JsonFormatter formatter;
- public EventSender() {
- generator = new RandomGenerator();
- formatter = new JsonFormatter();
- }
- public CompletableFuture send() {
- var event = generator.generate();
- var serialForm = formatter.format(event);
- // send bytes
- }
- }
- public static class RandomGenerator {
- public Event generate() {
- // generate event with random id and value
- }
- }
- public static class JsonFormatter {
- public byte[] format(Event event) {
- // format "event" into json string
- }
- }
- }
- /**
- * This version is:
- * - using DI, all the collaborators/dependencies are **created outside the EventSender** and injected
- * - has tight coupling with "RandomGenerator" and "JsonFormatter" specific classes
- */
- public class TightCouplingWithDI {
- public static void main(String[] args) throws ExecutionException, InterruptedException {
- // this part of work is done by DI framework if any such is used (spring DI, micronaut DI, guice, etc.)
- // but may be done manually just like here, when no DI framework is used and DI is done manually
- var generator = new RandomGenerator();
- var formatter = new JsonFormatter();
- var eventSender = new EventSender(generator, formatter);
- // ---------------------------------------------
- eventSender.send().get();
- }
- @Data
- public static class Event {
- private final String id;
- private final BigDecimal value;
- }
- public static class EventSender {
- private final RandomGenerator generator;
- private final JsonFormatter formatter;
- public EventSender(RandomGenerator generator, JsonFormatter formatter) {
- // when DI is applied, then components never create their collaborators, instead all the collaborators are
- // managed outside and are passed either as constructor params or via setters
- this.generator = generator;
- this.formatter = formatter;
- }
- public CompletableFuture send() {
- var event = generator.generate();
- var serialForm = formatter.format(event);
- // send bytes
- }
- }
- public static class RandomGenerator {
- public Event generate() {
- // generate event with random id and value
- }
- }
- public static class JsonFormatter {
- public byte[] format(Event event) {
- // format "event" into json string
- }
- }
- }
- /**
- * This version is:
- * - not using DI, generator and formatter are created **inside the EventSender**
- * - components are loosely coupled
- */
- public class LooseCouplingWithoutDI {
- public static void main(String[] args) throws ExecutionException, InterruptedException {
- var eventSender = EventSenderFactory.getInstance().create();
- eventSender.send().get();
- }
- @Data
- public static class Event {
- private final String id;
- private final BigDecimal value;
- }
- public interface EventSender {
- CompletableFuture send();
- }
- public interface Generator {
- Event generate();
- }
- public interface Formatter {
- byte[] format(Event event);
- }
- public static class EventSenderFactory {
- private static final EventSenderFactory INSTANCE = new EventSenderFactory();
- private EventSenderFactory() {
- }
- public static EventSenderFactory getInstance() {
- return INSTANCE;
- }
- public EventSender create() {
- // here we decide which impl to use - based on configuration or any other factors
- if (config.get("sender.type").equals("http")) {
- return new HttpSender();
- } else {
- // ......
- }
- }
- }
- public static class GeneratorFactory {
- private static final GeneratorFactory INSTANCE = new GeneratorFactory();
- private GeneratorFactory() {
- }
- public static GeneratorFactory getInstance() {
- return INSTANCE;
- }
- public Generator create() {
- // similar to EventSenderFactory.create() method
- if (config.get("generator.type").equals("random")) {
- return new RandomGenerator();
- } else if (config.get("generator.type").equals("sine")) {
- return new SineGenerator();
- } else {
- // etc.......
- }
- }
- }
- public static class FormatterFactory {
- private static final FormatterFactory INSTANCE = new FormatterFactory();
- private FormatterFactory() {
- }
- public static FormatterFactory getInstance() {
- return INSTANCE;
- }
- public Formatter create() {
- // similar to previous factories
- }
- }
- public static class HttpSender implements EventSender {
- private final Generator generator;
- private final Formatter formatter;
- public HttpSender() {
- // here we're NOT tightly coupled with exact implementations
- // however we're NOT using DI, but instead HttpSender performs collaborators creation
- this.generator = GeneratorFactory.getInstance().create();
- this.formatter = FormatterFactory.getInstance().create();
- }
- public CompletableFuture send() {
- var event = generator.generate();
- var serialForm = formatter.format(event);
- // send bytes over http
- }
- }
- public static class KafkaSender implements EventSender {
- private final Generator generator;
- private final Formatter formatter;
- public HttpSender() {
- // here we're NOT tightly coupled with exact implementations
- // however we're NOT using DI, but instead KafkaSender performs collaborators creation
- this.generator = GeneratorFactory.getInstance().create();
- this.formatter = FormatterFactory.getInstance().create();
- }
- @Override
- public CompletableFuture send() {
- var event = generator.generate();
- var serialForm = formatter.format(event);
- // send bytes to kafka topic
- }
- }
- public static class RandomGenerator implements Generator {
- @Override
- public Event generate() {
- // generate event with random id and value
- }
- }
- public static class SineGenerator implements Generator {
- @Override
- public Event generate() {
- // generate event by sine wave
- }
- }
- public static class JsonFormatter implements Formatter {
- @Override
- public byte[] format(Event event) {
- // format "event" into json string
- }
- }
- public static class KryoFormatter implements Formatter {
- @Override
- public byte[] format(Event event) {
- // serialize event using Kryo
- }
- }
- }
- /**
- * This version is:
- * - using DI, all the collaborators/dependencies are **created outside the EventSender** and injected
- * - components are loosely coupled
- */
- public class LooseCouplingWithDI {
- public static void main(String[] args) throws ExecutionException, InterruptedException {
- // this part of work is done by DI framework if any such is used (spring DI, micronaut DI, guice, etc.)
- // but may be done manually just like here, when no DI framework is used and DI is done manually
- Generator generator;
- switch (config.get("generator.type")) {
- case "random":
- generator = new RandomGenerator();
- break;
- case "sine":
- generator = new SineGenerator();
- break;
- default:
- throw new ConfigurationException();
- }
- Formatter formatter;
- switch (config.get("formatter.type")) {
- case "json":
- formatter = new JsonFormatter();
- break;
- case "kryo":
- formatter = new KryoFormatter();
- break;
- default:
- throw new ConfigurationException();
- }
- EventSender eventSender;
- switch (config.get("sender.type")) {
- case "http":
- eventSender = new HttpSender();
- break;
- case "kafka":
- eventSender = new KafkaSender();
- break;
- default:
- throw new ConfigurationException();
- }
- // ---------------------------------------------------------------------
- eventSender.send().get();
- }
- @Data
- public static class Event {
- private final String id;
- private final BigDecimal value;
- }
- public interface EventSender {
- CompletableFuture send();
- }
- public interface Generator {
- Event generate();
- }
- public interface Formatter {
- byte[] format(Event event);
- }
- public static class HttpSender implements EventSender {
- private final Generator generator;
- private final Formatter formatter;
- public HttpSender(Generator generator, Formatter formatter) {
- // when DI is applied, then components never create their collaborators, instead all the collaborators are
- // managed outside and are passed either as constructor params or via setters
- this.generator = generator;
- this.formatter = formatter;
- }
- public CompletableFuture send() {
- var event = generator.generate();
- var serialForm = formatter.format(event);
- // send bytes over http
- }
- }
- public static class KafkaSender implements EventSender {
- private final Generator generator;
- private final Formatter formatter;
- public KafkaSender(Generator generator, Formatter formatter) {
- // when DI is applied, then components never create their collaborators, instead all the collaborators are
- // managed outside and are passed either as constructor params or via setters
- this.generator = generator;
- this.formatter = formatter;
- }
- @Override
- public CompletableFuture send() {
- var event = generator.generate();
- var serialForm = formatter.format(event);
- // send bytes to kafka topic
- }
- }
- public static class RandomGenerator implements Generator {
- @Override
- public Event generate() {
- // generate event with random id and value
- }
- }
- public static class SineGenerator implements Generator {
- @Override
- public Event generate() {
- // generate event by sine wave
- }
- }
- public static class JsonFormatter implements Formatter {
- @Override
- public byte[] format(Event event) {
- // format "event" into json string
- }
- }
- public static class KryoFormatter implements Formatter {
- @Override
- public byte[] format(Event event) {
- // serialize event using Kryo
- }
- }
- }
Add Comment
Please, Sign In to add comment