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

org.hibernate.loader.plan.build.spi.ReturnGraphTreePrinter Maven / Gradle / Ivy

There is a newer version: 7.0.0.Alpha1
Show newest version
/*
 * Hibernate, Relational Persistence for Idiomatic Java
 *
 * License: GNU Lesser General Public License (LGPL), version 2.1 or later.
 * See the lgpl.txt file in the root directory or .
 */
package org.hibernate.loader.plan.build.spi;

import java.io.ByteArrayOutputStream;
import java.io.PrintStream;
import java.io.PrintWriter;

import org.hibernate.loader.plan.spi.BidirectionalEntityReference;
import org.hibernate.loader.plan.spi.CollectionAttributeFetch;
import org.hibernate.loader.plan.spi.CollectionFetchableElement;
import org.hibernate.loader.plan.spi.CollectionFetchableIndex;
import org.hibernate.loader.plan.spi.CollectionReference;
import org.hibernate.loader.plan.spi.CompositeFetch;
import org.hibernate.loader.plan.spi.EntityFetch;
import org.hibernate.loader.plan.spi.EntityReference;
import org.hibernate.loader.plan.spi.EntityReturn;
import org.hibernate.loader.plan.spi.Fetch;
import org.hibernate.loader.plan.spi.FetchSource;
import org.hibernate.loader.plan.spi.Return;
import org.hibernate.loader.plan.spi.ScalarReturn;

/**
 * Prints a {@link Return} graph as a tree structure.
 * 

* Intended for use in debugging, logging, etc. * * @author Steve Ebersole */ public class ReturnGraphTreePrinter { /** * Singleton access */ public static final ReturnGraphTreePrinter INSTANCE = new ReturnGraphTreePrinter(); private ReturnGraphTreePrinter() { } public String asString(Return rootReturn) { return asString( rootReturn, 0 ); } public String asString(Return rootReturn, int depth) { final ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); final PrintStream ps = new PrintStream( byteArrayOutputStream ); write( rootReturn, depth, ps ); ps.flush(); return new String( byteArrayOutputStream.toByteArray() ); } public void write(Return rootReturn, PrintStream printStream) { write( rootReturn, new PrintWriter( printStream ) ); } public void write(Return rootReturn, int depth, PrintStream printStream) { write( rootReturn, depth, new PrintWriter( printStream ) ); } // todo : see ASTPrinter and try to apply its awesome tree structuring here. // I mean the stuff it does with '|' and '\\-' and '+-' etc as // prefixes for the tree nodes actual text to visually render the tree public void write(Return rootReturn, PrintWriter printWriter) { write( rootReturn, 0, printWriter ); } public void write(Return rootReturn, int depth, PrintWriter printWriter) { if ( rootReturn == null ) { printWriter.println( "Return is null!" ); return; } printWriter.write( TreePrinterHelper.INSTANCE.generateNodePrefix( depth ) ); if ( ScalarReturn.class.isInstance( rootReturn ) ) { printWriter.println( extractDetails( (ScalarReturn) rootReturn ) ); } else if ( EntityReturn.class.isInstance( rootReturn ) ) { final EntityReturn entityReturn = (EntityReturn) rootReturn; printWriter.println( extractDetails( entityReturn ) ); writeEntityReferenceFetches( entityReturn, depth+1, printWriter ); } else if ( CollectionReference.class.isInstance( rootReturn ) ) { final CollectionReference collectionReference = (CollectionReference) rootReturn; printWriter.println( extractDetails( collectionReference ) ); writeCollectionReferenceFetches( collectionReference, depth+1, printWriter ); } printWriter.flush(); } private String extractDetails(ScalarReturn rootReturn) { return String.format( "%s(name=%s, type=%s)", rootReturn.getClass().getSimpleName(), rootReturn.getName(), rootReturn.getType().getName() ); } private String extractDetails(EntityReference entityReference) { return String.format( "%s(entity=%s, querySpaceUid=%s, path=%s)", entityReference.getClass().getSimpleName(), entityReference.getEntityPersister().getEntityName(), entityReference.getQuerySpaceUid(), entityReference.getPropertyPath().getFullPath() ); } private String extractDetails(CollectionReference collectionReference) { // todo : include some form of parameterized type signature? i.e., List, Set, etc return String.format( "%s(collection=%s, querySpaceUid=%s, path=%s)", collectionReference.getClass().getSimpleName(), collectionReference.getCollectionPersister().getRole(), collectionReference.getQuerySpaceUid(), collectionReference.getPropertyPath().getFullPath() ); } private String extractDetails(CompositeFetch compositeFetch) { return String.format( "%s(composite=%s, querySpaceUid=%s, path=%s)", compositeFetch.getClass().getSimpleName(), compositeFetch.getFetchedType().getReturnedClass().getName(), compositeFetch.getQuerySpaceUid(), compositeFetch.getPropertyPath().getFullPath() ); } private void writeEntityReferenceFetches(EntityReference entityReference, int depth, PrintWriter printWriter) { if ( BidirectionalEntityReference.class.isInstance( entityReference ) ) { return; } if ( entityReference.getIdentifierDescription().hasFetches() ) { printWriter.println( TreePrinterHelper.INSTANCE.generateNodePrefix( depth ) + "(entity id) " ); writeFetches( ( (FetchSource) entityReference.getIdentifierDescription() ).getFetches(), depth+1, printWriter ); } writeFetches( entityReference.getFetches(), depth, printWriter ); } private void writeFetches(Fetch[] fetches, int depth, PrintWriter printWriter) { for ( Fetch fetch : fetches ) { writeFetch( fetch, depth, printWriter ); } } private void writeFetch(Fetch fetch, int depth, PrintWriter printWriter) { printWriter.print( TreePrinterHelper.INSTANCE.generateNodePrefix( depth ) ); if ( EntityFetch.class.isInstance( fetch ) ) { final EntityFetch entityFetch = (EntityFetch) fetch; printWriter.println( extractDetails( entityFetch ) ); writeEntityReferenceFetches( entityFetch, depth+1, printWriter ); } else if ( CompositeFetch.class.isInstance( fetch ) ) { final CompositeFetch compositeFetch = (CompositeFetch) fetch; printWriter.println( extractDetails( compositeFetch ) ); writeCompositeFetchFetches( compositeFetch, depth+1, printWriter ); } else if ( CollectionAttributeFetch.class.isInstance( fetch ) ) { final CollectionAttributeFetch collectionFetch = (CollectionAttributeFetch) fetch; printWriter.println( extractDetails( collectionFetch ) ); writeCollectionReferenceFetches( collectionFetch, depth+1, printWriter ); } } private void writeCompositeFetchFetches(CompositeFetch compositeFetch, int depth, PrintWriter printWriter) { writeFetches( compositeFetch.getFetches(), depth, printWriter ); } private void writeCollectionReferenceFetches( CollectionReference collectionReference, int depth, PrintWriter printWriter) { final CollectionFetchableIndex indexGraph = collectionReference.getIndexGraph(); if ( indexGraph != null ) { printWriter.print( TreePrinterHelper.INSTANCE.generateNodePrefix( depth ) + "(collection index) " ); if ( EntityReference.class.isInstance( indexGraph ) ) { final EntityReference indexGraphAsEntityReference = (EntityReference) indexGraph; printWriter.println( extractDetails( indexGraphAsEntityReference ) ); writeEntityReferenceFetches( indexGraphAsEntityReference, depth+1, printWriter ); } else if ( CompositeFetch.class.isInstance( indexGraph ) ) { final CompositeFetch indexGraphAsCompositeFetch = (CompositeFetch) indexGraph; printWriter.println( extractDetails( indexGraphAsCompositeFetch ) ); writeCompositeFetchFetches( indexGraphAsCompositeFetch, depth+1, printWriter ); } } final CollectionFetchableElement elementGraph = collectionReference.getElementGraph(); if ( elementGraph != null ) { printWriter.print( TreePrinterHelper.INSTANCE.generateNodePrefix( depth ) + "(collection element) " ); if ( EntityReference.class.isInstance( elementGraph ) ) { final EntityReference elementGraphAsEntityReference = (EntityReference) elementGraph; printWriter.println( extractDetails( elementGraphAsEntityReference ) ); writeEntityReferenceFetches( elementGraphAsEntityReference, depth+1, printWriter ); } else if ( CompositeFetch.class.isInstance( elementGraph ) ) { final CompositeFetch elementGraphAsCompositeFetch = (CompositeFetch) elementGraph; printWriter.println( extractDetails( elementGraphAsCompositeFetch ) ); writeCompositeFetchFetches( elementGraphAsCompositeFetch, depth+1, printWriter ); } } } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy