import java.lang.constant.*;
import java.lang.classfile.*;
import java.lang.classfile.components.ClassPrinter; 
import java.nio.file.*;
import static java.lang.constant.ConstantDescs.*;
import static java.lang.classfile.ClassFile.*;

public class ModelParent {
    public static void main(String... args) throws Throwable {
        var cf = ClassFile.of();
        var classA = cf.parse(Path.of("A.class"));
        var classB = cf.parse(Path.of("B.class"));
        var methodB = classB.methods().stream().filter(mm -> (mm.flags().flagsMask() & ACC_STATIC) != 0).findFirst().orElseThrow();

        ClassTransform transform0 = ClassTransform.endHandler(clb -> clb.transformMethod(methodB, MethodTransform.transformingCode(CodeTransform.endHandler(cob -> {
                System.out.println("Running");
                cob.getstatic(ClassDesc.of("java.lang.System"), "out", ClassDesc.of("java.io.PrintStream"))
                    .loadConstant("Haha")
                    .invokevirtual(ClassDesc.of("java.io.PrintStream"), "println", MethodTypeDesc.of(CD_void, CD_String))
                    .return_();}))));
                    
        ClassTransform transform1 = (cb, ce) -> {
            if (ce instanceof MethodModel mm) {
                System.out.println(mm.methodName() + " " + mm.parent());
            } else {
                System.out.println(ce);
            }
            cb.with(ce);
        };

        var result = cf.transform(classA, transform0.andThen(transform1));
        var rc = cf.parse(result);
        ClassPrinter.toYaml(rc, ClassPrinter.Verbosity.MEMBERS_ONLY, System.out::print);
    }
}

class A {
    static void methodA() {}
}

class B {
    static void methodB() {}
}