Input:
Merges the template and context into a file . If the directory of the file does not exists the full directory path to it will be created . [CODESPLIT] protected final void merge ( final VelocityContext context , final String artifactName , final String templateName , final String filename ) throws GenerateException { final GeneratedFile genFile = getTargetFile ( artifactName , filename , templateName ) ; if ( genFile . isSkip ( ) ) { LOG . debug ( "Omitted already existing file: {} [{}]" , genFile , templateName ) ; } else { LOG . debug ( "Start merging velocity template: {} [{}]" , genFile , templateName ) ; // Merge content
 try { final Writer writer = new FileWriter ( genFile . getTmpFile ( ) ) ; try { final Template template = ve . getTemplate ( templateName ) ; template . merge ( context , writer ) ; } finally { writer . close ( ) ; } genFile . persist ( ) ; } catch ( final IOException ex ) { throw new GenerateException ( "Error merging template '" + templateName + "' to '" + filename + "'!" , ex ) ; } } }


Input: Handle XML input stream from HTTP request . This method expects a single formal parameter current implementation supporting { @link Document } and { @link InputStream } . [CODESPLIT] @ Override public Object [ ] read ( HttpServletRequest httpRequest , Type [ ] formalParameters ) throws IOException , IllegalArgumentException { if ( formalParameters . length != 1 ) { throw new IllegalArgumentException ( "Bad parameters count. Should be exactly one but is |%d|." , formalParameters . length ) ; } if ( formalParameters [ 0 ] instanceof ParameterizedType ) { throw new IllegalArgumentException ( "Parameterized type |%s| is not supported." , formalParameters [ 0 ] ) ; } return new Object [ ] { read ( httpRequest . getInputStream ( ) , formalParameters [ 0 ] ) } ; }


Input: Process XML input stream accordingly requested type . Current implementation supports two type : XML { @link Document } and XML input stream . [CODESPLIT] @ Override public Object read ( InputStream inputStream , Type type ) throws IOException { if ( Types . isKindOf ( type , Document . class ) ) { return documentBuilder . loadXML ( inputStream ) ; } else if ( Types . isKindOf ( type , InputStream . class ) ) { threadLocal . set ( inputStream ) ; return inputStream ; } else { throw new IllegalArgumentException ( "Unsupported formal parameter type |%s| for XML content type." , type ) ; } }


Input: Returns the model directory . [CODESPLIT] public final File getModelDir ( ) { if ( ( modelDir == null ) && ( modelPath != null ) ) { modelDir = Utils4J . getCanonicalFile ( new File ( modelPath ) ) ; } return modelDir ; }


Input: Returns the template directory . [CODESPLIT] public final File getTemplateDir ( ) { if ( ( templateDir == null ) && ( templatePath != null ) ) { try { templateDir = new File ( templatePath ) . getCanonicalFile ( ) ; } catch ( final IOException ex ) { throw new RuntimeException ( "Couldn't determine canonical template file: " + templatePath , ex ) ; } } return templateDir ; }


Input: number of seconds from 1970 - 01 - 01T00 : 00 : 00Z UTC until the specified UTC date / time [CODESPLIT] public static Long toNumericDate ( Date value ) { if ( value == null ) { return null ; } return DateUtils . clearMs ( value ) . getTime ( ) / 1000 ; }


Input: Serialize XML document to output stream of given HTTP response . [CODESPLIT] @ Override public void write ( HttpServletResponse httpResponse , Object value ) throws IOException { final Document document = ( Document ) value ; document . serialize ( new OutputStreamWriter ( httpResponse . getOutputStream ( ) , "UTF-8" ) ) ; }


Input: Configuration Property : set the initial URL . This property is <b > mandatory< / b > . If the browser is already created this web view loads this new url . [CODESPLIT] @ Property ( name = "url" ) public synchronized void setURL ( final String url ) { this . m_url = url ; if ( m_browser != null ) { QApplication . invokeLater ( new Runnable ( ) { public void run ( ) { m_browser . open ( url ) ; } } ) ; } }


Input: Starts the browser and loads the set url in the web view . [CODESPLIT] @ Validate public void start ( ) { QApplication . invokeLater ( new Runnable ( ) { public void run ( ) { configureApplication ( ) ; m_logger . info ( "Creating a web ui..." ) ; synchronized ( WebViewFactory . this ) { m_browser = new WebWindow ( m_url , WebViewFactory . this ) ; configureWindow ( m_browser ) ; m_browser . show ( ) ; } m_logger . info ( "Web UI created." ) ; } } ) ; }


Input: Configures the application : <ul > <li > sets the application name ( default : akquinet ChameRIA ) < / li > <li > sets the application version ( default : current web view factory version ) < / li > <li > sets the application icon ( default : no icon ) < / li > < / ul > [CODESPLIT] private void configureApplication ( ) { if ( m_appName != null ) { QApplication . setApplicationName ( m_appName ) ; } else { QApplication . setApplicationName ( "akquinet ChameRIA" ) ; } if ( m_appVersion != null ) { QApplication . setApplicationVersion ( m_appVersion ) ; } else { QApplication . setApplicationVersion ( m_context . getBundle ( ) . getVersion ( ) . toString ( ) ) ; } if ( m_icon != null ) { QFile file = new QFile ( m_icon ) ; QIcon icon = new QIcon ( file . fileName ( ) ) ; QApplication . setWindowIcon ( icon ) ; } QApplication . setOrganizationName ( "akquinet A.G." ) ; // Configure the proxy if ( m_proxyType != null ) { m_logger . warn ( "Set application proxy : " + m_proxyType ) ; if ( m_proxyHostName == null || m_proxyPort == 0 ) { m_logger . error ( "Cannot configure proxy : hostname or port not set : " + m_proxyHostName + ":" + m_proxyPort ) ; } else { QNetworkProxy proxy = new QNetworkProxy ( m_proxyType , m_proxyHostName , m_proxyPort ) ; QNetworkProxy . setApplicationProxy ( proxy ) ; m_logger . warn ( "Application proxy set " + m_proxyType + " on " + m_proxyHostName + ":" + m_proxyPort ) ; } } }


Input: Configures the browser window . [CODESPLIT] private void configureWindow ( WebWindow web ) { if ( m_fullscreen ) { // We need to store the previous width and height values m_width = web . width ( ) ; m_height = web . height ( ) ; web . showFullScreen ( ) ; } else { web . showNormal ( ) ; if ( ! m_resizable ) { web . setFixedSize ( new QSize ( m_width , m_height ) ) ; } else { web . setBaseSize ( new QSize ( m_width , m_height ) ) ; } web . resize ( m_width , m_height ) ; } if ( ! m_bar ) { web . menuBar ( ) . setVisible ( false ) ; } else { web . menuBar ( ) . setVisible ( true ) ; if ( m_icon != null ) { QIcon icon = new QIcon ( m_icon ) ; web . setWindowIcon ( icon ) ; } web . setWindowTitle ( m_appName ) ; } if ( ! m_contextMenu ) { web . setContextMenuPolicy ( ContextMenuPolicy . PreventContextMenu ) ; } else { web . setContextMenuPolicy ( ContextMenuPolicy . DefaultContextMenu ) ; } }


Input: Print callback . Checks if the print feature is enabled . If so launch the system print job . [CODESPLIT] public void print ( QWebView view ) { if ( m_print ) { QPrinter printer = new QPrinter ( ) ; QPrintDialog printDialog = new QPrintDialog ( printer , view ) ; if ( printDialog . exec ( ) == QDialog . DialogCode . Accepted . value ( ) ) { // print ... view . print ( printer ) ; } } else { m_logger . warn ( "Print disabled" ) ; } }


Input: Save callback ( for unsupported content ) . Checks if the save feature is enabled . If so launch the system save dialog . [CODESPLIT] public void save ( QNetworkReply reply ) { if ( m_download ) { String fn = QFileDialog . getSaveFileName ( ) ; if ( fn != null && fn . length ( ) > 0 ) { m_logger . info ( "File name : " + fn ) ; try { URL u = new URL ( reply . url ( ) . toString ( ) ) ; FileOutputStream out = new FileOutputStream ( new File ( fn ) ) ; InputStream in = u . openStream ( ) ; write ( in , out ) ; } catch ( IOException e ) { m_logger . error ( "Cannot download file " + e . getMessage ( ) , e ) ; } } else { m_logger . warn ( "No File Name - Download request cancelled" ) ; } } else { m_logger . warn ( "Download disabled" ) ; } }


Input: Utility method to copy a stream to another stream . [CODESPLIT] public static void write ( InputStream in , OutputStream out ) throws IOException { byte [ ] b = new byte [ 4096 ] ; for ( int n ; ( n = in . read ( b ) ) != - 1 ; ) { out . write ( b , 0 , n ) ; } in . close ( ) ; out . close ( ) ; }


Input: Open callback ( <code > window . open< / code > ) . Checks if the open new window feature is enabled . If so creates the web view [CODESPLIT] public QWebView openWindow ( ) { if ( m_window_open ) { // We share the same factory QWebView newwindow = new ChameriaWebView ( this ) ; return newwindow ; } else { m_logger . warn ( "Open new window disabled" ) ; return null ; } }


Input: Retrieve managed instance from application factory and invoke given method on that instance . [CODESPLIT] @ Override public Object invoke ( Object proxy , Method method , Object [ ] args ) throws Throwable { T instance = appFactory . getInstance ( interfaceClass ) ; return method . invoke ( instance , args ) ; }


Input:
Attach this instance to HTTP servlet request . Load this instance state from HTTP servlet request and mark it as attached . [CODESPLIT] public void attach ( HttpServletRequest httpRequest , HttpServletResponse httpResponse ) { // takes care to not override request URL, locale and request path values if set by request pre-processor
 if ( requestURL == null ) { requestURL = httpRequest . getRequestURI ( ) ; } if ( locale == null ) { locale = httpRequest . getLocale ( ) ; } if ( requestPath == null ) { // request URI and context path cannot ever be null
 requestPath = httpRequest . getRequestURI ( ) . substring ( httpRequest . getContextPath ( ) . length ( ) ) ; } this . httpRequest = httpRequest ; this . httpResponse = httpResponse ; this . attached = true ; }


Input: Detach request context instance from HTTP servlet request . Invoking getters on this instance after detaching is considered a bug . [CODESPLIT] public void detach ( ) { attached = false ; locale = null ; securityDomain = null ; cookies = null ; requestPath = null ; requestURL = null ; }


Input: Get request cookies . [CODESPLIT] public Cookies getCookies ( ) { assertAttached ( ) ; if ( cookies == null ) { cookies = new Cookies ( httpRequest , httpResponse ) ; } return cookies ; }


Input:
Get HTTP session this request context is part of or null if session is not or could not be created . If <code > create< / code > flag is not provided this method return current HTTP session as it is that is return it if already created or null if not . <p > If <code > create< / code > flag is present and is true this method returns current HTTP session if there is one associated with current request or create a new one . This method never returns null if requested to create session but can throw illegal state exception if attempt to create session after response commit . [CODESPLIT] public HttpSession getSession ( boolean ... create ) { assertAttached ( ) ; if ( create . length == 0 ) { return httpRequest . getSession ( ) ; } // if create flag is true next call can throw IllegalStateException if HTTP response is committed
 return httpRequest . getSession ( create [ 0 ] ) ; }


Input: Dump this request context state to error logger . If this instance is not attached this method is NOP . [CODESPLIT] public void dump ( ) { if ( ! attached ) { return ; } StringBuilder message = new StringBuilder ( ) ; message . append ( "Request context |" ) ; message . append ( httpRequest . getRequestURI ( ) ) ; message . append ( "|:" ) ; message . append ( System . lineSeparator ( ) ) ; message . append ( "\t- remote-address: " ) ; message . append ( httpRequest . getRemoteHost ( ) ) ; message . append ( System . lineSeparator ( ) ) ; message . append ( "\t- method: " ) ; message . append ( httpRequest . getMethod ( ) ) ; message . append ( System . lineSeparator ( ) ) ; message . append ( "\t- query-string: " ) ; if ( httpRequest . getQueryString ( ) != null ) { message . append ( httpRequest . getQueryString ( ) ) ; } Enumeration < String > headerNames = httpRequest . getHeaderNames ( ) ; while ( headerNames . hasMoreElements ( ) ) { message . append ( System . lineSeparator ( ) ) ; String headerName = headerNames . nextElement ( ) ; message . append ( "\t- " ) ; message . append ( headerName ) ; message . append ( ": " ) ; message . append ( httpRequest . getHeader ( headerName ) ) ; } log . error ( message . toString ( ) ) ; }


Input: Registers the { @link TypeHandler } which is provided by { @code className } . After processing this row the TypeAdapter will be automatically used when the destination type matches { @link TypeHandler#getType () } . [CODESPLIT] @ SuppressWarnings ( "unchecked" ) public void load ( final String className ) throws Exception { Class < ? extends TypeHandler < ? > > clazz = ( Class < ? extends TypeHandler < ? > > ) Class . forName ( className ) ; TypeHandlerFactory helper = DependencyManager . getOrCreate ( TypeHandlerFactory . class ) ; helper . register ( clazz ) ; }


Input: Collect invocation meters from application managed classes . [CODESPLIT] private static List < InvocationMeter > getMeters ( ) { List < InvocationMeter > invocationMeters = new ArrayList < InvocationMeter > ( ) ; ContainerSPI container = ( ContainerSPI ) Factory . getAppFactory ( ) ; for ( ManagedMethodSPI managedMethod : container . getManagedMethods ( ) ) { invocationMeters . add ( ( ( ManagedMethod ) managedMethod ) . getMeter ( ) ) ; } return invocationMeters ; }


Input: Configure events stream instance from configuration object . [CODESPLIT] protected void config ( EventStreamConfig config ) { if ( config . hasSecretKey ( ) ) { secretKey = config . getSecretKey ( ) ; } if ( config . hasKeepAlivePeriod ( ) ) { keepAlivePeriod = config . getKeepAlivePeriod ( ) ; } parameters = config . getParameters ( ) ; }


Input:
Push event to this events stream client . This method just stores the event on { @link #eventsQueue events queue } being executed into invoker thread . This events stream thread is blocked on the events queue ; after this method execution it will unblock and process the event see { @link #loop () } method . <p > Queue offer operation is guarded by { @link #EVENTS_QUEUE_PUSH_TIMEOUT } . This timeout can occur only in a very improbable condition of events flood combined with system resources starvation . For this reason there is no attempt to recover ; event is simple lost with warning on application logger . [CODESPLIT] public void push ( Event event ) { if ( ! active . get ( ) ) { throw new BugError ( "Event stream |%s| is closed." , this ) ; } // BlockingQueue is thread safe so we do not need to synchronize this method
 try { if ( ! eventsQueue . offer ( event , EVENTS_QUEUE_PUSH_TIMEOUT , TimeUnit . MILLISECONDS ) ) { log . warn ( "Timeout trying to push event on events queue. Event |%s| not processed." , event ) ; } } catch ( InterruptedException unused ) { log . warn ( "Thread interruption on event stream |%s| while trying to push event to queue. Event |%s| not processed." , this , event ) ; Thread . currentThread ( ) . interrupt ( ) ; } }


Input: Close this event stream loop and waits for associated { [CODESPLIT] @ Override public void close ( ) { if ( ! active . get ( ) ) { return ; } log . debug ( "Closing event stream |%s| ..." , this ) ; push ( new ShutdownEvent ( ) ) ; active . set ( false ) ; log . debug ( "Event stream |%s| was closed." , this ) ; }


Input: Set the host address for client connected to this event stream . [CODESPLIT] protected void setRemoteHost ( String remoteHost ) { if ( string == null ) { string = Strings . concat ( ' ' , STREAM_ID ++ , ' ' , remoteHost ) ; } }


Input:
Event stream main loop repeated for every event . Waits for an event and push it to the client via { @link #writer } writer initialized by { @link EventStreamServlet } on this event stream creation . Note that this logic is executed into HTTP request thread ; it blocks the thread till an event become available . This method always returns true allowing event stream to continue . It returns false only when got { @link ShutdownEvent } pushed on queue by { @link #close () } method or there is an error on print writer . Checking for print writer errors is especially useful to detect that remote client closes its socket and to gracefully close this stream and release parent servlet instance . <p > Also this method takes care to periodically send keep alive events see { @link #keepAlivePeriod } . Keep alive is used to ensure server side and client logic that peer is still running and to avoid connection drop due to routers idle connection timeout . [CODESPLIT] protected boolean loop ( ) { Event event = null ; try { event = eventsQueue . poll ( keepAlivePeriod , TimeUnit . MILLISECONDS ) ; } catch ( InterruptedException unused ) { if ( ! active . get ( ) ) { log . debug ( "Events stream |%s| thread is interrupted. Break events stream loop." , this ) ; return false ; } // in a perfect world, now would be the right moment to stop the events stream, returning false...
 // but i'm not sure interruption occurs only when current thread is interrupted
 // for now i play safe, allowing events stream to continue and use shutdown event to break it
 log . warn ( "Events stream |%s| thread is interrupted. Continue events stream loop." , this ) ; return true ; } if ( event == null ) { // we are here due to keep-alive period expiration
 // returns true to signal event stream should continue
 sendKeepAlive ( ) ; log . debug ( "Keep-alive was sent to event stream |%s|." , this ) ; return ! writer . checkError ( ) ; } // close method puts this event into queue; returns false to break this events stream loop
 if ( event instanceof ShutdownEvent ) { log . debug ( "Got shutdown event. Break event stream loop." ) ; return false ; } sendEvent ( event ) ; onSent ( event ) ; log . debug ( "Event |%s| was sent to event stream |%s|." , event , this ) ; return ! writer . checkError ( ) ; }


Input: Get named parameter throwing exception if not found . [CODESPLIT] protected < T > T getParameter ( String name , Class < T > type ) { if ( parameters == null ) { throw new BugError ( "Event stream |%s| parameters not configured." , this ) ; } String value = parameters . get ( name ) ; if ( value == null ) { throw new BugError ( "Missing event stream parameter |%s| of expected type |%s|." , name , type ) ; } return ConverterRegistry . getConverter ( ) . asObject ( value , type ) ; }


Input:
Send event instance to this event stream consumer . Compile a W3C Server - Sent event from <code > event< / code > instance argument and write it to this { @link #writer } . This event stream implementation does not use all W3C server - sent event fields : only <code > event< / code > and <code > data< / code > as folows : <ul > <li > event field stores event argument canonical class name <li > data field value is event argument instance serialized JSON . < / ul > Just for those curious here is an sample of a serialized hypothetical event as it is on wire : [CODESPLIT] protected void sendEvent ( Event event ) { write ( "data:" ) ; if ( secretKey == null ) { json . serialize ( writer , event ) ; } else { try { Cipher cipher = Cipher . getInstance ( secretKey . getAlgorithm ( ) ) ; cipher . init ( Cipher . ENCRYPT_MODE , secretKey ) ; // this overload of doFinal from Cipher class is able to perform single step encrypting
 // excerpt from API:
 // Encrypts or decrypts data in a single-part operation, or finishes a multiple-part operation.
 byte [ ] encryptedMessage = cipher . doFinal ( json . serialize ( event ) ) ; // encode encrypted event message with Base64 since content type should be text
 write ( Base64 . encode ( encryptedMessage ) ) ; } catch ( InvalidKeyException | NoSuchPaddingException | BadPaddingException | IllegalBlockSizeException e ) { // we step here only for bugs on encryption provider:
 // secret key size is incorrect or key is not properly initialized
 // single step encryption using directly Cipher#doFinal is supposed to process all input at once
 // missing JVM default padding mechanism
 // bad padding occurring on encryption
 throw new BugError ( e ) ; } catch ( NoSuchAlgorithmException e ) { throw new BugError ( "Missing support for |%s| cryptographic algorithm." , secretKey . getAlgorithm ( ) ) ; } } // end data field
 crlf ( ) ; // single end of line is the mark for event end
 crlf ( ) ; flush ( ) ; }


Input: Removes a prefix from a path . If the path does not start with the prefix the unchanged path is returned . [CODESPLIT] public String removePrefix ( final String path , final String prefix ) { String pathWithoutPrefix = path ; if ( pathWithoutPrefix . startsWith ( prefix ) ) { pathWithoutPrefix = pathWithoutPrefix . substring ( prefix . length ( ) ) ; while ( pathWithoutPrefix . startsWith ( "/" ) || pathWithoutPrefix . startsWith ( "\\" ) ) { pathWithoutPrefix = pathWithoutPrefix . substring ( 1 ) ; } } return pathWithoutPrefix ; }


Input: Checks whether { @code subDir } is a sub directory of { @code parentDir } . Note : the comparison is case sensitive . [CODESPLIT] public boolean isSubDir ( final File subDir , final File parentDir ) throws IOException { int parentDirLength = parentDir . getCanonicalFile ( ) . getAbsolutePath ( ) . length ( ) ; File currentDir = subDir . getCanonicalFile ( ) . getAbsoluteFile ( ) ; while ( currentDir . getAbsolutePath ( ) . length ( ) > parentDirLength ) { currentDir = currentDir . getParentFile ( ) ; } return currentDir . equals ( parentDir . getAbsoluteFile ( ) ) ; }


Input: Returns all directory paths between { @code fromDir } and { @code toDir } . [CODESPLIT] public File [ ] getParentDirs ( final File fromDir , final File toDir ) throws IOException { List < File > result = new LinkedList <> ( ) ; final File fromDirCanonical = fromDir . getCanonicalFile ( ) ; for ( File current = toDir . getCanonicalFile ( ) . getAbsoluteFile ( ) ; ! current . equals ( fromDirCanonical ) ; current = current . getParentFile ( ) ) { result . add ( 0 , current ) ; } return result . toArray ( new File [ result . size ( ) ] ) ; }


Input: Gets the longest common parent directory path of two paths . [CODESPLIT] public File getCommonDir ( final File dir1 , final File dir2 ) throws IOException { List < File > parts1 = getParentDirs ( dir1 ) ; List < File > parts2 = getParentDirs ( dir2 ) ; File matched = null ; final int maxCommonSize = Math . min ( parts1 . size ( ) , parts2 . size ( ) ) ; for ( int i = 0 ; i < maxCommonSize ; ++ i ) { if ( parts1 . get ( i ) . equals ( parts2 . get ( i ) ) ) { matched = parts1 . get ( i ) ; } else { break ; } } return matched ; }


Input: Converts an absolute path into a relative one . [CODESPLIT] public String abs2rel ( final String basePath , final String absPath ) { if ( ! isAbsolutePath ( absPath ) ) { return absPath ; } if ( isWindowsDrive ( absPath ) && isWindowsDrive ( basePath ) && absPath . charAt ( 0 ) != basePath . charAt ( 0 ) ) { return absPath ; } StringBuilder result = new StringBuilder ( ) ; String [ ] baseParts = getParts ( basePath ) ; String [ ] absParts = getParts ( absPath ) ; // extract common prefix int start = 0 ; for ( int i = 0 ; i < Math . min ( baseParts . length , absParts . length ) ; ++ i ) { if ( baseParts [ i ] . equals ( absParts [ i ] ) ) { start = i + 1 ; } } for ( int i = start ; i < baseParts . length ; ++ i ) { if ( result . length ( ) > 0 ) { result . append ( File . separator ) ; } result . append ( ".." ) ; } for ( int i = start ; i < absParts . length ; ++ i ) { if ( result . length ( ) > 0 ) { result . append ( File . separator ) ; } result . append ( absParts [ i ] ) ; } return result . toString ( ) ; }


Input: Converts an relative path into an absolute one . [CODESPLIT] public File rel2abs ( final String basePath , final String relPath ) { String [ ] baseParts = getParts ( basePath ) ; String [ ] relParts = getParts ( relPath ) ; if ( isAbsolutePath ( relPath ) ) { return new File ( relPath ) ; } List < String > parts = new ArrayList <> ( ) ; for ( int i = 0 ; i < baseParts . length ; ++ i ) { if ( i > 0 || ! isWindowsDrive ( basePath ) ) { parts . add ( baseParts [ i ] ) ; } } for ( String part : relParts ) { if ( part . equals ( ".." ) && parts . size ( ) > 0 ) { parts . remove ( parts . size ( ) - 1 ) ; } else if ( ! part . equals ( "." ) && ! part . equals ( ".." ) ) { parts . add ( part ) ; } } StringBuilder result = new StringBuilder ( ) ; if ( isWindowsDrive ( basePath ) ) { result . append ( baseParts [ 0 ] ) ; } for ( String part : parts ) { result . append ( File . separator ) ; result . append ( part ) ; } return new File ( result . toString ( ) ) ; }


Input: Counts the number of directories in a given path . [CODESPLIT] public int dirDepth ( final File path ) { final String stringPath = path . getPath ( ) ; return stringPath . length ( ) - stringPath . replaceAll ( "[/\\\\]" , "" ) . length ( ) ; }


Input: Servlet life cycle callback executed at this servlet instance initialization . Mainly takes care to initialize parent container reference . If there is no servlet context attribute with the name { @link TinyContainer#ATTR_INSTANCE } this initialization fails with servlet permanently unavailable . <p > Parent container instance has application life span and its reference is valid for entire life span of this servlet instance . [CODESPLIT] @ Override public void init ( ServletConfig config ) throws UnavailableException { container = ( ContainerSPI ) config . getServletContext ( ) . getAttribute ( TinyContainer . ATTR_INSTANCE ) ; if ( container == null ) { log . fatal ( "Tiny container instance not properly created, probably misconfigured. Servlet |%s| permanently unvailable." , config . getServletName ( ) ) ; throw new UnavailableException ( "Tiny container instance not properly created, probably misconfigured." ) ; } servletName = Strings . concat ( config . getServletContext ( ) . getServletContextName ( ) , ' ' , config . getServletName ( ) ) ; log . trace ( "Initialize servlet |%s|." , servletName ) ; }


Input:
Prepare execution context and delegates the actual HTTP request processing to abstract handler . Initialize request context bound to current thread and delegates { @link #handleRequest ( RequestContext ) } . After request handler execution takes care to cleanup request context . <p > This method also initialize logger context see { @link #logContext } with remote address of current request so that logging utility can include contextual diagnostic data into log messages . Just before exiting this service request cleanups the logger context . [CODESPLIT] @ Override protected void service ( HttpServletRequest httpRequest , HttpServletResponse httpResponse ) throws IOException , ServletException { // push context path and remote address of the requested processed by this thread to logger diagnostic context
 logContext . put ( LOG_CONTEXT_APP , httpRequest . getContextPath ( ) . isEmpty ( ) ? TinyContainer . ROOT_CONTEXT : httpRequest . getContextPath ( ) . substring ( 1 ) ) ; logContext . put ( LOG_CONTEXT_IP , httpRequest . getRemoteHost ( ) ) ; logContext . put ( LOG_CONTEXT_ID , Integer . toString ( requestID . getAndIncrement ( ) , Character . MAX_RADIX ) ) ; if ( isEmptyUriRequest ( httpRequest ) ) { log . debug ( "Empty URI request for |%s|. Please check for <img> with empty 'src' or <link>, <script> with empty 'href' in HTML source or script resulting in such condition." , httpRequest . getRequestURI ( ) ) ; return ; } String requestURI = httpRequest . getRequestURI ( ) ; long start = System . currentTimeMillis ( ) ; Factory . bind ( container ) ; // request context has THREAD scope and this request thread may be reused by servlet container
 // takes care to properly initialize request context for every HTTP request
 RequestContext context = container . getInstance ( RequestContext . class ) ; context . attach ( httpRequest , httpResponse ) ; log . trace ( "Processing request |%s|." , requestURI ) ; try { handleRequest ( context ) ; } catch ( IOException | ServletException | Error | RuntimeException t ) { // last line of defense; dump request context and throwable then dispatch exception to servlet container
 // servlet container will generate response page using internal templates or <error-page>, if configured
 dumpError ( context , t ) ; throw t ; } finally { log . trace ( "%s %s processed in %d msec." , httpRequest . getMethod ( ) , context . getRequestURL ( ) , System . currentTimeMillis ( ) - start ) ; // cleanup remote address from logger context and detach request context instance from this request
 logContext . clear ( ) ; context . detach ( ) ; } }


Input: Detect self - referenced request URI . It seems there are browsers considering empty string as valid URL pointing to current loaded page . If we have an <code > img< / code > element with empty <code > src< / code > attribute browser will try to load that image from current URL that is the content of current page . This means is possible to invoke a controller many times for a single page request . <p > To avoid such condition check if this request comes from the same page i . e . referrer is current request . Note that this is also true for <code > link< / code > and <code > script< / code > with empty <code > href< / code > . Finally worthy to mention is that this check is not performed on request accepting <code > text / html< / code > . [CODESPLIT] private static boolean isEmptyUriRequest ( HttpServletRequest httpRequest ) { if ( ! "GET" . equals ( httpRequest . getMethod ( ) ) ) { return false ; } String acceptValue = httpRequest . getHeader ( HttpHeader . ACCEPT ) ; if ( acceptValue != null && acceptValue . contains ( ContentType . TEXT_HTML . getMIME ( ) ) ) { return false ; } String referer = httpRequest . getHeader ( HttpHeader . REFERER ) ; if ( referer == null ) { return false ; } StringBuilder uri = new StringBuilder ( httpRequest . getRequestURI ( ) ) ; String query = httpRequest . getQueryString ( ) ; if ( query != null ) { if ( query . charAt ( 0 ) != ' ' ) { uri . append ( ' ' ) ; } uri . append ( query ) ; } return referer . toLowerCase ( ) . endsWith ( uri . toString ( ) . toLowerCase ( ) ) ; }


Input:
Send unauthorized access response . This method send back a response with status code { @link HttpServletResponse#SC_UNAUTHORIZED } and response header { @link HttpHeader#WWW_AUTHENTICATE } set to basic authentication method and { @link ContainerSPI#getLoginRealm () } authentication realm . <p > If request is from an agent using XHR this method behaves a little different . XHR specification mandates that unauthorized access to be handled transparently by client agent that usually displays client agent login form not very well integrated with application . Below is a snippet from this framework script library . <p > For not authorized XHR requests this method sends { @link HttpServletResponse#SC_OK } and custom response header { @link HttpHeader#X_HEADER_LOCATION } set to application login page see { @link ContainerSPI#getLoginPage () } . Client script can handle this response and redirect to given login page . [CODESPLIT] protected static void sendUnauthorized ( RequestContext context ) { final ContainerSPI container = context . getContainer ( ) ; final HttpServletResponse httpResponse = context . getResponse ( ) ; if ( httpResponse . isCommitted ( ) ) { log . fatal ( "Abort HTTP transaction. Attempt to send reponse after response already commited." ) ; return ; } log . error ( "Reject unauthorized request for private resource or service: |%s|." , context . getRequestURI ( ) ) ; String loginPage = container . getLoginPage ( ) ; if ( HttpHeader . isXHR ( context . getRequest ( ) ) && loginPage != null ) { // XMLHttpRequest specs mandates that redirection codes to be performed transparently by user agent
 // this means redirect from server does not reach script counterpart
 // as workaround uses 200 OK and X-JSLIB-Location extension header
 log . trace ( "Send X-JSLIB-Location |%s| for rejected XHR request: |%s|" , container . getLoginPage ( ) , context . getRequestURI ( ) ) ; httpResponse . setStatus ( HttpServletResponse . SC_OK ) ; httpResponse . setHeader ( HttpHeader . X_HEADER_LOCATION , container . getLoginPage ( ) ) ; return ; } log . trace ( "Send WWW-Authenticate |Basic realm=%s| for rejected request: |%s|" , container . getLoginRealm ( ) , context . getRequestURI ( ) ) ; httpResponse . setStatus ( HttpServletResponse . SC_UNAUTHORIZED ) ; httpResponse . setHeader ( HttpHeader . WWW_AUTHENTICATE , String . format ( "Basic realm=%s" , container . getLoginRealm ( ) ) ) ; }


Input: Send response for bad request with request URI as message . This utility method is used when a request URI is not well formed as expected by concrete servlet implementation . It dumps request context and delegates servlet container { @link HttpServletResponse#sendError ( int String ) } to send { @link HttpServletResponse#SC_BAD_REQUEST } . [CODESPLIT] protected static void sendBadRequest ( RequestContext context ) throws IOException { log . error ( "Bad request format for resource or service: |%s|." , context . getRequestURI ( ) ) ; context . dump ( ) ; context . getResponse ( ) . sendError ( HttpServletResponse . SC_BAD_REQUEST , context . getRequestURI ( ) ) ; }


Input: Send response for resource or service not found containing the exception that describes missing entity . This method sends back exception object wrapped in { @link RemoteException } . Response is encoded JSON and status code is { @link HttpServletResponse#SC_NOT_FOUND } . [CODESPLIT] protected static void sendNotFound ( RequestContext context , Exception exception ) throws IOException { log . error ( "Request for missing resource or service: |%s|." , context . getRequestURI ( ) ) ; sendJsonObject ( context , new RemoteException ( exception ) , HttpServletResponse . SC_NOT_FOUND ) ; }


Input:
Send server error response with given exception serialized JSON . This utility method dumps stack trace and request context to application logger and send back throwable object . Response is encoded JSON and status code is { @link HttpServletResponse#SC_INTERNAL_SERVER_ERROR } . If given exception argument is { @link InvocationException } or { @link InvocationTargetException } extract the cause . <p > There is a special case for { @link BusinessException } . This exception signals broken business constrain and is send back also as JSON object but with status code { @link HttpServletResponse#SC_BAD_REQUEST } . Also does not dump exception stack trace or request context . [CODESPLIT] protected static void sendError ( RequestContext context , Throwable throwable ) throws IOException { if ( throwable instanceof InvocationException && throwable . getCause ( ) != null ) { throwable = throwable . getCause ( ) ; } if ( throwable instanceof InvocationTargetException ) { throwable = ( ( InvocationTargetException ) throwable ) . getTargetException ( ) ; } if ( throwable instanceof BusinessException ) { // business constrains exception is generated by user space code and sent to client using HTTP response
 // status 400 - HttpServletResponse.SC_BAD_REQUEST, as JSON serialized object
 log . debug ( "Send business constrain exception |%d|." , ( ( BusinessException ) throwable ) . getErrorCode ( ) ) ; sendJsonObject ( context , throwable , HttpServletResponse . SC_BAD_REQUEST ) ; } else { dumpError ( context , throwable ) ; sendJsonObject ( context , new RemoteException ( throwable ) , HttpServletResponse . SC_INTERNAL_SERVER_ERROR ) ; } }


Input: Dump throwable stack trace and request context to application logger . [CODESPLIT] protected static void dumpError ( RequestContext context , Throwable throwable ) { log . dump ( "Error on HTTP request:" , throwable ) ; context . dump ( ) ; }


Input: Send object back to client encoded JSON with given HTTP status code . Take care to set content type length and language . Content language is extracted from request context locale . [CODESPLIT] protected static void sendJsonObject ( RequestContext context , Object object , int statusCode ) throws IOException { final HttpServletResponse httpResponse = context . getResponse ( ) ; if ( httpResponse . isCommitted ( ) ) { log . fatal ( "Abort HTTP transaction. Attempt to send JSON object after reponse commited." ) ; return ; } log . trace ( "Send response object |%s|." , object . toString ( ) ) ; Json json = Classes . loadService ( Json . class ) ; String buffer = json . stringify ( object ) ; byte [ ] bytes = buffer . getBytes ( "UTF-8" ) ; httpResponse . setStatus ( statusCode ) ; httpResponse . setContentType ( ContentType . APPLICATION_JSON . getValue ( ) ) ; httpResponse . setContentLength ( bytes . length ) ; httpResponse . setHeader ( "Content-Language" , context . getLocale ( ) . toLanguageTag ( ) ) ; httpResponse . getOutputStream ( ) . write ( bytes ) ; httpResponse . getOutputStream ( ) . flush ( ) ; }


Input: Adds another template to the list . If the list does not exist it will be created . [CODESPLIT] public final void addParamTemplate ( final ParameterizedTemplateModel paramTemplate ) { if ( paramTemplates == null ) { paramTemplates = new ArrayList < ParameterizedTemplateModel > ( ) ; } paramTemplates . add ( paramTemplate ) ; }


Input: Adds all templates to the list . If the list does not exist it will be created . [CODESPLIT] public final void addParamTemplates ( final List < ParameterizedTemplateModel > list ) { if ( list != null ) { for ( final ParameterizedTemplateModel template : list ) { addParamTemplate ( template ) ; } } }


Input: Initalizes the object . [CODESPLIT] public final void init ( final SrcGen4JContext context , final Map < String , String > vars ) { if ( paramTemplates != null ) { for ( final ParameterizedTemplateModel paramTemplate : paramTemplates ) { paramTemplate . init ( context , vars ) ; } } }


Input: Returns a list that contains all models that reference the given template . [CODESPLIT] public final List < ParameterizedTemplateModel > findReferencesTo ( final File templateDir , final File templateFile ) { final List < ParameterizedTemplateModel > result = new ArrayList < ParameterizedTemplateModel > ( ) ; if ( ( paramTemplates != null ) && Utils4J . fileInsideDirectory ( templateDir , templateFile ) ) { for ( final ParameterizedTemplateModel paramTemplate : paramTemplates ) { if ( paramTemplate . hasReferenceTo ( templateDir , templateFile ) ) { result . add ( paramTemplate ) ; } } } return result ; }


Input: Checks whether two StringBuilder { @code a } and { @code b } are equal . <p > This method removes whitespaces around both strings first . [CODESPLIT] @ Override public final boolean unsafeEquals ( final StringBuilder a , Object b ) { return a . toString ( ) . trim ( ) . equals ( b . toString ( ) . trim ( ) ) ; }


Input: Write bytes to output stream of HTTP response . This method invokes { @link StreamHandler#invokeHandler ( OutputStream ) } with HTTP response output stream . Stream handler instance is created by application and allows application logic access to HTTP response stream . [CODESPLIT] @ Override public void write ( HttpServletResponse httpResponse , Object value ) throws IOException { ( ( StreamHandler < ? > ) value ) . invokeHandler ( httpResponse . getOutputStream ( ) ) ; }


Input: Controls whether a save button is shown and fields are editable . [CODESPLIT] public void setSaveEnabled ( boolean val ) { saveButton . setVisible ( val ) ; setReadOnly ( ! val ) ; entityForm . setReadOnly ( ! val ) ; }


Input: Deletes the element . [CODESPLIT] protected void delete ( ) { String question = "Are you sure you want to delete " + getCaption ( ) + "?" ; ConfirmDialog . show ( getUI ( ) , question , ( ConfirmDialog cd ) -> { if ( cd . isConfirmed ( ) ) { try { onDelete ( ) ; close ( ) ; } catch ( IOException | IllegalArgumentException | IllegalAccessException | IllegalStateException ex ) { onError ( ex ) ; } catch ( RuntimeException ex ) { // Must explicitly send unhandled exceptions to error handler. // Would otherwise get swallowed silently within callback handler. getUI ( ) . getErrorHandler ( ) . error ( new com . vaadin . server . ErrorEvent ( ex ) ) ; } } } ) ; }


Input: Handler for deleting the element . [CODESPLIT] protected void onDelete ( ) throws IOException , IllegalArgumentException , IllegalAccessException , FileNotFoundException , IllegalStateException { endpoint . delete ( ) ; eventBus . post ( new ElementDeletedEvent <> ( endpoint ) ) ; }


Input: Replaces variables ( if defined ) in the path name and arguments . [CODESPLIT] public final void init ( final Map < String , String > vars ) { path = Utils4J . replaceVars ( path , vars ) ; name = Utils4J . replaceVars ( name , vars ) ; if ( arguments != null ) { for ( final Argument argument : arguments ) { argument . init ( vars ) ; } } }


Input: Opens the file and returns a { @code BufferedReader } object using the given encoding . [CODESPLIT] public BufferedReader openBufferedReader ( final String encoding ) throws IOException { final InputStream fis = openInputStream ( ) ; final InputStreamReader isr = new InputStreamReader ( fis , encoding ) ; return new BufferedReader ( isr ) ; }


Input:
Uses managed class constructor to create new instance with provided arguments . Arguments should be in order types and number required by constructor signature . [CODESPLIT] @ SuppressWarnings ( "unchecked" ) @ Override public < T > T newInstance ( ManagedClassSPI managedClass , Object ... args ) { Constructor < ? > constructor = managedClass . getConstructor ( ) ; if ( constructor == null ) { throw new BugError ( "Local instance factory cannot instantiate |%s|. Missing constructor." , managedClass ) ; } Object instance = null ; try { instance = constructor . newInstance ( args ) ; } catch ( IllegalArgumentException e ) { log . error ( "Wrong number of arguments or bad types for |%s|: [%s]." , constructor , Strings . join ( Classes . getParameterTypes ( args ) ) ) ; throw e ; } catch ( InstantiationException e ) { // managed class implementation is already validated, i.e. is not abstract and
 // test for existing constructor is performed... so no obvious reasons for instantiation exception
 throw new BugError ( e ) ; } catch ( IllegalAccessException e ) { // constructor has accessibility true and class is tested for public access modifier
 // so there is no reason for illegal access exception
 throw new BugError ( e ) ; } catch ( InvocationTargetException e ) { log . error ( "Managed instance constructor |%s| fail due to: %s." , constructor , e . getCause ( ) ) ; throw new InvocationException ( e ) ; } if ( managedClass . getInstanceType ( ) . equals ( InstanceType . PROXY ) ) { // there are two proxy handlers: one transactional and one not
 // the difference is that transactional proxy handler gets a reference to an external transactional resource
 ManagedProxyHandler handler = null ; if ( managedClass . isTransactional ( ) ) { TransactionalResource transactionalResource = managedClass . getContainer ( ) . getInstance ( TransactionalResource . class ) ; handler = new ManagedProxyHandler ( transactionalResource , managedClass , instance ) ; } else { handler = new ManagedProxyHandler ( managedClass , instance ) ; } final ClassLoader classLoader = managedClass . getImplementationClass ( ) . getClassLoader ( ) ; final Class < ? > [ ] interfaceClasses = managedClass . getInterfaceClasses ( ) ; return ( T ) Proxy . newProxyInstance ( classLoader , interfaceClasses , handler ) ; } return ( T ) instance ; }


Input: Creates and initializes a SrcGen4J configuration from a configuration file that contains ONLY generators / parsers of type { @link ParameterizedTemplateParser } and { @link ParameterizedTemplateGenerator } . [CODESPLIT] public static SrcGen4JConfig createAndInit ( final SrcGen4JContext context , final File configFile ) throws UnmarshalObjectException { try { final JaxbHelper helper = new JaxbHelper ( ) ; final SrcGen4JConfig config = helper . create ( configFile , JAXBContext . newInstance ( SrcGen4JConfig . class , VelocityGeneratorConfig . class , ParameterizedTemplateParserConfig . class , ParameterizedTemplateGeneratorConfig . class ) ) ; config . init ( context , Utils4J . getCanonicalFile ( configFile . getParentFile ( ) ) ) ; return config ; } catch ( final JAXBException ex ) { throw new UnmarshalObjectException ( "Error reading the configuration: " + configFile , ex ) ; } }


Input: PEM : Privacy - enhanced Electronic Mail [CODESPLIT] public static String toPemEncoded ( byte [ ] der , String label ) { StringWriter pem = new StringWriter ( ) ; PrintWriter pw = new PrintWriter ( pem ) ; pw . append ( "-----BEGIN " ) . append ( label ) . println ( "-----" ) ; pw . write ( new String ( Base64Delegate . getDefault ( ) . mimeEncode ( der ) , CharsetUtils . US_ASCII ) ) ; pw . println ( ) ; pw . append ( "-----END " ) . append ( label ) . println ( "-----" ) ; pw . close ( ) ; return pem . toString ( ) ; }


Input: Returns all Link headers listed in an { @link HttpResponse } . [CODESPLIT] public static Iterable < LinkHeader > getLinkHeaders ( HttpResponse response ) { return stream ( response . getHeaders ( "Link" ) ) . flatMap ( x -> stream ( x . getElements ( ) ) . map ( LinkHeader :: new ) ) . collect ( toList ( ) ) ; }


Input: Reads invocation arguments from HTTP request URL parameters accordingly formal parameters list . This arguments reader implementation delegates { @link QueryParametersParser } for URL parameters parsing . [CODESPLIT] @ Override public Object [ ] read ( HttpServletRequest httpRequest , Type [ ] formalParameters ) throws IOException , IllegalArgumentException { try { QueryParametersParser queryParameters = new QueryParametersParser ( httpRequest . getInputStream ( ) ) ; return queryParameters . getArguments ( formalParameters ) ; } catch ( SyntaxException e ) { throw new IllegalArgumentException ( e ) ; } }


Input: Saves the result <code > result< / code > of the file { @code file } . [CODESPLIT] @ Override public void put ( final File file , final Counts result ) { FileCount fileCount = new FileCount ( file , result ) ; if ( results . contains ( fileCount ) ) { results . remove ( fileCount ) ; } results . add ( fileCount ) ; }


Input: Returns the { @code Counts } of a filename . [CODESPLIT] public Counts get ( final File file ) { int index = results . indexOf ( new FileCount ( file , null ) ) ; if ( index == - 1 ) { return null ; } else { return results . get ( index ) . getCounts ( ) ; } }


Input: Returns all saved filenames . [CODESPLIT] public File [ ] getFiles ( ) { List < File > result = new ArrayList <> ( ) ; for ( FileCount fileCount : results ) { result . add ( fileCount . getFile ( ) ) ; } Collections . sort ( result , new FitFileComparator ( ) ) ; return result . toArray ( new File [ result . size ( ) ] ) ; }


Input: Returns the sum of all results . [CODESPLIT] public Counts getSummary ( ) { Counts result = new Counts ( ) ; for ( FileCount fileCount : results ) { if ( fileCount . getCounts ( ) != null ) { result . tally ( fileCount . getCounts ( ) ) ; } } return result ; }


Input:
Returns a single HTML Table row representing the results of the file { @code file } . [CODESPLIT] public String getRow ( final File file ) { StringBuilder builder = new StringBuilder ( ) ; Counts counts = get ( file ) ; builder . append ( "
" ) ; int depth = dirHelper . dirDepth ( file ) ; indent ( depth , builder ) ; builder . append ( "" ) ; builder . append ( file . getName ( ) ) ; builder . append ( "" ) ; builder . append ( "	" ) ; if ( counts == null ) { builder . append ( "(none)" ) ; } else { builder . append ( counts . toString ( ) ) ; } builder . append ( "
" ) ; return builder . toString ( ) ; }


Input:
Returns a summary row for a whole test run . [CODESPLIT] public String getSummaryRow ( final File directory ) { StringBuilder builder = new StringBuilder ( ) ; Counts counts = getSummary ( ) ; builder . append ( "
" ) ; builder . append ( directory . getName ( ) ) ; builder . append ( "	" ) ; builder . append ( counts . toString ( ) ) ; builder . append ( "
" ) ; return builder . toString ( ) ; }


Input:
Prints out a table to { @code stream } which contains all saved results including all summary rows . [CODESPLIT] @ Override public void print ( final File directory , final OutputStream stream ) throws IOException { OutputStreamWriter osw = new OutputStreamWriter ( stream ) ; BufferedWriter bw = new BufferedWriter ( osw ) ; bw . write ( "
" ) ; bw . write ( getSummaryRow ( directory ) ) ; bw . write ( "

" ) ; File [ ] files = getFiles ( ) ; if ( files . length == 0 ) { bw . write ( "
no files found
" ) ; } else { File currentDir = directory ; for ( File file : files ) { File newDir = file . getAbsoluteFile ( ) . getParentFile ( ) ; if ( ! newDir . equals ( currentDir ) && ! dirHelper . isSubDir ( currentDir , newDir ) ) { for ( File tmpDir : dirHelper . getParentDirs ( dirHelper . getCommonDir ( currentDir , file ) , newDir ) ) { bw . write ( getSubSummaryRow ( tmpDir ) ) ; } } currentDir = newDir ; bw . write ( getRow ( file ) ) ; } } bw . write ( "
" ) ; bw . flush ( ) ; osw . flush ( ) ; }


Input:
Generates a HTML summary row for a subdirectory . [CODESPLIT] public String getSubSummaryRow ( final File path ) throws IOException { Counts sum = subDirSum ( path ) ; return String . format ( "
%s	%s
" , color ( sum ) , FitUtils . htmlSafeFile ( dirHelper . abs2rel ( new File ( "" ) . getAbsolutePath ( ) , path . getAbsolutePath ( ) ) ) , sum . toString ( ) ) ; }


Input: Serialize return value to HTTP response using JSON encoding . This method delegates { @link Json#stringify ( java . io . Writer Object ) } for value serialization . [CODESPLIT] @ Override public void write ( HttpServletResponse httpResponse , Object value ) throws IOException { json . stringify ( new OutputStreamWriter ( httpResponse . getOutputStream ( ) , "UTF-8" ) , value ) ; }


Input: Delegates { @link AppFactory#getInstance ( Class Object ... ) } . [CODESPLIT] public static < T > T getInstance ( Class < T > interfaceClass , Object ... args ) { return getAppFactory ( ) . getInstance ( interfaceClass , args ) ; }


Input: Delegates { @link AppFactory#getInstance ( String Class Object ... ) } . [CODESPLIT] public static < T > T getInstance ( String instanceName , Class < T > interfaceClass , Object ... args ) { return getAppFactory ( ) . getInstance ( instanceName , interfaceClass , args ) ; }


Input: Delegates { @link AppFactory#getOptionalInstance ( Class Object ... ) } . [CODESPLIT] public static < T > T getOptionalInstance ( Class < T > interfaceClass , Object ... args ) { return getAppFactory ( ) . getOptionalInstance ( interfaceClass , args ) ; }


Input: Delegates { @link AppFactory#getRemoteInstance ( String Class ) } . [CODESPLIT] public static < T > T getRemoteInstance ( String implementationURL , Class < ? super T > interfaceClass ) { return getAppFactory ( ) . getRemoteInstance ( implementationURL , interfaceClass ) ; }


Input: Helper method to retrieve application factory bound to current thread . Retrieve application factory from current thread local storage . In order to be successfully this method must be preceded by { @link #bind ( AppFactory ) } called from current thread ; otherwise bug error is thrown . [CODESPLIT] public static AppFactory getAppFactory ( ) { AppFactory appFactory = tls . get ( ) ; if ( appFactory == null ) { throw new BugError ( "No application factory bound to current thread |%s|. See #bind(AppFactory)." , Thread . currentThread ( ) ) ; } return appFactory ; }


Input: Adds a row of filter text boxes to a Vaadin { @link Grid } . [CODESPLIT] public static void addFilterRow ( Grid grid ) { if ( grid . getHeaderRowCount ( ) < 2 ) { grid . appendHeaderRow ( ) ; } Grid . HeaderRow headerRow = grid . getHeaderRow ( 1 ) ; Container . Indexed container = grid . getContainerDataSource ( ) ; container . getContainerPropertyIds ( ) . forEach ( pid -> { TextField filterField = new TextField ( ) ; filterField . setInputPrompt ( "Filter" ) ; filterField . addStyleName ( ValoTheme . TEXTFIELD_SMALL ) ; filterField . setWidth ( 100 , Sizeable . Unit . PERCENTAGE ) ; filterField . addTextChangeListener ( event -> { ( ( Container . SimpleFilterable ) container ) . removeContainerFilters ( pid ) ; if ( ! event . getText ( ) . isEmpty ( ) ) { ( ( Container . Filterable ) container ) . addContainerFilter ( new SimpleStringFilter ( pid , event . getText ( ) , true , false ) ) ; } } ) ; headerRow . getCell ( pid ) . setComponent ( filterField ) ; } ) ; }


Input: Load service defined by managed class interface and return service instance . This factory does not support arguments . Service provider should be present into run - time otherwise no provider exception is thrown . [CODESPLIT] @ SuppressWarnings ( "unchecked" ) @ Override public < I > I newInstance ( ManagedClassSPI managedClass , Object ... args ) { if ( args . length > 0 ) { throw new IllegalArgumentException ( "Service instances factory does not support arguments." ) ; } Class < ? > [ ] interfaceClasses = managedClass . getInterfaceClasses ( ) ; if ( interfaceClasses == null ) { throw new BugError ( "Invalid managed class. Null interface classes." ) ; } if ( interfaceClasses . length != 1 ) { throw new BugError ( "Invalid managed class. It should have exactly one interface class." ) ; } return ( I ) Classes . loadService ( interfaceClasses [ 0 ] ) ; }


Input: Returns the setup class . [CODESPLIT] public final Class < ? > getSetupClass ( ) { if ( setupClass != null ) { return setupClass ; } LOG . info ( "Creating setup class: {}" , setupClassName ) ; try { setupClass = Class . forName ( setupClassName , true , context . getClassLoader ( ) ) ; } catch ( final ClassNotFoundException ex ) { throw new RuntimeException ( "Couldn't load setup class: " + setupClassName , ex ) ; } return setupClass ; }


Input: Returns a list of model directories to parse . [CODESPLIT] public final List < File > getModelDirs ( ) { if ( ( modelDirs == null ) && ( modelPath != null ) ) { modelDirs = paths ( ) . stream ( ) . filter ( XtextParserConfig :: isFile ) . map ( XtextParserConfig :: asFile ) . collect ( Collectors . toList ( ) ) ; } return modelDirs ; }


Input: Returns a list of model resources to parse . [CODESPLIT] public final List < URI > getModelResources ( ) { if ( ( modelResources == null ) && ( modelPath != null ) ) { modelResources = new ArrayList <> ( ) ; modelResources = paths ( ) . stream ( ) . filter ( XtextParserConfig :: isResource ) . map ( XtextParserConfig :: asResource ) . collect ( Collectors . toList ( ) ) ; } return modelResources ; }


Input: Reads a row which contains two cells and registers an alias . <p > The first cell must contain the alias the second one must contains the fully qualified class name . Using another alias as class name is not permitted . <p > Cross references are resolved . [CODESPLIT] @ Override protected void doRow ( FitRow row ) { if ( row . size ( ) < 2 ) { row . cells ( ) . get ( 0 ) . ignore ( ) ; return ; } alias = validator . preProcess ( row . cells ( ) . get ( 0 ) ) ; className = validator . preProcess ( row . cells ( ) . get ( 1 ) ) ; AliasHelper aliasHelper = DependencyManager . getOrCreate ( AliasHelper . class ) ; aliasHelper . register ( alias , className ) ; }


Input: Sets a set of candidates for selection . [CODESPLIT] public void setCandidates ( Collection < T > candidates ) { twinColSelect . setContainerDataSource ( container = new BeanItemContainer <> ( entityType , candidates ) ) ; }


Input: Runs the file { @code fileName } using the current runner and replaces the current row with the results . [CODESPLIT] public void file ( final String fileName ) throws Exception { String in = thisDir . getAbsolutePath ( ) ; File out = outDir . getAbsoluteFile ( ) ; //noinspection ResultOfMethodCallIgnored out . mkdirs ( ) ; File inputFile = dirHelper . rel2abs ( in , fileName ) ; File outputFile = dirHelper . subdir ( out , inputFile . getName ( ) ) ; Counts result = runner . run ( inputFile , outputFile ) ; appendResults ( row , inputFile . getName ( ) , result ) ; row . getTable ( ) . getCounts ( ) . tally ( result ) ; }


Input: TODO : not tested? [CODESPLIT] public void directory ( final String dir ) throws Exception { File srcDir = dirHelper . rel2abs ( thisDir . getAbsolutePath ( ) , dir ) ; List < FileInformation > files = new DirectoryFilter ( srcDir , dirHelper ) . getSelectedFiles ( ) ; RunConfiguration runConfiguration = new RunConfiguration ( ) ; runConfiguration . setEncoding ( runner . getEncoding ( ) ) ; runConfiguration . setBaseDir ( srcDir ) ; runConfiguration . setDestination ( outDir . getPath ( ) ) ; runConfiguration . setSource ( files . toArray ( new FileInformation [ files . size ( ) ] ) ) ; System . out . println ( "Run: " + files + " in " + srcDir + " to " + outDir ) ; final FitRunner fitRunner = new FitRunner ( dirHelper , runConfiguration ) ; FitParseResult results = new FitParseResult ( ) ; fitRunner . run ( results ) ; results . insertAndReplace ( row ) ; row . getTable ( ) . getCounts ( ) . tally ( results . getCounts ( ) ) ; }


Input: Load configuration document from file . [CODESPLIT] protected static void loadXML ( InputStream inputStream , Loader loader ) throws ConfigException { try { SAXParserFactory factory = SAXParserFactory . newInstance ( ) ; SAXParser parser = factory . newSAXParser ( ) ; XMLReader reader = parser . getXMLReader ( ) ; reader . setContentHandler ( loader ) ; reader . parse ( new InputSource ( inputStream ) ) ; } catch ( Exception e ) { throw new ConfigException ( "Fail to load configuration document from file |%s|: %s" , inputStream , e ) ; } }


Input: Handler for errors reported by REST endpoints . [CODESPLIT] protected void onError ( Exception ex ) { Notification . show ( "Error" , ex . getLocalizedMessage ( ) , Notification . Type . ERROR_MESSAGE ) ; }


Input: Builds a form layout with fields for all properties exposed by the entity . [CODESPLIT] protected Component buildAndBind ( Class < TEntity > entityType ) { FormLayout layout = new FormLayout ( ) ; getPropertiesWithoutAnnotation ( entityType , EditorHidden . class ) . forEach ( ( property ) - > { if ( property . getWriteMethod ( ) == null ) { return ; } Component component = buildAndBind ( property ) ; component . setWidth ( 100 , Unit . PERCENTAGE ) ; if ( component . getCaption ( ) == null ) { component . setCaption ( propertyIdToHumanFriendly ( property . getName ( ) ) ) ; } if ( component instanceof DateField ) { ( ( DateField ) component ) . setResolution ( Resolution . SECOND ) ; } layout . addComponent ( component ) ; getAnnotation ( entityType , property , Description . class ) . ifPresent ( x -> layout . addComponent ( buildDescriptionComponent ( property , x . value ( ) ) ) ) ; }


Input:
Parse URL query parameters provided by source reader . Detect query parameters name and and value and update a list of parsed parameters . Takes care to decode escaped characters from both parameter names and values . <p > This parser expect UTF - 8 for text encoding and throws unsupported encoding for different codes . [CODESPLIT] private static List < Parameter > parse ( Reader reader ) throws IOException { List < Parameter > parameters = new ArrayList < Parameter > ( ) ; Parameter parameter = new Parameter ( ) ; State state = State . NAME ; for ( ; ; ) { int b = reader . read ( ) ; if ( b == - 1 ) { // conclude last parameter value
 if ( parameter . isEmpty ( ) ) { break ; } if ( parameters . isEmpty ( ) && parameter . isRawValue ( ) ) { parameter . commitRawValue ( ) ; } else { parameter . commitValue ( ) ; } parameters . add ( parameter ) ; break ; } char c = ( char ) b ; switch ( state ) { case NAME : switch ( c ) { case ' ' : state = State . VALUE ; parameter . commitName ( ) ; break ; case ' ' : if ( parameter . getBuilder ( ) . isEmpty ( ) ) { throw new SyntaxException ( "Invalid query string. Empty parameter name." ) ; } else { throw new SyntaxException ( "Invalid query string parameter |%s|. Missing name/value separator." , parameter . getBuilder ( ) ) ; } default : parameter . append ( c ) ; } break ; case VALUE : switch ( c ) { case ' ' : state = State . NAME ; parameter . commitValue ( ) ; parameters . add ( parameter ) ; parameter = new Parameter ( ) ; break ; case ' ' : throw new SyntaxException ( "Invalid query string parameter |%s|. Unescaped '=' character." , parameter . getBuilder ( ) ) ; default : parameter . append ( c ) ; } } } return parameters ; }


Input:
Get an array of arguments suitable for a method invocation . This method did its best to fill the arguments array . The logic is simple : ignore query extra parameters and set to null the missing ones . Both cases are recorded to debug log . Returned arguments array has the same size as requested formal parameters array . <p > Parameter values from parsed { @link #parameters } are converted to requested type using { @link #asObject ( String Type ) } utility method . If formal parameters has a single type that has no converter uses reflection to map query parameters to object field by name . <p > Note that because parameter names are not preserved on run - time query parameters are mapped by position to invocation arguments . This means is caller responsibility to match formal parameters order and type with actual query string parameters . [CODESPLIT] public Object [ ] getArguments ( Type [ ] formalParameters ) { if ( formalParameters . length == 0 ) { return new Object [ 0 ] ; } Object [ ] arguments = new Object [ formalParameters . length ] ; if ( isObject ( formalParameters ) ) { // if there is single formal parameter and it is not a value type create object instance and initialize fields from
 // request parameters; object class should have no arguments constructor
 Class < ? > type = ( Class < ? > ) formalParameters [ 0 ] ; Object object = Classes . newInstance ( type ) ; for ( Parameter parameter : parameters ) { Field field = Classes . getField ( type , Strings . toMemberName ( parameter . getName ( ) ) ) ; Classes . setFieldValue ( object , field , asObject ( parameter . getValue ( ) , field . getType ( ) ) ) ; } return new Object [ ] { object } ; } int i = 0 , argumentsCount = Math . min ( formalParameters . length , parameters . size ( ) ) ; for ( i = 0 ; i < argumentsCount ; ++ i ) { arguments [ i ] = asObject ( parameters . get ( i ) . getValue ( ) , formalParameters [ i ] ) ; } for ( ; i < formalParameters . length ; ++ i ) { log . debug ( "Missing request parameter |%s|. Set it to null." , i , formalParameters [ i ] ) ; arguments [ i ] = null ; } for ( ; i < parameters . size ( ) ; ++ i ) { log . debug ( "Unused request parameter |%s|. Ignore it." , parameters . get ( i ) ) ; } return arguments ; }


Input:
Helper method to convert string parameter to an instance of a given type . Requested <code > type< / code > should be a value type as accepted by converter package or an array / collection of value types . In the later case <code > value< / code > should be a comma separated string of items . If given <code > value< / code > is null returns an empty value as defined by { @link Types#getEmptyValue ( Type ) } . [CODESPLIT] @ SuppressWarnings ( "unchecked" ) private static < T > T asObject ( String value , Type type ) { if ( value == null ) { return ( T ) Types . getEmptyValue ( type ) ; } if ( ! Types . isArrayLike ( type ) ) { if ( ! ( type instanceof Class ) ) { throw new BugError ( "Generic value types are not supported." ) ; } if ( ConverterRegistry . hasType ( type ) ) { return ConverterRegistry . getConverter ( ) . asObject ( value , ( Class < T > ) type ) ; } log . debug ( "Missing converter for query parameter of type |%s|." , type ) ; return ( T ) Types . getEmptyValue ( type ) ; } // here we have an array/collection represented as comma separated primitives
 List < String > strings = Strings . split ( value , ' ' ) ; if ( type == String [ ] . class ) { return ( T ) strings . toArray ( new String [ strings . size ( ) ] ) ; } if ( Types . isKindOf ( type , Collection . class ) ) { Type collectionType = type ; Class < ? > itemType = String . class ; if ( type instanceof ParameterizedType ) { collectionType = ( ( ParameterizedType ) type ) . getRawType ( ) ; itemType = ( Class < ? > ) ( ( ParameterizedType ) type ) . getActualTypeArguments ( ) [ 0 ] ; } Collection < Object > collection = Classes . newCollection ( collectionType ) ; Converter converter = ConverterRegistry . getConverter ( ) ; for ( String s : strings ) { collection . add ( converter . asObject ( s . trim ( ) , itemType ) ) ; } return ( T ) collection ; } throw new BugError ( "Type not supported |%s|." , type ) ; }


Input: Test if method formal parameters designates a strict object that is is not primitive array collection or map . [CODESPLIT] private static boolean isObject ( Type [ ] formalParameters ) { if ( formalParameters . length != 1 ) { return false ; } final Type type = formalParameters [ 0 ] ; if ( ! ( type instanceof Class ) ) { return false ; } if ( Types . isPrimitive ( type ) ) { return false ; } if ( Types . isArrayLike ( type ) ) { return false ; } if ( Types . isMap ( type ) ) { return false ; } if ( ConverterRegistry . hasType ( type ) ) { return false ; } return true ; }


Input: Uses JSON deserializer to parse method invocation arguments accordingly formal parameters list . [CODESPLIT] @ Override public Object [ ] read ( HttpServletRequest httpRequest , Type [ ] formalParameters ) throws IOException , IllegalArgumentException { JsonReader reader = new JsonReader ( httpRequest . getInputStream ( ) , expectedStartSequence ( formalParameters ) ) ; try { return json . parse ( reader , formalParameters ) ; } catch ( JsonException e ) { throw new IllegalArgumentException ( e . getMessage ( ) ) ; } finally { reader . close ( ) ; } }


Input: Parse JSON from input stream accordingly given type . Return parsed object . [CODESPLIT] @ Override public Object read ( InputStream inputStream , Type type ) throws IOException { try { return json . parse ( new InputStreamReader ( inputStream , "UTF-8" ) , type ) ; } catch ( JsonException | ClassCastException | UnsupportedEncodingException e ) { throw new IllegalArgumentException ( e . getMessage ( ) ) ; } }


Input:
Pre - process constructor arguments for local managed classes . A managed class is <code > local< / code > if is of { @link InstanceType#POJO } or { @link InstanceType#PROXY } type . Attempting to pre - process arguments for other managed class types is silently ignored . This method delegates { @link #preProcessArguments ( ManagedClassSPI Member Class [] Object ... ) } . [CODESPLIT] public Object [ ] preProcessArguments ( ManagedClassSPI managedClass , Object ... args ) { // arguments can be null if on invocations chain there is Proxy handler invoked with no arguments
 if ( args == null ) { args = EMPTY_ARGS ; } if ( managedClass . getImplementationClass ( ) == null ) { return args ; } Constructor < ? > constructor = managedClass . getConstructor ( ) ; // managed class constructor parameters have the same limitation as injected fields: they must be a managed
 // class on their turn; it is considered a bug trying to use not managed classes as constructor argument
 // because managed class is not generic is safe to use getParameterTypes instead of getGenericParameterTypes
 final Class < ? > [ ] types = constructor . getParameterTypes ( ) ; return preProcessArguments ( managedClass , constructor , types , args ) ; }


Input:
Pre - process managed method invocation arguments . This processor prepares invocation arguments for given managed method ; it just delegates { @link #preProcessArguments ( ManagedClassSPI Member Class [] Object ... ) } . [CODESPLIT] public Object [ ] preProcessArguments ( ManagedMethodSPI managedMethod , Object ... args ) { // arguments can be null if on invocations chain there is Proxy handler invoked with no arguments
 if ( args == null ) { args = EMPTY_ARGS ; } final ManagedClassSPI managedClass = managedMethod . getDeclaringClass ( ) ; final Method method = managedMethod . getMethod ( ) ; final Class < ? > [ ] types = method . getParameterTypes ( ) ; return preProcessArguments ( managedClass , method , types , args ) ; }


Input:
Update and validate invocation arguments against given formal parameter types . If formal parameters is not empty but no invocation arguments this method will inject dependency using { @link #getDependencyValue ( ManagedClassSPI Class ) } . This method also performs arguments validity check against formal parameters throwing illegal arguments if validation fails . [CODESPLIT] private static Object [ ] preProcessArguments ( ManagedClassSPI managedClass , Member member , Class < ? > [ ] formalParameters , Object ... args ) { switch ( args . length ) { case 0 : args = new Object [ formalParameters . length ] ; for ( int i = 0 ; i < args . length ; i ++ ) { args [ i ] = getDependencyValue ( managedClass , formalParameters [ i ] ) ; } break ; case 1 : // TODO: refine variable arguments: test for formal parameters type, document and test
 if ( args [ 0 ] instanceof VarArgs && formalParameters . length == 1 && formalParameters [ 0 ] . isArray ( ) ) { args [ 0 ] = ( ( VarArgs < ? > ) args [ 0 ] ) . getArguments ( ) ; } break ; } // arguments validity test against formal parameters: count and types
 if ( formalParameters . length != args . length ) { throw new IllegalArgumentException ( "Invalid arguments count on method |%s|. Expected |%d| but got |%d|." , member , formalParameters . length , args . length ) ; } for ( int i = 0 ; i < formalParameters . length ; ++ i ) { if ( args [ i ] != null && ! Types . isInstanceOf ( args [ i ] , formalParameters [ i ] ) ) { throw new IllegalArgumentException ( "Invalid argument type at position |%d| on method |%s|. Expected |%s| but got |%s|." , i , member , formalParameters [ i ] , args [ i ] . getClass ( ) ) ; } } return args ; }


Input: extracts and removes parameters from a cell . [CODESPLIT] public static String extractCellParameter ( FitCell cell ) { final Matcher matcher = PARAMETER_PATTERN . matcher ( cell . getFitValue ( ) ) ; if ( matcher . matches ( ) ) { cell . setFitValue ( matcher . group ( 1 ) ) ; return matcher . group ( 2 ) ; } else { return null ; } }


Input: javax . persistence . Query & javax . persistence . TypedQuery [CODESPLIT] @ Override public java . util . Map < java . lang . String , java . lang . Object > getHints ( ) { return this . q . getHints ( ) ; }


Input: / * Altered by Rick Mugridge to dispatch on the first Fixture [CODESPLIT] public void doDocument ( FitDocument document ) { summary . put ( "run date" , new Date ( ) ) ; summary . put ( "run elapsed time" , new RunTime ( ) ) ; if ( document != null ) { interpretTables ( document ) ; } }


Input: / * Added by Rick Mugridge [CODESPLIT] private void interpretTables ( FitDocument documents ) { for ( FitTable table : documents . tables ( ) ) { try { Fixture fixture = getLinkedFixtureWithArgs ( table ) ; fixture . doTable ( table ) ; counts . tally ( table . getCounts ( ) ) ; } catch ( Throwable e ) { table . exception ( e ) ; counts . exceptions ++ ; } } }


Input: / * Added from FitNesse [CODESPLIT] protected Fixture getLinkedFixtureWithArgs ( FitTable table ) { Fixture fixture = loadFixture ( table . getFixtureClass ( ) ) ; fixture . setParams ( getArgsForTable ( table ) ) ; return fixture ; }


Input: Loads a fixutre by its fully quallified { @code className } . If the { @code className } is an alias the referenced class is used . [CODESPLIT] private Fixture loadFixture ( final String fixtureName ) { AliasHelper helper = DependencyManager . getOrCreate ( AliasHelper . class ) ; String realName = helper . getClazz ( fixtureName ) ; return loadFixtureByName ( realName ) ; }


Input: Sets the SSL parameter of the mail { @link SetupHelper } . [CODESPLIT] public void ssl ( final String ssl ) { DependencyManager . getOrCreate ( SetupHelper . class ) . setSSL ( BooleanTypeHandler . parseBool ( ssl ) ) ; }


Input: Sets the port parameter of the mail { @link SetupHelper } . [CODESPLIT] public void port ( final String port ) { DependencyManager . getOrCreate ( SetupHelper . class ) . setPort ( Integer . parseInt ( port ) ) ; }


Input: Test if given HTTP request is performed via XMLHttpRequest . [CODESPLIT] public static boolean isXHR ( HttpServletRequest httpRequest ) { String requestedWith = httpRequest . getHeader ( X_REQUESTED_WITH ) ; return requestedWith != null ? requestedWith . equalsIgnoreCase ( XML_HTTP_REQUEST ) : false ; }


Input: Test if HTTP request is from Android . [CODESPLIT] public static boolean isAndroid ( HttpServletRequest httpRequest ) { String requestedWith = httpRequest . getHeader ( X_REQUESTED_WITH ) ; return requestedWith != null ? requestedWith . equalsIgnoreCase ( ANDROID_USER_AGENT ) : false ; }


Input: This method is enacted for empty formal parameters . It just return { @link #EMPTY_ARGUMENTS } . [CODESPLIT] @ Override public Object [ ] read ( HttpServletRequest httpRequest , Type [ ] formalParameters ) throws IOException , IllegalArgumentException { return EMPTY_ARGUMENTS ; }


Input: Traversal //////////////////////////////// [CODESPLIT] @ Override protected void doRow ( FitRow row ) throws Exception { Date start = time ( ) ; super . doRow ( row ) ; long split = time ( ) . getTime ( ) - start . getTime ( ) ; FitCell cell = row . append ( ) ; cell . setDisplayValue ( format . format ( start ) ) ; cell . info ( "time" ) ; cell = row . append ( ) ; cell . setDisplayValueRaw ( split < 1000 ? " " : Double . toString ( ( split ) / 1000.0 ) ) ; cell . info ( "split" ) ; }


Input: FIXME : test! [CODESPLIT] public void remove ( int index ) { table . select ( TAG ) . get ( index + contentStartPosition ) . remove ( ) ; rows . remove ( index ) ; updateIndices ( ) ; }


Input: FIXME : test! [CODESPLIT] public FitRow insert ( int index ) { Element tr = new Element ( Tag . valueOf ( TAG ) , table . baseUri ( ) ) ; FitRow row = new FitRow ( this , tr ) ; Element tbody = table . select ( "tbody" ) . first ( ) ; tbody . insertChildren ( index + contentStartPosition , Collections . singleton ( tr ) ) ; rows . add ( index , row ) ; updateIndices ( ) ; return row ; }


Input: This method is a this wrapper for { @link StreamFactory#getInstance ( InputStream Type ) } . [CODESPLIT] @ Override public Object read ( InputStream inputStream , Type type ) throws IOException { Closeable closeable = StreamFactory . getInstance ( inputStream , type ) ; threadLocal . set ( closeable ) ; return closeable ; }


Input:
Persist instance bound to given managed instance key . This method simply uses provided <code > instanceKey< / code > argument to add instance to { @link #instancesPool } . Both arguments should to be not null . [CODESPLIT] @ Override public void persistInstance ( InstanceKey instanceKey , Object instance ) { // at this point managed class and instance are guaranteed to be non null
 instancesPool . put ( instanceKey , instance ) ; }


Input: Refresh when child elements are created or updated [CODESPLIT] @ Subscribe public void handle ( ElementEvent < TEntity > message ) { if ( message . getEndpoint ( ) . getEntityType ( ) == this . endpoint . getEntityType ( ) ) { refresh ( ) ; } }


Input: Processes the content of { @code cells } . [CODESPLIT] @ Override protected void doCells ( List < FitCell > cells ) { String name = cells . get ( 0 ) . getFitValue ( ) ; processRowWithCommand ( cells , name ) ; }


Input: Lists all properties on a bean type . Ensures properties annotated with { @link Id } or called name are always listed first . [CODESPLIT] @ SneakyThrows public static List < PropertyDescriptor > getProperties ( Class < ? > beanType ) { LinkedList < PropertyDescriptor > properties = new LinkedList <> ( ) ; for ( PropertyDescriptor property : Introspector . getBeanInfo ( beanType ) . getPropertyDescriptors ( ) ) { if ( getAnnotation ( beanType , property , Id . class ) . isPresent ( ) || property . getName ( ) . equals ( "name" ) ) { properties . addFirst ( property ) ; } else { properties . add ( property ) ; } } return properties ; }


Input: Lists all properties on a bean type that have a specific annotation on their getter or backing field . [CODESPLIT] public static < TAnnotation extends Annotation > List < PropertyDescriptor > getPropertiesWithAnnotation ( Class < ? > beanType , Class < TAnnotation > annotationType ) { LinkedList < PropertyDescriptor > result = new LinkedList <> ( ) ; getProperties ( beanType ) . forEach ( property -> { if ( property . getReadMethod ( ) != null && property . getReadMethod ( ) . getAnnotation ( annotationType ) != null || isFieldAnnotated ( beanType , property . getName ( ) , annotationType ) ) { result . add ( property ) ; } } ) ; return result ; }


Input: Returns an annotation of a specific type on a property s getter or its backing field . [CODESPLIT] public static < TAnnotation extends Annotation > Optional < TAnnotation > getAnnotation ( Class < ? > beanType , PropertyDescriptor property , Class < TAnnotation > annotationType ) { Optional < TAnnotation > annotation = stream ( property . getReadMethod ( ) . getAnnotationsByType ( annotationType ) ) . findAny ( ) ; return annotation . isPresent ( ) ? annotation : getAnnotationOnField ( beanType , property . getName ( ) , annotationType ) ; }


Input: Sets the filename pattern to { @code pattern } . [CODESPLIT] public void pattern ( final String pattern ) { FileFixtureHelper helper = DependencyManager . getOrCreate ( FileFixtureHelper . class ) ; helper . setPattern ( pattern ) ; }


Input: Sets the directory to { @code directory } . [CODESPLIT] public void directory ( final String directory ) { FileFixtureHelper helper = DependencyManager . getOrCreate ( FileFixtureHelper . class ) ; helper . setDirectory ( new File ( directory ) ) ; }


Input: Sets the encoding to { @code encoding } . [CODESPLIT] public void encoding ( final String encoding ) { FileFixtureHelper helper = DependencyManager . getOrCreate ( FileFixtureHelper . class ) ; helper . setEncoding ( encoding ) ; }


Input: Log formatted message to Java logger since framework logger is not yet initialized . [CODESPLIT] private static String log ( String message , Object ... args ) { message = String . format ( message , args ) ; java . util . logging . Logger . getLogger ( Server . class . getCanonicalName ( ) ) . log ( java . util . logging . Level . SEVERE , message ) ; return message ; }


Input: Uses the Ruby Whois gem to perform a whois lookup [CODESPLIT] public WhoisResult lookup ( String domain , int timeout ) { container . put ( "domain" , domain ) ; container . put ( "timeout_param" , timeout ) ; try { return ( WhoisResult ) container . runScriptlet ( JRubyWhois . class . getResourceAsStream ( "jruby-whois.rb" ) , "jruby-whois.rb" ) ; } catch ( EvalFailedException e ) { if ( e . getMessage ( ) . startsWith ( "(ServerNotFound)" ) ) { throw new ServerNotFoundException ( e ) ; } if ( e . getMessage ( ) . startsWith ( "(WebInterfaceError" ) ) { throw new WebInterfaceErrorException ( e ) ; } throw e ; } }


Input: Check if Ruby Whois gem has a parser for a specific registrar [CODESPLIT] public boolean hasParserForWhoisHost ( String whoisHost ) { container . put ( "host" , whoisHost ) ; return ( Boolean ) container . runScriptlet ( JRubyWhois . class . getResourceAsStream ( "jruby-has-parser.rb" ) , "jruby-has-parser.rb" ) ; }


Input:
HTTP - RMI request service . This is the implementation of the { @link AppServlet#service ( javax . servlet . ServletRequest javax . servlet . ServletResponse ) } abstract method . It locates remote managed method addressed by request path deserialize actual parameters from HTTP request reflexively invoke the method and serialize method returned value to HTTP response . <p > Actual parameters are transported into HTTP request body and are encoded accordingly <code > Content - Type< / code > request header ; for supported parameters encodings please see { @link ServerEncoders#getArgumentsReader ( HttpServletRequest Type [] ) } factory method . On its side returned value is transported into HTTP response body too and is encoded accordingly its type - see { @link ServerEncoders#getValueWriter ( ContentType ) } for supported encodings for returned value . [CODESPLIT] @ Override public void handleRequest ( RequestContext context ) throws IOException { HttpServletRequest httpRequest = context . getRequest ( ) ; HttpServletResponse httpResponse = context . getResponse ( ) ; Matcher matcher = REQUEST_PATH_PATTERN . matcher ( context . getRequestPath ( ) ) ; if ( ! matcher . find ( ) ) { sendBadRequest ( context ) ; return ; } String interfaceName = className ( matcher . group ( 1 ) ) ; String methodName = matcher . group ( 2 ) ; ManagedMethodSPI managedMethod = null ; ArgumentsReader argumentsReader = null ; Object value = null ; try { ManagedClassSPI managedClass = getManagedClass ( container , interfaceName , httpRequest . getRequestURI ( ) ) ; managedMethod = getManagedMethod ( managedClass , methodName , httpRequest . getRequestURI ( ) ) ; final Type [ ] formalParameters = managedMethod . getParameterTypes ( ) ; argumentsReader = argumentsReaderFactory . getArgumentsReader ( httpRequest , formalParameters ) ; Object [ ] arguments = argumentsReader . read ( httpRequest , formalParameters ) ; Object instance = container . getInstance ( managedClass ) ; value = managedMethod . invoke ( instance , arguments ) ; } catch ( AuthorizationException e ) { sendUnauthorized ( context ) ; return ; } catch ( Throwable t ) { // all exception, including class not found, no such method and illegal argument are send back to client as they are
 sendError ( context , t ) ; return ; } finally { if ( argumentsReader != null ) { argumentsReader . clean ( ) ; } } httpResponse . setCharacterEncoding ( "UTF-8" ) ; if ( managedMethod . isVoid ( ) ) { httpResponse . setStatus ( HttpServletResponse . SC_NO_CONTENT ) ; return ; } ContentType contentType = valueWriterFactory . getContentTypeForValue ( value ) ; httpResponse . setStatus ( HttpServletResponse . SC_OK ) ; httpResponse . setContentType ( contentType . getValue ( ) ) ; ValueWriter valueWriter = valueWriterFactory . getValueWriter ( contentType ) ; valueWriter . write ( httpResponse , value ) ; }


Input: Get remotely accessible managed class registered to a certain interface class . [CODESPLIT] private static ManagedClassSPI getManagedClass ( ContainerSPI container , String interfaceName , String requestURI ) throws ClassNotFoundException { Class < ? > interfaceClass = Classes . forOptionalName ( interfaceName ) ; if ( interfaceClass == null ) { log . error ( "HTTP-RMI request for not existing class |%s|." , interfaceName ) ; throw new ClassNotFoundException ( requestURI ) ; } ManagedClassSPI managedClass = container . getManagedClass ( interfaceClass ) ; if ( managedClass == null ) { log . error ( "HTTP-RMI request for not existing managed class |%s|." , interfaceName ) ; throw new ClassNotFoundException ( requestURI ) ; } if ( ! managedClass . isRemotelyAccessible ( ) ) { log . error ( "HTTP-RMI request for local managed class |%s|. See @Remote annotation." , interfaceName ) ; throw new ClassNotFoundException ( requestURI ) ; } return managedClass ; }


Input: Get managed method that is remotely accessible and has requested name . [CODESPLIT] private static ManagedMethodSPI getManagedMethod ( ManagedClassSPI managedClass , String methodName , String requestURI ) throws NoSuchMethodException { ManagedMethodSPI managedMethod = managedClass . getNetMethod ( methodName ) ; if ( managedMethod == null ) { log . error ( "HTTP-RMI request for not existing managed method |%s#%s|." , managedClass . getInterfaceClass ( ) . getName ( ) , methodName ) ; throw new NoSuchMethodException ( requestURI ) ; } if ( ! managedMethod . isRemotelyAccessible ( ) ) { log . error ( "HTTP-RMI request for local managed method |%s#%s|. See @Remote annotation." , managedClass . getInterfaceClass ( ) . getName ( ) , methodName ) ; throw new NoSuchMethodException ( requestURI ) ; } if ( Types . isKindOf ( managedMethod . getReturnType ( ) , Resource . class ) ) { log . error ( "HTTP-RMI request for managed method |%s#%s| returning a resource." , managedClass . getInterfaceClass ( ) . getName ( ) , methodName ) ; throw new NoSuchMethodException ( requestURI ) ; } return managedMethod ; }


Input:
Extract qualified class name including inner classes from class path part of the request path . Class path parameter is the class name but with slash as separator e . g . <code > / sixqs / site / controller / ParticipantController< / code > . This helper handles inner classes using standard notation with $ separator ; for example <code > / js / test / net / RmiController / Query< / code > is converted to <code > js . test . net . RmiController$Query< / code > . <p > Class nesting is not restricted to a single level . For example <code > / js / test / net / RmiController / Query / Item< / code > is converted to <code > js . test . net . RmiController$Query$Item< / code > . <p > It is expected that class path argument to be well formed . If class path argument is not valid this method behavior is not defined . [CODESPLIT] private static String className ( String classPath ) { StringBuilder className = new StringBuilder ( ) ; char separator = ' ' ; char c = classPath . charAt ( 1 ) ; // i = 1 to skip leading path separator
 for ( int i = 1 ; ; ) { if ( c == ' ' ) { c = separator ; } className . append ( c ) ; if ( ++ i == classPath . length ( ) ) { break ; } c = classPath . charAt ( i ) ; // after first class detected change separator to dollar since rest are inner classes
 // this solution copes well with not restricted inner level
 if ( Character . isUpperCase ( c ) ) { separator = ' ' ; } } return className . toString ( ) ; }


Input: Checks whether the log messages contain the expected exception . [CODESPLIT] public void processNotContainsException ( Map < String , String > parameters ) { LoggingEvent match = getMessageWithException ( parameters ) ; if ( match == null ) { cell . right ( ) ; } else { cell . wrong ( match . getThrowableInformation ( ) . getThrowableStrRep ( ) [ 0 ] ) ; } }


Input: Checks whether the log messages do not contain the expected text . [CODESPLIT] public void processNotContains ( Map < String , String > parameters ) { LoggingEvent match = getMessageWithString ( parameters ) ; if ( match == null ) { cell . right ( ) ; } else { cell . wrong ( match . getMessage ( ) . toString ( ) ) ; } }


Input: Get Primitive Wrappers [CODESPLIT] public Boolean getBoolean2 ( String columnLabel ) throws java . sql . SQLException { boolean value = this . rs . getBoolean ( columnLabel ) ; return ! this . rs . wasNull ( ) ? value : null ; }


Input: java . sql . Wrapper [CODESPLIT] @ Override public boolean isWrapperFor ( java . lang . Class < ? > arg0 ) throws java . sql . SQLException { return this . rs . isWrapperFor ( arg0 ) ; }


Input: Replaces variables ( if defined ) in the value . [CODESPLIT] public final void init ( final Map < String , String > vars ) { value = Utils4J . replaceVars ( getValue ( ) , vars ) ; }


Input: Set common HTTP response headers and delegates actual serialization to subclass . This method disables cache and set content type to value returned by subclass . [CODESPLIT] @ Override public void serialize ( HttpServletResponse httpResponse ) throws IOException { httpResponse . setHeader ( HttpHeader . CACHE_CONTROL , HttpHeader . NO_CACHE ) ; httpResponse . addHeader ( HttpHeader . CACHE_CONTROL , HttpHeader . NO_STORE ) ; httpResponse . setHeader ( HttpHeader . PRAGMA , HttpHeader . NO_CACHE ) ; httpResponse . setDateHeader ( HttpHeader . EXPIRES , 0 ) ; httpResponse . setContentType ( getContentType ( ) . getValue ( ) ) ; serialize ( httpResponse . getOutputStream ( ) ) ; }


Input: Get value of the named cookie or null if cookie does not exist . [CODESPLIT] public String get ( String name ) { Params . notNullOrEmpty ( name , "Cookie name" ) ; if ( cookies == null ) { return null ; } for ( Cookie cookie : cookies ) { if ( name . equals ( cookie . getName ( ) ) ) { return cookie . getValue ( ) ; } } return null ; }


Input: Add cookie to HTTP response of the current request context . Override cookie value if already exists . [CODESPLIT] public void add ( String name , String value ) { Params . notNullOrEmpty ( name , "Cookie name" ) ; Params . notNull ( value , "Cookie value" ) ; Cookie cookie = new Cookie ( name , value ) ; cookie . setPath ( "/" ) ; httpResponse . addCookie ( cookie ) ; }


Input: Convert value object to string and delegates { @link #add ( String String ) } . String conversion is performed by { @link Converter } and may throw { @link ConverterException } . [CODESPLIT] public void add ( String name , Object value ) { add ( name , ConverterRegistry . getConverter ( ) . asString ( value ) ) ; }


Input: Remove cookie from HTTP response . If named cookie does not exist this method does nothing . [CODESPLIT] public void remove ( String name ) { Params . notNullOrEmpty ( name , "Cookie name" ) ; if ( cookies == null ) { return ; } for ( Cookie cookie : cookies ) { if ( name . equals ( cookie . getName ( ) ) ) { cookie . setMaxAge ( 0 ) ; cookie . setValue ( "" ) ; cookie . setPath ( "/" ) ; httpResponse . addCookie ( cookie ) ; break ; } } }


Input: Get cookies iterator . Return empty iterator if not cookies on HTTP request . [CODESPLIT] public Iterator < Cookie > iterator ( ) { if ( cookies == null ) { return Collections . emptyIterator ( ) ; } return Arrays . asList ( cookies ) . iterator ( ) ; }


Input: Configure instance with configuration object provided by instance managed class . In order to perform instance configuration instance should implement { @link Configurable } and managed class should have configuration object see { @link ManagedClassSPI#getConfig () } . If both conditions are satisfied this method executes { @link Configurable#config ( Config ) } on instance . [CODESPLIT] @ Override public void postProcessInstance ( ManagedClassSPI managedClass , Object instance ) { if ( ! ( instance instanceof Configurable ) ) { return ; } Config config = managedClass . getConfig ( ) ; if ( config == null ) { if ( ! ( instance instanceof OptionalConfigurable ) ) { return ; } log . info ( "Default configuration for managed class |%s|." , managedClass ) ; } try { ( ( Configurable ) instance ) . config ( config ) ; } catch ( ConfigException e ) { throw new BugError ( "Invalid configuration for managed class |%s|:\r\n\t- %s" , managedClass , e ) ; } catch ( Throwable t ) { throw new BugError ( t ) ; } }


Input: Returns an existing target file list producer instance or creates a new one if it s the first call to this method . [CODESPLIT] public final TargetFileListProducer getTargetFileListProducer ( ) { if ( tflProducer != null ) { return tflProducer ; } final Object obj = Utils4J . createInstance ( className ) ; if ( ! ( obj instanceof TargetFileListProducer ) ) { throw new IllegalStateException ( "Expected class to be of type '" + TargetFileListProducer . class . getName ( ) + "', but was: " + className ) ; } tflProducer = ( TargetFileListProducer ) obj ; return tflProducer ; }


Input: Adds a public field to the constructed class . [CODESPLIT] public void add ( final Class < ? > type , final String name ) throws ClassNotFoundException { FieldGen fg ; if ( result != null ) { throw new IllegalStateException ( "Class already generated" ) ; } fg = new FieldGen ( Constants . ACC_PUBLIC | Constants . ACC_SUPER , Type . getType ( type ) , name , cg . getConstantPool ( ) ) ; cg . addField ( fg . getField ( ) ) ; }


Input: Compiles the class and returns a class object which contains all added fields . [CODESPLIT] public final Class < ? > compile ( ) { if ( result == null ) { loader . loadJavaClass ( cg . getClassName ( ) , cg . getJavaClass ( ) ) ; try { result = loader . loadClass ( cg . getClassName ( ) ) ; } catch ( ClassNotFoundException e ) { throw new RuntimeException ( e ) ; } } return result ; }


Input: Test that selected image identified by given token is the right response . [CODESPLIT] public boolean verifyResponse ( String token ) throws NullPointerException { return value . equals ( getValue ( tokenedImageFiles . get ( token ) ) ) ; }


Input: Challenge value associated with image file . File name is converted to lower case extension removed and non letter characters replaces with space that is non letters are considered words separators . [CODESPLIT] private static String getValue ( File file ) throws NullPointerException { if ( file == null ) { return null ; } return file . getName ( ) . toLowerCase ( ) . replaceAll ( EXTENSION_REX , "" ) . replaceAll ( NOT_LETTERS_REX , " " ) ; }


Input: Adds a trailing slash to the URI if it does not already have one . [CODESPLIT] @ SneakyThrows public static URI ensureTrailingSlash ( URI uri ) { URIBuilder builder = new URIBuilder ( uri ) ; if ( ! builder . getPath ( ) . endsWith ( "/" ) ) { builder . setPath ( builder . getPath ( ) + "/" ) ; } return builder . build ( ) ; }


Input: Generates a properties object which can be used by { @link de . cologneintelligence . fitgoodies . mail . providers . JavaMailMessageProvider } . Default values are not set . [CODESPLIT] public Properties generateProperties ( ) { Properties result = new Properties ( ) ; if ( proto == null ) { throw new RuntimeException ( "no protocol selected" ) ; } String protocol = proto . toLowerCase ( ) ; setProperty ( result , "mail.store.protocol" , protocol ) ; setProperty ( result , "mail." + protocol + ".host" , host ) ; setProperty ( result , "mail.username" , user ) ; setProperty ( result , "mail.password" , pass ) ; if ( port != 0 ) { setProperty ( result , "mail." + protocol + ".port" , Integer . toString ( port ) ) ; } if ( ssl ) { setProperty ( result , "mail." + protocol + ".ssl" , "true" ) ; } if ( protocol . equals ( "pop3" ) ) { setProperty ( result , "mail.inbox" , "INBOX" ) ; } else { if ( inbox == null ) { throw new RuntimeException ( "no inbox selected" ) ; } setProperty ( result , "mail.inbox" , inbox ) ; } return result ; }


Input:
Implements tiny container boostrap logic . See class description for overall performed steps . Also loads context parameters from external descriptors using { @link ServletContext#getInitParameter ( String ) } . <p > Context initialized listener is not allowed to throw exceptions and it seems there is no standard way to ask servlet container to abort launching the web application . Tiny container solution is to leave servlet context attribute { @link #ATTR_INSTANCE } null . On { @link AppServlet#init ( javax . servlet . ServletConfig ) } mentioned attribute is tested for null and if so permanently mark servlet unavailable . <p > <b > Implementation note : < / b > bootstrap process logic is based on assumption that this <code > contextInitialized< / code > handler is called before servlets initialization . Here is the relevant excerpt from API - DOC : <em > All ServletContextListeners are notified of context initialization before any filter or servlet in the web application is initialized . < / em > [CODESPLIT] @ Override public void contextInitialized ( ServletContextEvent contextEvent ) { final ServletContext servletContext = contextEvent . getServletContext ( ) ; /** Logger diagnostic context stores contextual information regarding current request. */ LogContext logContext = LogFactory . getLogContext ( ) ; logContext . put ( LOG_CONTEXT_APP , servletContext . getContextPath ( ) . isEmpty ( ) ? TinyContainer . ROOT_CONTEXT : servletContext . getContextPath ( ) . substring ( 1 ) ) ; final long start = System . currentTimeMillis ( ) ; log . debug ( "Starting application |%s| container..." , servletContext . getContextPath ( ) ) ; Enumeration < String > parameterNames = servletContext . getInitParameterNames ( ) ; while ( parameterNames . hasMoreElements ( ) ) { final String name = parameterNames . nextElement ( ) ; final String value = servletContext . getInitParameter ( name ) ; contextParameters . setProperty ( name , value ) ; log . debug ( "Load context parameter |%s| value |%s|." , name , value ) ; } try { ConfigBuilder builder = new TinyConfigBuilder ( servletContext , contextParameters ) ; config ( builder . build ( ) ) ; Factory . bind ( this ) ; start ( ) ; // set tiny container reference on servlet context attribute ONLY if no exception
 servletContext . setAttribute ( TinyContainer . ATTR_INSTANCE , this ) ; log . info ( "Application |%s| container started in %d msec." , appName , System . currentTimeMillis ( ) - start ) ; } catch ( ConfigException e ) { log . error ( e ) ; log . fatal ( "Bad container |%s| configuration." , appName ) ; } catch ( Throwable t ) { log . dump ( String . format ( "Fatal error on container |%s| start:" , appName ) , t ) ; } }


Input: Release resources used by this tiny container instance . After execution this method no HTTP requests can be handled . <p > <b > Implementation note : < / b > tiny container destruction logic is based on assumption that this <code > contextDestroyed< / code > handler is called after all web application s servlets destruction . Here is the relevant excerpt from API - DOC : <em > All servlets and filters have been destroy () ed before any ServletContextListeners are notified of context destruction . < / em > [CODESPLIT] @ Override public void contextDestroyed ( ServletContextEvent contextEvent ) { log . debug ( "Context |%s| destroying." , appName ) ; try { destroy ( ) ; } catch ( Throwable t ) { log . dump ( String . format ( "Fatal error on container |%s| destroy:" , appName ) , t ) ; } }


Input:
SECURITY CONTEXT INTERFACE [CODESPLIT] @ Override public boolean login ( String username , String password ) { try { getHttpServletRequest ( ) . login ( username , password ) ; } catch ( ServletException e ) { // exception is thrown if request is already authenticated, servlet container authentication is not enabled or
 // credentials are not accepted
 // consider all these conditions as login fail but record the event to application logger
 log . debug ( e ) ; return false ; } return true ; }


Input: Get HTTP request from current request context . [CODESPLIT] private HttpServletRequest getHttpServletRequest ( ) { RequestContext context = getInstance ( RequestContext . class ) ; HttpServletRequest request = context . getRequest ( ) ; if ( request == null ) { throw new BugError ( "Attempt to use not initialized HTTP request." ) ; } return request ; }


Input:
Invocation handler implementation . Every method invocation on managed class interface is routed to this point . Here actual container services are implemented and method is invoked against wrapped instance . [CODESPLIT] @ Override public Object invoke ( Object proxy , Method method , Object [ ] args ) throws Throwable { final ManagedMethodSPI managedMethod = managedClass . getManagedMethod ( method ) ; log . trace ( "Invoke |%s|." , managedMethod ) ; if ( ! managedMethod . isTransactional ( ) ) { // execute managed method that is not included within transactional boundaries
 try { return managedMethod . invoke ( managedInstance , args ) ; } catch ( Throwable t ) { throw throwable ( t , "Non transactional method |%s| invocation fails." , managedMethod ) ; } } if ( managedMethod . isImmutable ( ) ) { return executeImmutableTransaction ( managedMethod , args ) ; } return executeMutableTransaction ( managedMethod , args ) ; }