Spring Learning II: Write a spring based on spring

Source: Internet
Author: User

Please read my other article first: "Spring learning One: the IOC (Control inversion) and the AOP (aspect-oriented) XML configuration and annotation method" probably knew his simple usage

Then I want to write a simple sping, annotated way to write later

Method: 1. Parsing XML configuration

2. Production of dynamic proxy objects using the reflection mechanism of Java

3. Scan the annotations on the class, then use Reflection (not written)

The code is as follows (simple implementation, heavy principle, light code, not happy to spray)

XML configuration I just use my previous spring-test configuration, the code is also used in the previous article, but the parsing is written with their own, no call any spring API code

<?xml version= "1.0" encoding= "UTF-8"? ><beans xmlns= "Http://www.springframework.org/schema/beans" xmlns: Mvc= "Http://www.springframework.org/schema/mvc" xmlns:xsi= "Http://www.w3.org/2001/XMLSchema-instance" xmlns: context= "Http://www.springframework.org/schema/context" xmlns:aop= "HTTP://WWW.SPRINGFRAMEWORK.ORG/SCHEMA/AOP" xsi:schemalocation= "Http://www.springframework.org/schema/beans Http://www.springframewor K.org/schema/beans/spring-beans-3.0.xsd Http://www.springframework.org/schema/context http                  ://www.springframework.org/schema/context/spring-context-3.0.xsd HTTP://WWW.SPRINGFRAMEWORK.ORG/SCHEMA/MVC Http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd http://www.springframework.or  G/SCHEMA/AOP http://www.springframework.org/schema/aop/spring-aop-3.0.xsd "> <!-- annotation support, in order for us to use annotations to create bean--><context:annotation-config/><!--Set the location of the package to be scanned--<context:component-scan base-package= "Com.eyugame.test"/><!--support AOP annotations-->< Aop:aspectj-autoproxy/><aop:config ><!--The class that configures the AOP trigger call is MyService, which corresponds to the Myserviceimpl--&GT;&LT;AOP: Aspect id= "SPECT" ref= "MYAOP" ><!--configured to invoke Com.eyugame.test.MyBean's Todo () method when triggering AOP--><aop:pointcut id= " Target "expression=" Execution (* com.eyugame.test.MyBean.toDo (..)) "/><!--called before execution, calling method Dobefore--&GT;&LT;AOP: Before pointcut-ref= "target" method= "Dobefore ()"/><!--after execution, call method Doafter--><aop:after pointcut-ref= " Target "method=" Doafter () "/><!--returned when called, method Doreturn--><aop:after-returning pointcut-ref=" Target " Method= "Doreturn ()"/><!--throw an exception when called, call method Doreturn--><aop:after-throwing pointcut-ref= "target" method= " Dothrowing () "throwing=" ex "/><!--note aop:aroup in the new version spring seems to expire, pit me--><!--<aop:around pointcut-ref=" Businessservice "method=" Doaround "/>--></aop:aspect></aop:config><beAn id= "MYAOP" class= "Com.eyugame.test.MyAop" ></bean><bean id= "Depedecybean" class= " Com.eyugame.test.DependencyBean "></bean><!--Dependency Injection 1 constructor injected--><bean id=" Mybean "class=" Com.eyugame.test.MyBean "><constructor-arg ref=" Depedecybean "></constructor-arg></bean>< !--Dependency Injection 2 setpoint injection--><bean id= "myBean2" class= "com.eyugame.test.MyBean2" ><!--name is consistent with the name of the class to be injected into the class-->< Property Name= "Idependency" ref= "Depedecybean" ></property></bean><!--annotated AOP--><bean id= " MyAop2 "class=" Com.eyugame.test.MyAop2 "></bean></beans>

The code is as follows

Package Com.eyugame.test.context;import Java.beans.beaninfo;import Java.beans.introspectionexception;import Java.beans.introspector;import Java.beans.propertydescriptor;import Java.io.inputstream;import Java.lang.reflect.constructor;import Java.lang.reflect.invocationtargetexception;import Java.lang.reflect.Method ; Import Java.util.arraylist;import Java.util.hashmap;import java.util.list;import Java.util.map;import Javax.xml.parsers.documentbuilder;import Javax.xml.parsers.documentbuilderfactory;import Net.sf.cglib.proxy.enhancer;import Net.sf.cglib.proxy.methodinterceptor;import Net.sf.cglib.proxy.MethodProxy; Import Org.w3c.dom.document;import org.w3c.dom.element;import org.w3c.dom.nodelist;/** * Custom Parsing XML * * @author k560 * */ public class MyApplicationContext {/* Config symbol */private static string LINK = "/";p rivate static string bean = "Bean";p rivate static string bean_id = "ID";p rivate static string bean_ref = "REF";p rivate static string bean_constroctor_arg = "Construc Tor-arg ";p rivatestatic string Bean_property = "Property";p rivate static string bean_class = "CLASS";p rivate static string bean_name = "Nam E ";p rivate static string aop_config =" Aop:config ";p rivate static string aop_aspect =" Aop:aspect ";p rivate static string A Op_pointcut = "Aop:pointcut";p rivate static string aop_before = "Aop:before";p rivate static string aop_after = "Aop:after" ;p rivate static string aop_after_returning = "aop:after-returning";p rivate static string aop_after_thrwoing = "AOP: After-throwing ";p rivate static String method =" Method ";p rivate static string expression =" expression ";/* used to store Beanid, and Cl The location of the */private map<string, entry> beanmap;private IAop aop;/* construction method */public MyApplicationContext (String path) {b Eanmap = new hashmap<string, entry> (); AOP = new AOP (); init (path); /* Get Bean */public Object getbean (String beanid) {try {Entry Entry = Beanmap.get (Beanid) by ID; Myinvocationhandler invo = new Myinvocationhandler (AOP); if (entry.constructors! = null &&!entry.construCtors.isempty ()) {/* constructor injected */int size = Entry.constructors.size (); object[] params = new Object[size];for (int i = 0; I &lt ; Size i++) {Entry en = entry.constructors.get (i); if (en.constructors = = NULL | | en.constructors.isEmpty ()) {class<?> Claz z = Class.forName (Beanmap.get (en.id). ClassName);p Arams[i] = invo.getinstance (clazz);} else {Params[i] = This.getbean (en.id);}} Object obj = invo.getinstance (Class.forName (entry.classname), params); return obj;} Object obj = invo.getinstance (Class.forName (entry.classname)); if (entry.properties! = NULL &&!) Entry.properties.isEmpty ()) {int pSize = Entry.properties.size (); for (int i = 0; i < pSize; i++) {Entry en = Entry.prop Erties.get (i); object[] params = new Object[psize];if (en.properties = = NULL | | en.properties.isEmpty ()) {class<?> C Lazz = Class.forName (Beanmap.get (en.id). ClassName);p Arams[i] = invo.getinstance (clazz);} else {Params[i] = This.getbean (en.id);} This.setpro (obj, En.name, params[i]);}} return obj;} catch (exception e) {e.printstacktrace ();} return null;} /* Reflection method injection */public void Setpro (object bean, String name, Object param) throws Introspectionexception, Illegalaccessexcep tion, illegalargumentexception, invocationtargetexception {BeanInfo BeanInfo = Introspector.getbeaninfo ( Bean.getclass ()); propertydescriptor[] PropertyDescriptors = Beaninfo.getpropertydescriptors (); for (PropertyDescriptor PD: PropertyDescriptors) {String name2 = Pd.getname (); if (Name.equals (name2)) {method = Pd.getwritemethod (); if (!name . Equalsignorecase ("class")) {Method.invoke (bean, param);}}} /* Initialize */private void init (String path) {documentbuilderfactory dbf = documentbuilderfactory.newinstance ();D Ocumentbuilder documentbuilder;try {documentbuilder = Dbf.newdocumentbuilder (); InputStream InputStrem = This.getClass (). getResourceAsStream (LINK + path);D ocument doc = Documentbuilder.parse (inputstrem); NodeList nList = Doc.getelementsbytagname (BEAN); int length = Nlist.getlength (); for (int i = 0; i < length; i++) {ElemeNT node = (Element) nlist.item (i); NodeList constructors = Node.getelementsbytagname (Bean_constroctor_arg); NodeList pros = Node.getelementsbytagname (bean_property); String id = node.getattributes (). getNamedItem (bean_id). Getnodevalue (); String className = Node.getattributes (). getNamedItem (Bean_class). Getnodevalue (); Entry Entry = new Entry (id); entry.classname = Classname;int clength = Constructors.getlength (); if (Clength > 0) {LIST&L T entry> cList = new arraylist<entry> (); for (int j = 0; J < Clength; J + +) {String key = Constructors.item (j). Get Attributes (). getNamedItem (Bean_ref). Getnodevalue (); Entry centry = new Entry (key); Clist.add (centry);} Entry.constructors = cList;}  int plength = Pros.getlength (); if (Plength > 0) {list<entry> pList = new arraylist<entry> (); for (int j = 0; J < Plength; J + +) {String key = Pros.item (j). GetAttributes (). getNamedItem (Bean_ref). Getnodevalue (); String name = Pros.item (j). GetAttributes (). getNamedItem (Bean_name). Getnodevalue (); EntryPentry = new Entry (key);p entry.name = Name;plist.add (pentry);} Entry.properties = pList;} Beanmap.put (ID, entry);} NodeList aoplist = Doc.getelementsbytagname (aop_config); int aoplength = Aoplist.getlength ();/* AOP parsing */for (int i = 0; I & Lt Aoplength; i++) {Element aopnode = (Element) aoplist.item (i); NodeList acelist = Aopnode.getelementsbytagname (aop_aspect); int alength = Acelist.getlength (); for (int j = 0; J < Aleng Th J + +) {String key = Acelist.item (i). GetAttributes (). getNamedItem (Bean_ref). Getnodevalue (); String className = This.beanMap.get (key). ClassName; element node = (element) acelist.item (i); NodeList nn = node.getelementsbytagname (aop_pointcut); String expression = Nn.item (0). GetAttributes (). getNamedItem (expression). Getnodevalue (); String before = Node.getelementsbytagname (Aop_before). Item (0). GetAttributes (). getNamedItem (METHOD). Getnodevalue () ; String after = Node.getelementsbytagname (Aop_after). Item (0). GetAttributes (). getNamedItem (METHOD). Getnodevalue (); String returning = Node.getElementsbytagname (aop_after_returning). Item (0). GetAttributes (). getNamedItem (METHOD). Getnodevalue (); String throwing = Node.getelementsbytagname (aop_after_thrwoing). Item (0). GetAttributes (). getNamedItem (METHOD). Getnodevalue (); This.aop.addAfter (new Target (className, after, expression)) This.aop.addBeafore (new Target ( ClassName, before, expression); This.aop.addReturn (New Target (className, returning, expression)); This.aop.addThrow ( New Target (className, throwing, expression));}}} catch (Exception e) {e.printstacktrace ();}}} /* Information for storing beans */class Entry {/* Bean ID */string id;/* bean name */string name;/* Bean's class */string classname;/* constructor injection parameter Bea N */list<entry> constructors;/* Method injection parameter */list<entry> properties;public Entry (String id) {this.id = id;}}  /** * cglib Dynamic Agent * */class Myinvocationhandler implements Methodinterceptor {private IAop aop;private Object target;public Myinvocationhandler () {super ();} Public Myinvocationhandler (IAop AOP) {super (), THIS.AOP = Aop;this.aop.setinvo (this);}public object Getinstanceforobject (object target) {this.target = target; Enhancer enhancer = new Enhancer () Enhancer.setsuperclass (This.target.getClass ());//callback Method Enhancer.setcallback (this) ;//Create proxy object return Enhancer.create ();} /** * Production Agent Object * * @param T * class to Proxy * @param clazzs * Parameter type * @param params * parameter list * @retur n */public <T> t getinstance (Class<?> T, class<?>[] Clazzs, object[] params) {Enhancer enhancer = new En Hancer (); Enhancer.setsuperclass (T);//callback Method Enhancer.setcallback (this);//Create proxy object @suppresswarnings ("unchecked") T target = (T) enhancer.create (Clazzs, params); this.target = Target;return target;} /** * Production Agent Object * * @param T * class to Proxy * @param params * parameter list * @return */public <T> t getinstance (Class<?> T, object[] params) {Enhancer enhancer = new enhancer (); Enhancer.setsuperclass (T);//callback Method Enhancer.setcallback (this); constructor<?>[] ts = t.getconstructors (); for (constructor<?> Constructor: TS) {class<?>[] Clazzs = Constructor.getparametertypes (); try {@SuppressWarnings ("unchecked") T target = (t) Enhancer.create (Clazzs, params); this.target = Target;return target;} catch (Exception e) {continue;}} return null;} /** * Production Agent Object * * @param t * @return * * * @SuppressWarnings ("unchecked") public <T> T getinstance (class<?> t) {ENH Ancer enhancer = new Enhancer (); Enhancer.setsuperclass (t);//callback Method Enhancer.setcallback (this);//Create proxy object T target = (t) Enhancer.create (); this.target = Target;return target;} /** * Faceted AOP */public object Intercept (Object obj, method, object[] params, Methodproxy proxy) throws Throwable {I F (AOP! = null) {String className = Obj.getclass (). GetName (); String methodName = Method.getname (); try {aop.dobefore (className, MethodName, params);p roxy.invokesuper (obj, params); Aop.doafter (ClassName, methodName, params); Aop.doreturn (ClassName, methodName, params);} catch (Throwable e) {e.printstacktrace (); Aop.dotthrow (ClassName, methodName, params);}} Else {System.out.println (Method.getname ());p roxy.invokesuper (obj, params);} return null;}} /* AOP */class AOP implements IAOP {/* Execute pre-call */private list<target> beaforelist;/* after execution call */private List<target&gt ; Afterlist;private list<target> returnlist;private list<target> throwlist;private MyInvocationHandler Invo;public Aop () {this.beaforelist = new arraylist<target> (); this.afterlist = new arraylist<target> (); This.returnlist = new arraylist<target> (); this.throwlist = new arraylist<target> ();} public void Setinvo (Myinvocationhandler invo) {this.invo = Invo;} public void Addbeafore (target target) {This.beaforeList.add (target);} public void Addafter (target target) {This.afterList.add (target);} public void Addreturn (target target) {This.returnList.add (target);} public void Addthrow (target target) {This.throwList.add (target);} public void Dobefore (string className, String methodName, object[] params) {for (Target target:beaforelist) {Target.todo (ClassName, MEthodname, params, invo);}} public void Doafter (string className, String methodName, object[] params) {for (Target target:afterlist) {Target.todo (cl Assname, MethodName, params, invo);}} public void Doreturn (string className, String methodName, object[] params) {for (Target target:returnlist) {Target.todo ( ClassName, MethodName, params, invo);}} public void Dotthrow (string className, String methodName, object[] params) {for (Target target:throwlist) {Target.todo (c Lassname, MethodName, params, invo);}}} /* Record the class name to be AOP processed, method name, */class target {/** * AOP object */string aopname;/** * AOP Call non-method */string methodname;/** * Expression */string E Xecution;public Target (String aopname, String methodName, string execution) {super (); this.aopname = Aopname; This.methodname = Methodname;this.execution = execution;} public void Todo (string className, String methodName, object[] params, Myinvocationhandler invo) {if (This.istrue (Classna Me, MethodName, params) {try {class<?> Aopclass = class.forname (this.aopname); Object AOP = Invo.getinstance (Aopclass); method = Aopclass.getmethod (This.methodName.replace ("()", "")), Method.invoke (AOP, new object[] {});} catch (Exception e) {e.printstacktrace ();}}} /** * Parse execution whether the match I directly wrote Dead */public boolean isTrue (String className, String methodName, object[] params) {if (className. Contains ("com.eyugame.test.mybean$$") && methodname.equals ("ToDo")) {return true;} return false;}} /* AOP interface */interface IAop {void Setinvo (Myinvocationhandler invo); void Dobefore (String className, String methodName, Obje Ct[] params); void Doafter (String className, String methodName, object[] params); void Doreturn (String className, String me Thodname, object[] params), void Dotthrow (String className, String methodName, object[] params), void Addbeafore (Target Target), void Addafter (target target), void Addreturn (target target), void Addthrow (target target);}



Test

Package Com.eyugame.test.context;import Com.eyugame.test.mybean;import Com.eyugame.test.mybean2;public class Test { public static void Main (string[] args) {MyApplicationContext context = new MyApplicationContext ("config/spring/ Spring-test.xml ");/* constructor injection, AOP*/SYSTEM.OUT.PRINTLN (" Mybean will have AOP-----------"); Mybean Mybean = (Mybean) context.getbean ("Mybean"); Mybean.todo ();/* Registration Method Injection */SYSTEM.OUT.PRINTLN ("MyBean2 without AOP, Because there is no configuration------------"); MyBean2 myBean2 = (MyBean2) context.getbean ("myBean2"); Mybean2.todo ();}}



Running results like I use spring, there's no


Spring Learning II: Write a spring based on spring

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.