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

org.beanio.parser.flat.FlatBeanDefinition Maven / Gradle / Ivy

Go to download

A Java un/marshalling library for CSV, XML, delimited and fixed length stream formats.

There is a newer version: 2.1.0
Show newest version
/*
 * Copyright 2011 Kevin Seim
 * 
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.beanio.parser.flat;

import java.lang.reflect.Array;
import java.util.*;

import org.beanio.parser.*;

/**
 * Provides support for formatting bean objects for delimited and fixed length formatted records.
 * 
 * @author Kevin Seim
 * @since 1.0
 */
public abstract class FlatBeanDefinition extends BeanDefinition {

    /**
     * Recursively formats a bean object into a record.
     * @param record the record object
     * @param bean the bean to format
     */
    protected void formatRecord(Object record, Object bean) {
        formatBean(0, record, bean, null);
    }
       
    @SuppressWarnings("unchecked")
    private int formatBean(int offset, final Object record, Object bean, List backfill) {
        if (isCollection()) {
            if (bean == null) {
                for (int i=0; i)bean) {
                    formatProperty(offset + getLength() * i, record, obj, backfill);
                    ++i;
                }
            }
        }
        else {
            formatProperty(offset, record, bean, backfill);
        }
        return 0;
    }
    
    private void formatProperty(int offset, final Object record, Object bean, List backfill) {
        List fieldList = getPropertyList();
        for (PropertyDefinition property : fieldList) {
            
            final Object value = bean != null ?  getBeanProperty(property, bean) : null;
            if (property.isBean()) {
                ((FlatBeanDefinition)property).formatBean(offset, record, value, backfill);
            }
            else if (property.isField()) {
                final FieldDefinition field = (FieldDefinition) property;
                final int position = field.getPosition() + offset;
                
                if (value != null || !field.isLazy()) {
                    // when we encounter a required field or non-null value, write all previous
                    // optional fields to the stream
                    if (backfill != null && !backfill.isEmpty()) {
                        for (Runnable r : backfill) {
                            r.run();
                        }
                        backfill.clear();
                    }
                    addField(field, position, record, value);
                }
                else {
                    // if the value is null and the field isn't required, skip it for now
                    // until a required field is found
                    if (backfill == null) {
                        backfill = new LinkedList();
                    }
                    backfill.add(new Runnable() {
                        public void run() {
                            addField(field, position, record, value);
                        }
                    });
                }
            }
        }
    }
    
    @SuppressWarnings("unchecked")
    private void addField(FieldDefinition field, int position, Object record, Object value) {
        if (field.isCollection()) {
            int fieldLength = field.getLength();
            
            if (value == null) {
                String text = field.formatValue(null);
                for (int i=0; i)value) {
                    updateRecord(record, position + i*fieldLength, field.formatValue(obj));
                    ++i;
                }
            }
        }
        else {
            updateRecord(record, position, field.formatValue(value));
        }
        
    }
    
    /**
     * This method is called by formatRecord to set the field text on the record
     * object being formatted.
     * @param record the record object
     * @param position the field position
     * @param text the field text
     */
    protected abstract void updateRecord(Object record, int position, String text);

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy