All Downloads are FREE. Search and download functionalities are using the official Maven repository.

src.main.java.com.mgnt.lifecycle.management.package-info Maven / Gradle / Ivy

Go to download

Set of various Utils: stacktrace noise filter, String to/from unicode sequence converter, simple Http client JSON parser/serializer, Silent String parsing to Integer and other numeric types, Parsing String to time intervals with support for time unit suffixes, JSON parser that provides serialization/deserialization of classes to JSON, Version comparator and Version ranges operations, Self-throttling binary reader from Http request, File reader, A utility that automatically initiates a Factory with instances of all classes that implement user provided interface. An infrastructure for writing Scheduled Task classes where time interval for task execution is provided in humanly readable format (such as "9h" for 9 hours)

There is a newer version: 1.7.0.1
Show newest version
/**
 * This package contains some small infrastructure that simplifies and automates working with Factories that provide
 * concrete implementations of an Interface. The package contains just 2 classes:
 * {@link com.mgnt.lifecycle.management.BaseEntityFactory} and {@link com.mgnt.lifecycle.management.BaseEntity}. In short
 * what this infrastructure does is that if you create a factory that extends
 * {@link com.mgnt.lifecycle.management.BaseEntityFactory} and some Interface with all its concrete implementations
 * extending {@link com.mgnt.lifecycle.management.BaseEntity} then each your concrete implementation class instances will be
 * automatically inserted into your factory. You won't have to worry about how and when to populate your factory. The
 * infrastructure will do it for you when the constructor of your concrete implementation class is invoked. So all you
 * will have to do is to create any number of concrete implementation classes and make sure that for each one constructor
 * is invoked. After that you can use your factory to get any of your concrete implementation classes anywhere in your code.
 * This is short explanation. There are few more details but not that many.
 *
 * 

* Lets show it with an example. This infrastructure has Package {@code com.mgnt.lifecycle.management.example} * that has some sub-packages that contains source code example that demonstrate how this infrastructure is used. So in * this javadoc the same classes will be used. Please see the source code of that package to get all the details. * Say you have an Interface called * {@link com.mgnt.lifecycle.management.example.InfoFormatter} that has a single method * {@link com.mgnt.lifecycle.management.example.InfoFormatter#formatMessage(java.lang.String)}. Obviously this method * takes some text and formats it according some logic that would be implemented in each concrete implementation. *

* Next we need to create a factory for our concrete implementations. So we have a factory class * {@link com.mgnt.lifecycle.management.example.InfoFormatterFactory} that extends * {@link com.mgnt.lifecycle.management.BaseEntityFactory} This class look like this: *

* package com.mgnt.lifecycle.management.example;
* * import com.mgnt.lifecycle.management.BaseEntityFactory;
* import java.util.Collection;
*
* public class InfoFormatterFactory extends BaseEntityFactory<InfoFormatter> {
*   private static InfoFormatterFactory FACTORY = new InfoFormatterFactory();
*
*   private InfoFormatterFactory() {
*   }
*
*   public static InfoFormatterFactory getFactoryInstance() {
*     return FACTORY;
*   }
*
*   public static InfoFormatter getInstance(String key) {
*     return FACTORY.getEntity(key);
*   }
*
*     public static Collection getAllInstances() {
*     return FACTORY.getAllEntities();
*   }
* }
*

*

* * * For the purposes of this infrastructure it is recommended that a single abstract parent class extending * {@link com.mgnt.lifecycle.management.BaseEntity} and implementing your interface is created. Then all your concrete * implementations will extend this class. So in our case we will have * {@link com.mgnt.lifecycle.management.example.BaseInfoFormatter} that extends {@link com.mgnt.lifecycle.management.BaseEntity} * and implements {@link com.mgnt.lifecycle.management.example.InfoFormatter}. * This class should look like this: *


* *   public abstract class BaseInfoFormatter extends BaseEntity<BaseInfoFormatter> implements InfoFormatter {
*
*      // This is mandatory part of the code for the infrastructure to work
*      private static final String FACTORY_TYPE = BaseInfoFormatter.class.getSimpleName();
*
*      static {
*        init(FACTORY_TYPE, InfoFormatterFactory.getFactoryInstance());
*      }
*
*      public BaseInfoFormatter() {
*          super(FACTORY_TYPE);
*      }
*
*      public BaseInfoFormatter(String customName) {
*        super(FACTORY_TYPE, customName);
*      }
*
*      // The end of mandatory part
*
*      // Some business logic methods that are common to all concrete implementations
*      //...
*
*      //Implementation of interface declared method
*      //...
*   }
*

* * Then we have 2 concrete implementations: {@link com.mgnt.lifecycle.management.example.implementations.JsonInfoFormatter} * and {@link com.mgnt.lifecycle.management.example.implementations.XmlInfoFormatter} (both of them extending their abstract * parent class {@link com.mgnt.lifecycle.management.example.BaseInfoFormatter}). Here is how one of them might look, * (the second looks very similar so it is ommitted here) *


*   public class JsonInfoFormatter extends BaseInfoFormatter {
*      private final static String CUSTOM_NAME = "JSON";
*
*      public JsonInfoFormatter() {
*        super(CUSTOM_NAME);
*      }
*
*      //Implementation of abstract method or overriding methods goes here
*   }
*

* * So this is our row material so to speak. * So lets see how this is used. Look at the class * {@link com.mgnt.lifecycle.management.example.implementations.usage.UsageExample} and in particular its methods * {@link com.mgnt.lifecycle.management.example.implementations.usage.UsageExample#init()} (that is invoked in the main() * method) and looks as folllows *


*    private static void init() {
*      new JsonInfoFormatter();
*      new XmlInfoFormatter();
*    }
*
*


* and * {@link com.mgnt.lifecycle.management.example.implementations.usage.UsageExample#printFormattedGreetings()} that looks * as follows *


*    private static void printFormattedGreetings() {
*      InfoFormatter formatter = InfoFormatterFactory.getInstance("JSON");
*      System.out.println("JSON greeting: " + formatter.formatMessage(MESSAGE));
*      formatter = InfoFormatterFactory.getInstance("XML");
*      System.out.println("XML greeting: " + formatter.formatMessage(MESSAGE));
*      List allMessages = new ArrayList<>();
*      for(InfoFormatter formattedMessage : InfoFormatterFactory.getAllInstances()) {
*        allMessages.add(formattedMessage.formatMessage(MESSAGE));
*      }
*      System.out.println("All greetings: " + allMessages);
*    }
*
*

* Note that we simply use {@link com.mgnt.lifecycle.management.example.InfoFormatterFactory#getInstance(java.lang.String)} * to get ahold of our concrete implementations. This works because method init was invoked before. Note that in init method * we simply instantiate our concrete implementations and not saving any references to them. Thanks to the infrastructure, * during its instantiation each instance inserted itself into its factory and that allows it to be accessed through the * factory. As for the names ("XML" and "JSON") they are in our case defined in each concrete class and passed to the factory * through use of its parent constructor * {@link com.mgnt.lifecycle.management.example.BaseInfoFormatter#BaseInfoFormatter(java.lang.String)} which in turn will * invoke its parent constructor {@link com.mgnt.lifecycle.management.BaseEntity#BaseEntity(java.lang.String, java.lang.String)}. * However, {@link com.mgnt.lifecycle.management.BaseEntity} provides another constructor * {@link com.mgnt.lifecycle.management.BaseEntity#BaseEntity(java.lang.String)} where custom name for entity is not * required. And the entity would be registered in its factory by its class name. *

*
* That was about how this infrastructure works. Now where would it be convenient and beneficial to use it? Note that in order * for infrastructure to work we had to invoke constructor for each concrete class. If only someone or something could * have done that for us, that would be magical. Well, this could be done for us by Spring framework. Remember that Spring * instantiate all it's defined beans during its initialization. So within Spring context if we simply declare our concrete * implementations as Spring beans, Spring would instantiate them for us, thus initializing their factory automatically. * This could be very convenient. Imagine that you have some bean that has a property of type * {@link com.mgnt.lifecycle.management.example.InfoFormatter}, but which actual implementation would be needed is determined * at runtime. So at that moment you can use * {@link com.mgnt.lifecycle.management.example.InfoFormatterFactory#getInstance(java.lang.String)} to access needed * implementation. This will allow you not to inject ALL your concrete instantiations into your bean and you won't have to * use Spring BeanFactory to access a Spring defined bean as that would violate non-intrusiveness of Spring (meaning * you can write components which have no dependency on Spring). Also, If at some later stage you will need to add * more concrete implementations, all you will have to do is to add your implementation classes to you code and declare * them to be Spring beans. The rest will be done by Spring and this infrastructure! *

*/ package com.mgnt.lifecycle.management;




© 2015 - 2024 Weber Informatics LLC | Privacy Policy