package gw.vark.typeloader;

import gw.lang.GosuShop;
import gw.lang.reflect.IType;
import gw.lang.reflect.ParameterInfoBuilder;
import gw.lang.reflect.TypeSystem;
import org.apache.tools.ant.IntrospectionHelper;
import org.apache.tools.ant.Project;
import org.apache.tools.ant.Task;
import org.apache.tools.ant.types.EnumeratedAttribute;

/**
* Created with IntelliJ IDEA.
* User: bchang
* Date: 9/27/12
* Time: 11:27 AM
* To change this template use File | Settings | File Templates.
*/
class TaskSetter extends TaskMethod {
  private enum TypeCategory {
    PRIMITIVE,
    ENUM,
    PLAIN
  }
  private TypeCategory _typeCategory;

  TaskSetter(String helperKey, Class type) {
    super(helperKey, type);
    if (type.isPrimitive()) {
      _typeCategory = TypeCategory.PRIMITIVE;
    }
    else if (EnumeratedAttribute.class.isAssignableFrom(type)) {
      _typeCategory = TypeCategory.ENUM;
    }
    else {
      _typeCategory = TypeCategory.PLAIN;
    }
  }

  @Override
  String buildParamName() {
    return _helperKey;
  }

  @Override
  ParameterInfoBuilder createParameterInfoBuilder() {
    return new ParameterInfoBuilder()
            .withName(getParamName())
            .withType(makeParamType(_type))
            .withDefValue(GosuShop.getNullExpressionInstance());
  }

  @Override
  void invoke(Task taskInstance, Object arg, IntrospectionHelper helper) {
    if (TypeCategory.ENUM == _typeCategory) {
      arg = EnumeratedAttribute.getInstance(_type, arg.toString().toLowerCase());
    }
    helper.setAttribute(null, taskInstance, _helperKey, arg);
  }

  IType makeParamType(Class clazz) {
    switch (_typeCategory) {
      case PRIMITIVE:
        return TypeSystem.getBoxType(TypeSystem.get(clazz));
      case ENUM:
        String enumName = TypeSystem.get(_type).getRelativeName().replace('.', '_');
        try {
          return TypeSystem.getByFullName("gw.vark.enums." + enumName);
        }
        catch (Exception e) {
          AntlibTypeLoader.log("could not find generated enum type for " + enumName + " - must use EnumeratedAttribute instance instead", Project.MSG_VERBOSE);
        }
        _typeCategory = TypeCategory.PLAIN;
        // fall through
      case PLAIN:
      default:
        return TypeSystem.get(clazz);
    }
  }
}

@@ -796,37 +796,220 @@
 lse 
-if (EnumeratedAttribute.class
+%7B%0A      _typeCategory = TypeCategory.PLAIN;%0A%0A      // Check if it is an enumerated attribute%0A      try %7B%0A        Class%3C?%3E clazz = TypeSystemUtil.getAntClass(EnumeratedAttribute.class.getName());%0A        if (clazz
 .isA
@@ -1029,32 +1029,36 @@
 (type)) %7B%0A      
+ 
+   
 _typeCategory = 
@@ -1076,16 +1076,20 @@
 y.ENUM;%0A
+    
     %7D%0A  
@@ -1094,56 +1094,156 @@
     
-else %7B%0A      _typeCategory = TypeCategory.PLAIN;
+  %7D catch(ClassNotFoundException ex) %7B%0A        AntlibTypeLoader.log(%22could not load proper EnumeratedAttribute.class%22, Project.MSG_VERBOSE);%0A      %7D
 %0A   

Check against class loader through typesystem, rather than through classloader