Search code examples
javaafp

how to extract metadata from AFP file?


i have a sample AFP file.. want to read TLE(Tag Logical Element) from it to get certain predefined tags such as account no or bill number so that i can convert that to PDF for particular bill no. Also is there any public Java api for performing the same action.


Solution

  • There are two different types of TLE: group level and page level. Group level TLE appear right after a BNG (Begin Named Group), while page level TLEs appear after the environment group of a page (BPG). The TLE itself uses two triplets to carry the meta data: FullyQualifiedName and AttributeValue. The first contains the key name, and the other one the value.

    With the assumption that your AFP is well-formed following code helps you extracting the meta data from TLEs:

    import java.io.BufferedInputStream;
    import java.io.FileInputStream;
    import java.io.IOException;
    import java.util.Optional;
    
    import org.afplib.afplib.*;
    import org.afplib.base.*;
    import org.afplib.io.AfpInputStream;
    
    public class DumpTLE {
    
    public static void main(String[] args) {
        try (AfpInputStream in = new AfpInputStream(
                new BufferedInputStream(new FileInputStream(args[0])))) {
    
            int page = 0;
            int group = 0;
            boolean pageLevel = false;
            SF sf;
            while((sf = in.readStructuredField()) != null) {
    
                if(sf instanceof BPG) {
                    page++;
                    pageLevel = true;
                }
                if(sf instanceof EPG) {
                    pageLevel = false;
                }
                if(sf instanceof BNG) {
                    group++;
                }
    
                if(sf instanceof TLE) {
                    TLE tle = (TLE) sf;
    
                    Optional<FullyQualifiedName> fqn = tle.getTriplets().stream()
                            .filter(FullyQualifiedName.class::isInstance).map(FullyQualifiedName.class::cast)
                            .findFirst();
                    Optional<AttributeValue> value = tle.getTriplets().stream()
                            .filter(AttributeValue.class::isInstance).map(AttributeValue.class::cast)
                            .findFirst();
    
                    if(fqn.isPresent() && value.isPresent()) {
                        if(pageLevel) {
                            System.out.println("page "+page+" - "+fqn.get().getFQName()+":"+value.get().getAttVal());
                        } else {
                            System.out.println("group "+group+" - "+fqn.get().getFQName()+":"+value.get().getAttVal());
                        }
                    }
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    
    }
    
    }
    

    The code uses afplib (https://github.com/yan74/afplib). Converting your AFP to PDF is a totally different story and not that easy.