Fake Code easy implements

package org.miniframe.modules.utils;

import java.util.HashMap;
import java.util.Map;

import javax.script.Bindings;
import javax.script.ScriptContext;
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;
 

public class FakeCode {
	
	private static final ScriptEngineManager sem = new ScriptEngineManager();
	private static final ScriptEngine engine = sem.getEngineByName("groovy");
	private Bindings bindings = engine.getBindings(ScriptContext.ENGINE_SCOPE);
	private static boolean cacheFlag = true;
	private static Map<String,Object> cacheMap = new HashMap<String,Object>();
	
	public FakeCode(){
		bindings.put("tag", new TagImpl());
	}
	
	/**
	 * call fake code with parameter map
	 * 
	 * same expression and params will be cache next time call
	 * 
	 * @param expression
	 * @param params
	 * @return
	 */
	public Object eval(String expression,Map<String,Object> params){
		CacheKey ck = new CacheKey(expression,params);
		Object obj = cacheMap.get(ck.getKey());
		if(obj!=null){
			return obj;
		}else{
			try {
				if(params.containsKey("tag")){
					throw new RuntimeException("you can't override system key");
				}
				bindings.putAll(params);
				obj = engine.eval(expression);
			} catch (ScriptException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			if(cacheFlag){
				cacheMap.put(ck.getKey(), obj);
			}
		} 
		return obj;
	}
	
	/**
	 * call fake code with parameter index
	 * 
	 * same expression and params will be cache next time call
	 * 
	 * @param expression
	 * @param args
	 * @return
	 */
	public Object eval(String expression,Object...args){
		CacheKey ck = new CacheKey(expression,args);
		Object obj = cacheMap.get(ck.getKey());
		if(obj!=null){
			return obj;
		}else{
			try {
				obj = engine.eval(String.format(expression,args));
			} catch (ScriptException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			if(cacheFlag){
				cacheMap.put(ck.getKey(), obj);
			}
		} 
		return obj;
	}
	
	public void addBuinding(String key, Object value){
		bindings.put(key, value);
	}
	
	class CacheKey{
		String expression;
		Object[] args = new Object[0];
		Map<String,Object> params = new HashMap<String,Object>();
		public CacheKey(String expression,Object...args){
			this.expression=expression;
			this.args=args;
		}
		public CacheKey(String expression,Map<String,Object> params){
			this.expression=expression;
			this.params=params;
		}
		  
		public String getKey(){
			StringBuffer sb = new StringBuffer(expression); 
			for(Object arg:args){
				sb.append(arg);
			}
			for(Map.Entry<String, Object> entry:params.entrySet()){
				sb.append(entry.getKey()).append(entry.getValue());
			}
			return sb.toString();
		}
		
	}
	
	class TagImpl{
		
		/**
		 * judge user account has Tag 
		 * 
		 * @param account
		 * @return
		 */
		public boolean hasTag(int account){ 
			boolean result= account%2==0;
			//... judge this account has Tag.
			return result;
		}
		
		/**
		 * judge user account is manager
		 * 
		 * @param account
		 * @return
		 */
		public boolean isManager(int account){
			boolean result= account%2!=0;
			//... judge this account has Tag.
			return result;
		}
	}

	/**
	 * @param args
	 */
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		FakeCode fc = new FakeCode();
		System.out.println(fc.eval("tag.hasTag(%1$s)",10));
		System.out.println(fc.eval("tag.hasTag(%1$s)",9));
		System.out.println(fc.eval("tag.isManager(%1$s)",10));
		System.out.println(fc.eval("tag.isManager(%1$s)",10));
		System.out.println(fc.eval("tag.isManager(%1$s)",9));
		System.out.println(fc.eval("tag.isManager(%1$s)&&tag.hasTag(%1$s)",9));
		System.out.println(fc.eval("tag.isManager(%1$s)&&tag.hasTag(%2$s)",9,10));
		//may be you will feel that i don't want to define %1$s, i can't remember the index.
		
		Map<String,Object> params = new HashMap<String,Object>();
		params.put("account", 10);
		System.out.println(fc.eval("tag.hasTag(account)",params));
		System.out.println(fc.eval("tag.hasTag(account)",params)); 
	}

}

你可能感兴趣的:(code)