// Path: copybook4java/src/main/java/com/nordea/oss/copybook/converters/TypeConverter.java
// public interface TypeConverter {
//     void initialize(TypeConverterConfig config);
//     void validate(Class<?> type, int size, int decimals);
//     TypeConverter copy(Class<?> type) throws IllegalAccessException, InstantiationException;
//     Object to(byte[] bytes, int offset, int length, int decimals, boolean removePadding);
//     byte[] from(Object value, int length, int decimals, boolean addPadding);
// }
// 
// Path: copybook4java/src/main/java/com/nordea/oss/copybook/converters/TypeConverterConfig.java
// public class TypeConverterConfig {
//     private Charset charset;
//     private CopyBookFieldSigningType signingType;
//     private boolean rightPadding;
//     private char paddingChar;
//     private char nullFillerChar;
//     private String defaultValue;
//     private String format;
// 
//     public TypeConverterConfig() {
//     }
// 
//     public Charset getCharset() {
//         return charset;
//     }
// 
//     public void setCharset(Charset charset) {
//         this.charset = charset;
//     }
// 
//     public CopyBookFieldSigningType getSigningType() {
//         return signingType;
//     }
// 
//     public void setSigningType(CopyBookFieldSigningType signingType) {
//         this.signingType = signingType;
//     }
// 
//     public boolean isRightPadding() {
//         return rightPadding;
//     }
// 
//     public void setRightPadding(boolean rightPadding) {
//         this.rightPadding = rightPadding;
//     }
// 
//     public char getPaddingChar() {
//         return paddingChar;
//     }
// 
//     public void setPaddingChar(char paddingChar) {
//         this.paddingChar = paddingChar;
//     }
// 
//     public char getNullFillerChar() {
//         return nullFillerChar;
//     }
// 
//     public void setNullFillerChar(char nullFillerChar) {
//         this.nullFillerChar = nullFillerChar;
//     }
// 
//     public String getDefaultValue() {
//         return defaultValue;
//     }
// 
//     public void setDefaultValue(String defaultValue) {
//         this.defaultValue = defaultValue;
//     }
// 
//     public String getFormat() {
//         return format;
//     }
// 
//     public void setFormat(String format) {
//         this.format = format;
//     }
// }
// 
// Path: copybook4java/src/main/java/com/nordea/oss/copybook/exceptions/CopyBookException.java
// public class CopyBookException extends RuntimeException {
//     private static final long serialVersionUID = 28118369047109260L;
//     public CopyBookException(String message) {
//         super(message);
//     }
// 
//     public CopyBookException(String message, TypeConverterException ex) {
//         super(message + ": " + ex.getClass().getSimpleName() + " :" + ex.getMessage());
//     }
// 
//     public CopyBookException(String message, Exception ex) {
//         super(message + ": " + ex.getClass().getSimpleName() + " :" + ex.getMessage());
//     }
// }
// 
// Path: copybook4java/src/main/java/com/nordea/oss/copybook/exceptions/TypeConverterException.java
// public class TypeConverterException extends RuntimeException {
//     private static final long serialVersionUID = -7577535992947276304L;
//     public TypeConverterException(String message) {
//         super(message);
//     }
// }


import com.nordea.oss.copybook.annotations.*;
import com.nordea.oss.copybook.converters.TypeConverter;
import com.nordea.oss.copybook.converters.TypeConverterConfig;
import com.nordea.oss.copybook.exceptions.CopyBookException;
import com.nordea.oss.copybook.exceptions.TypeConverterException;
import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.nio.charset.Charset;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
                    }
                    // Try to see if we have a convert for any of the interfaces this type implements
                    if (typeConverter == null) {
                        for (Class<?> aInterface : fieldBaseType.getInterfaces()) {
                            typeConverter = fieldTypeConverterMap.get(copyBookType + "To" + aInterface.getSimpleName());
                            if(typeConverter != null) {
                                try {
                                    typeConverter = typeConverter.copy(type);

                                } catch (IllegalAccessException | InstantiationException e) {
                                    throw new CopyBookException("Failed to copy type convert for this field '" + fieldName + "'", e);
                                }
                            }
                        }
                    }

                } else {
                    if (field.getType().isArray()) {
                        //TODO: Add ArrayTo example and test
                        typeConverter = fieldTypeConverterMap.get("ArrayTo" + fieldTypeName + "Array");
                    }
                    if (typeConverter == null) {
                        typeConverter = fieldTypeConverterMap.get("To" + fieldTypeName);
                    }
                }

                if(typeConverter != null) {
                    try {
                        typeConverter.validate(fieldBaseType, size, decimals);

// Path: copybook4java/src/main/java/com/nordea/oss/copybook/converters/TypeConverter.java
// public interface TypeConverter {
//     void initialize(TypeConverterConfig config);
//     void validate(Class<?> type, int size, int decimals);
//     TypeConverter copy(Class<?> type) throws IllegalAccessException, InstantiationException;
//     Object to(byte[] bytes, int offset, int length, int decimals, boolean removePadding);
//     byte[] from(Object value, int length, int decimals, boolean addPadding);
// }
// 
// Path: copybook4java/src/main/java/com/nordea/oss/copybook/converters/TypeConverterConfig.java
// public class TypeConverterConfig {
//     private Charset charset;
//     private CopyBookFieldSigningType signingType;
//     private boolean rightPadding;
//     private char paddingChar;
//     private char nullFillerChar;
//     private String defaultValue;
//     private String format;
// 
//     public TypeConverterConfig() {
//     }
// 
//     public Charset getCharset() {
//         return charset;
//     }
// 
//     public void setCharset(Charset charset) {
//         this.charset = charset;
//     }
// 
//     public CopyBookFieldSigningType getSigningType() {
//         return signingType;
//     }
// 
//     public void setSigningType(CopyBookFieldSigningType signingType) {
//         this.signingType = signingType;
//     }
// 
//     public boolean isRightPadding() {
//         return rightPadding;
//     }
// 
//     public void setRightPadding(boolean rightPadding) {
//         this.rightPadding = rightPadding;
//     }
// 
//     public char getPaddingChar() {
//         return paddingChar;
//     }
// 
//     public void setPaddingChar(char paddingChar) {
//         this.paddingChar = paddingChar;
//     }
// 
//     public char getNullFillerChar() {
//         return nullFillerChar;
//     }
// 
//     public void setNullFillerChar(char nullFillerChar) {
//         this.nullFillerChar = nullFillerChar;
//     }
// 
//     public String getDefaultValue() {
//         return defaultValue;
//     }
// 
//     public void setDefaultValue(String defaultValue) {
//         this.defaultValue = defaultValue;
//     }
// 
//     public String getFormat() {
//         return format;
//     }
// 
//     public void setFormat(String format) {
//         this.format = format;
//     }
// }
// 
// Path: copybook4java/src/main/java/com/nordea/oss/copybook/exceptions/CopyBookException.java
// public class CopyBookException extends RuntimeException {
//     private static final long serialVersionUID = 28118369047109260L;
//     public CopyBookException(String message) {
//         super(message);
//     }
// 
//     public CopyBookException(String message, TypeConverterException ex) {
//         super(message + ": " + ex.getClass().getSimpleName() + " :" + ex.getMessage());
//     }
// 
//     public CopyBookException(String message, Exception ex) {
//         super(message + ": " + ex.getClass().getSimpleName() + " :" + ex.getMessage());
//     }
// }
// 
// Path: copybook4java/src/main/java/com/nordea/oss/copybook/exceptions/TypeConverterException.java
// public class TypeConverterException extends RuntimeException {
//     private static final long serialVersionUID = -7577535992947276304L;
//     public TypeConverterException(String message) {
//         super(message);
//     }
// }


// Path: copybook4java/src/main/java/com/nordea/oss/copybook/serializers/CopyBookParser.java
import com.nordea.oss.copybook.annotations.*;
import com.nordea.oss.copybook.converters.TypeConverter;
import com.nordea.oss.copybook.converters.TypeConverterConfig;
import com.nordea.oss.copybook.exceptions.CopyBookException;
import com.nordea.oss.copybook.exceptions.TypeConverterException;
import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.nio.charset.Charset;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;

                    }
                    // Try to see if we have a convert for any of the interfaces this type implements
                    if (typeConverter == null) {
                        for (Class<?> aInterface : fieldBaseType.getInterfaces()) {
                            typeConverter = fieldTypeConverterMap.get(copyBookType + "To" + aInterface.getSimpleName());
                            if(typeConverter != null) {
                                try {
                                    typeConverter = typeConverter.copy(type);

                                } catch (IllegalAccessException | InstantiationException e) {
                                    throw new CopyBookException("Failed to copy type convert for this field '" + fieldName + "'", e);
                                }
                            }
                        }
                    }

                } else {
                    if (field.getType().isArray()) {
                        //TODO: Add ArrayTo example and test
                        typeConverter = fieldTypeConverterMap.get("ArrayTo" + fieldTypeName + "Array");
                    }
                    if (typeConverter == null) {
                        typeConverter = fieldTypeConverterMap.get("To" + fieldTypeName);
                    }
                }

                if(typeConverter != null) {
                    try {
                        typeConverter.validate(fieldBaseType, size, decimals);

                    } catch (TypeConverterException ex) {