Difference between revisions of "Facade"

From CDOT Wiki
Jump to: navigation, search
 
(16 intermediate revisions by the same user not shown)
Line 2: Line 2:
  
 
== Facade Pattern ==
 
== Facade Pattern ==
The Facade Pattern is used to consolidate numerous complicated objects and function calls in a single interface.
+
The Facade Pattern is used to consolidate numerous complicated objects and function calls in a single interface. It does not necessarily encapsulate the objects behind the facade, as it commonly allows the  client to work directly with the object.
 +
 
 +
A facade is like a house. Someone walking by the house sees the exterior and knows the functionality contained within the house (shelter, kitchen, bathroom, bedrooms, etc), but does not know how they are set up or laid out (ie implemented).  The person walking by can approach the house and interact with its functionality through the front door, which is the single point of access to that which is contained within the house (ie sub-system).
  
 
== UML Example ==
 
== UML Example ==
 +
<center>[[Image:FacadeDesignPattern.png]]</center><br/>
 +
[http://en.wikipedia.org/wiki/Image:FacadeDesignPattern.png|Wikipedia, used under GNU FDL]
  
 
== Code Examples ==
 
== Code Examples ==
  
 
=== Java ===
 
=== Java ===
 +
[http://www.fluffycat.com/Java-Design-Patterns/Facade/|Java Design Patterns Facade]
 +
<pre>
 +
public class FacadeCuppaMaker { 
 +
  boolean teaBagIsSteeped;
 +
   
 +
  public FacadeCuppaMaker() {
 +
      System.out.println(
 +
        "FacadeCuppaMaker ready to make you a cuppa!");
 +
  }
 +
 
 +
  public FacadeTeaCup makeACuppa() {
 +
      FacadeTeaCup cup = new FacadeTeaCup();
 +
      FacadeTeaBag teaBag = new FacadeTeaBag();
 +
      FacadeWater water = new FacadeWater();
 +
      cup.addFacadeTeaBag(teaBag);
 +
      water.boilFacadeWater();
 +
      cup.addFacadeWater(water);
 +
      cup.steepTeaBag();
 +
      return cup;
 +
  }
 +
}
 +
</pre>
  
=== C++ ===
+
=== PHP5 ===
 +
[http://www.devshed.com/c/a/PHP/Introducing-the-Facade-Pattern-in-PHP-5/2/|DevShed Introducing Facade Pattern in PHP5]
 +
<pre>
 +
// define 'CompressContentFacade' class
 +
class CompressContentFacade{
 +
  public static function stripContent($content){
 +
    // remove new lines from content
 +
    $strippedContent=StripContent::stripString($content);
 +
    // compress content by using GZIP algorithm
 +
    $gzippedContent=GzipContent::compressString
 +
($strippedContent);
 +
    return $gzippedContent;
 +
  }
 +
}
 +
</pre>
  
 
=== C# .NET ===
 
=== C# .NET ===
 +
[http://www.dofactory.com/Patterns/PatternFacade.aspx#_self1|Facade Design Pattern in C# (via Data & Object Factory)]]
 +
<pre> // Facade pattern -- Structural example
 +
 +
using System;
 +
namespace DoFactory.GangOfFour.Facade.Structural
 +
{
 +
// Mainapp test application
 +
class MainApp
 +
  {
 +
    public static void Main()
 +
    {
 +
      Facade facade = new Facade();
 +
      facade.MethodA();
 +
      facade.MethodB();
 +
      // Wait for user
 +
      Console.Read();
 +
    }
 +
  }
 +
  // "Subsystem ClassA"
 +
  class SubSystemOne
 +
  {
 +
    public void MethodOne()
 +
    {
 +
      Console.WriteLine(" SubSystemOne Method");
 +
    }
 +
  }
 +
  // Subsystem ClassB"
 +
  class SubSystemTwo
 +
  {
 +
    public void MethodTwo()
 +
    {
 +
      Console.WriteLine(" SubSystemTwo Method");
 +
    }
 +
  }
 +
  // Subsystem ClassC"
 +
  class SubSystemThree
 +
  {
 +
    public void MethodThree()
 +
    {
 +
      Console.WriteLine(" SubSystemThree Method");
 +
    }
 +
  }
 +
  // Subsystem ClassD"
 +
  class SubSystemFour
 +
  {
 +
    public void MethodFour()
 +
    {
 +
      Console.WriteLine(" SubSystemFour Method");
 +
    }
 +
  }
 +
  // "Facade"
 +
  class Facade
 +
  {
 +
    SubSystemOne one;
 +
    SubSystemTwo two;
 +
    SubSystemThree three;
 +
    SubSystemFour four;
 +
 +
    public Facade()
 +
    {
 +
      one = new SubSystemOne();
 +
      two = new SubSystemTwo();
 +
      three = new SubSystemThree();
 +
      four = new SubSystemFour();
 +
    }
 +
    public void MethodA()
 +
    {
 +
      Console.WriteLine("\nMethodA() ---- ");
 +
      one.MethodOne();
 +
      two.MethodTwo();
 +
      four.MethodFour();
 +
    }
 +
    public void MethodB()
 +
    {
 +
      Console.WriteLine("\nMethodB() ---- ");
 +
      two.MethodTwo();
 +
      three.MethodThree();
 +
    }
 +
  }
 +
}
 +
</pre>
 +
  
=== VB .NET ===
 
  
 
== Open Source Applications ==
 
== Open Source Applications ==
  
 
=== Apache Excalibur ===
 
=== Apache Excalibur ===
[http://www.google.com/codesearch?hl=en&q=+facade+show:1y0Eke5phF0:4pzQJEULGSg:mi9_qGoVUJU&sa=N&cd=3&ct=rc&cs_p=https://svn.apache.org/repos/asf/excalibur/trunk&cs_f=containerkit/logger/src/java/org/apache/avalon/excalibur/logger/Facade.java#a0|Apache
+
[http://www.google.com/codesearch?hl=en&q=+facade+show:1y0Eke5phF0:4pzQJEULGSg:mi9_qGoVUJU&sa=N&cd=3&ct=rc&cs_p=https://svn.apache.org/repos/asf/excalibur/trunk&cs_f=containerkit/logger/src/java/org/apache/avalon/excalibur/logger/Facade.java#a0|Apache Excalibur Facade Class Code (via Google! Code Search) ]
Excalibur Facade Class Code (via Google! Code Search) ]
 
 
<pre>
 
<pre>
 
/**
 
/**
Line 87: Line 207:
  
 
=== Apache Tomcat ===
 
=== Apache Tomcat ===
 +
[http://www.google.com/codesearch?hl=en&q=show:hGyxCO8zbbo:dtgwsf4Jsds:mEr-jpM3hx4&sa=N&ct=rd&cs_p=http://download.nextag.com/apache/tomcat/tomcat-5/v5.5.17/src/apache-tomcat-5.5.17-src.tar.gz&cs_f=apache-tomcat-5.5.17-src/connectors/coyote/src/java/org/apache/coyote/tomcat4/CoyoteRequestFacade.java|Apache Excalibur Facade Class Code (via Google! Code Search)]<br/>
  
[http://www.google.com/codesearch?hl=en&q=show:hGyxCO8zbbo:dtgwsf4Jsds:mEr-jpM3hx4&sa=N&ct=rd&cs_p=http://download.nextag.com/apache/tomcat/tomcat-5/v5.5.17/src/apache-tomcat-5.5.17-src.tar.gz&cs_f=apache-tomcat-5.5.17-src/connectors/coyote/src/java/org/apache/coyote/tomcat4/CoyoteRequestFacade.java|Apache <pre>/*
+
<p>Serves to wrap the ServeltRequest object</p>
 +
<pre>/*
 
  *  Copyright 1999-2004 The Apache Software Foundation
 
  *  Copyright 1999-2004 The Apache Software Foundation
 
  *
 
  *
Line 96: Line 218:
 
  *
 
  *
 
  *      http://www.apache.org/licenses/LICENSE-2.0
 
  *      http://www.apache.org/licenses/LICENSE-2.0
*
 
*  Unless required by applicable law or agreed to in writing, software
 
*  distributed under the License is distributed on an "AS IS" BASIS,
 
*  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 
*  See the License for the specific language governing permissions and
 
*  limitations under the License.
 
 
  */
 
  */
  
Line 308: Line 424:
 
}
 
}
 
</pre>
 
</pre>
 
  
 
== Links ==
 
== Links ==
Line 318: Line 433:
 
[http://www.google.com/codesearch?hl=en&q=show:hGyxCO8zbbo:dtgwsf4Jsds:mEr-jpM3hx4&sa=N&ct=rd&cs_p=http://download.nextag.com/apache/tomcat/tomcat-5/v5.5.17/src/apache-tomcat-5.5.17-src.tar.gz&cs_f=apache-tomcat-5.5.17-src/connectors/coyote/src/java/org/apache/coyote/tomcat4/CoyoteRequestFacade.java|Apache Tomcat CoyoteRequestFacade Class Code (via Google! Code Search)]<br/>
 
[http://www.google.com/codesearch?hl=en&q=show:hGyxCO8zbbo:dtgwsf4Jsds:mEr-jpM3hx4&sa=N&ct=rd&cs_p=http://download.nextag.com/apache/tomcat/tomcat-5/v5.5.17/src/apache-tomcat-5.5.17-src.tar.gz&cs_f=apache-tomcat-5.5.17-src/connectors/coyote/src/java/org/apache/coyote/tomcat4/CoyoteRequestFacade.java|Apache Tomcat CoyoteRequestFacade Class Code (via Google! Code Search)]<br/>
 
[http://www.dofactory.com/Patterns/PatternFacade.aspx#_self1|Facade Design Pattern in C# and VB.NET]
 
[http://www.dofactory.com/Patterns/PatternFacade.aspx#_self1|Facade Design Pattern in C# and VB.NET]
 +
[http://www.devshed.com/c/a/PHP/Introducing-the-Facade-Pattern-in-PHP-5/2/|DevShed Introducing Facade Pattern in PHP5]
 +
[http://www.fluffycat.com/Java-Design-Patterns/Facade/|Java Design Patterns Facade]

Latest revision as of 11:38, 19 March 2007

Facade Pattern

The Facade Pattern is used to consolidate numerous complicated objects and function calls in a single interface. It does not necessarily encapsulate the objects behind the facade, as it commonly allows the client to work directly with the object.

A facade is like a house. Someone walking by the house sees the exterior and knows the functionality contained within the house (shelter, kitchen, bathroom, bedrooms, etc), but does not know how they are set up or laid out (ie implemented). The person walking by can approach the house and interact with its functionality through the front door, which is the single point of access to that which is contained within the house (ie sub-system).

UML Example

FacadeDesignPattern.png

used under GNU FDL

Code Examples

Java

Design Patterns Facade

public class FacadeCuppaMaker {  
   boolean teaBagIsSteeped; 
    
   public FacadeCuppaMaker() {
       System.out.println(
         "FacadeCuppaMaker ready to make you a cuppa!");
   }
   
   public FacadeTeaCup makeACuppa() {
       FacadeTeaCup cup = new FacadeTeaCup();
       FacadeTeaBag teaBag = new FacadeTeaBag();
       FacadeWater water = new FacadeWater();
       cup.addFacadeTeaBag(teaBag);
       water.boilFacadeWater();
       cup.addFacadeWater(water);
       cup.steepTeaBag();
       return cup;
   }
}

PHP5

Introducing Facade Pattern in PHP5

// define 'CompressContentFacade' class
class CompressContentFacade{
   public static function stripContent($content){
     // remove new lines from content
     $strippedContent=StripContent::stripString($content);
     // compress content by using GZIP algorithm
     $gzippedContent=GzipContent::compressString
($strippedContent);
     return $gzippedContent;
   }
}

C# .NET

Design Pattern in C# (via Data & Object Factory)]

 // Facade pattern -- Structural example

using System;
namespace DoFactory.GangOfFour.Facade.Structural
{
// Mainapp test application
class MainApp
  {
    public static void Main()
    {
      Facade facade = new Facade();
      facade.MethodA();
      facade.MethodB();
      // Wait for user
      Console.Read();
    }
  }
  // "Subsystem ClassA"
  class SubSystemOne
  {
    public void MethodOne()
    {
      Console.WriteLine(" SubSystemOne Method");
    }
  }
  // Subsystem ClassB"
  class SubSystemTwo
  {
    public void MethodTwo()
    {
      Console.WriteLine(" SubSystemTwo Method");
    }
  }
  // Subsystem ClassC"
  class SubSystemThree
  {
    public void MethodThree()
    {
      Console.WriteLine(" SubSystemThree Method");
    }
  }
  // Subsystem ClassD"
  class SubSystemFour
  {
    public void MethodFour()
    {
      Console.WriteLine(" SubSystemFour Method");
    }
  }
  // "Facade"
  class Facade
  {
    SubSystemOne one;
    SubSystemTwo two;
    SubSystemThree three;
    SubSystemFour four;

    public Facade()
    {
      one = new SubSystemOne();
      two = new SubSystemTwo();
      three = new SubSystemThree();
      four = new SubSystemFour();
    }
    public void MethodA()
    {
      Console.WriteLine("\nMethodA() ---- ");
      one.MethodOne();
      two.MethodTwo();
      four.MethodFour();
    }
    public void MethodB()
    {
      Console.WriteLine("\nMethodB() ---- ");
      two.MethodTwo();
      three.MethodThree();
    }
  }
}


Open Source Applications

Apache Excalibur

Excalibur Facade Class Code (via Google! Code Search)

/**
 * A facade to the modularized *LoggerManager building system.
 * Add methods here to create LoggerManagers to your preference.
 *
 * @author <a href="mailto:dev@nospamavalon.apache.org">Avalon Development Team</a>
 * @version CVS $Revision: 1.3 $ $Date: 2004/03/10 13:54:50 $
 * @since 4.0
 */

public class Facade
{
    /**
     * Assemble a new LoggerManager running on top of LogKit
     * configured from a configuration file logging to a supplied
     * logger as a fallback.
     * Use this method as a sample showing how to assemble your
     * own LoggerManager running on top of LogKit flavour.
     */
    public static LoggerManager createLogKitConfigurable(
            final String prefix, final String switchTo )
    {
        final org.apache.log.Hierarchy hierarchy = new Hierarchy();

        final LoggerManager bare = new LogKitAdapter( hierarchy );
        final LoggerManager decorated = applyDecorators( bare, prefix, switchTo );
        final LoggerManagerTee tee = new LoggerManagerTee( decorated );

        tee.addTee( new LogKitLoggerHelper( hierarchy ) );
        tee.addTee( new LogKitConfHelper( hierarchy ) );
        tee.makeReadOnly();

        return tee;
    }

    /**
     * Assemble LoggerManager for Log4J system configured
     * via a configuration file. All the logging errors
     * will go to System.err however.
     */
    public static LoggerManager createLog4JConfigurable(
            final String prefix, final String switchTo )
    {
        final LoggerManager bare = new Log4JConfAdapter();
        final LoggerManager decorated = applyDecorators( bare, prefix, switchTo );
        return decorated;
    }

    private static LoggerManager applyDecorators( LoggerManager target,
            final String prefix, final String switchTo )
    {
        if ( switchTo != null )
        {
            target = new LogToSelfDecorator( target, switchTo );
        }
        if ( prefix != null && prefix.length() > 0 )
        {
            target = new PrefixDecorator( target, prefix );
        }
        target = new CachingDecorator( target );
        return target;
    }
}

Apache Tomcat

Excalibur Facade Class Code (via Google! Code Search)

Serves to wrap the ServeltRequest object

/*
 *  Copyright 1999-2004 The Apache Software Foundation
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 */

package org.apache.coyote.tomcat4;

import java.io.BufferedReader;
import java.io.IOException;
import java.util.Enumeration;
import java.util.Locale;
import java.util.Map;
import javax.servlet.RequestDispatcher;
import javax.servlet.ServletInputStream;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import org.apache.catalina.connector.RequestFacade;

/**
 * Facade class that wraps a Coyote request object.
 * All methods are delegated to the wrapped request.
 *
 * @author Craig R. McClanahan
 * @author Remy Maucherat
 * @version $Revision: 299222 $ $Date: 2004-02-24 04:02:18 -0500 (Tue, 24 Feb 2004) $
 */

public class CoyoteRequestFacade
    extends RequestFacade
    implements HttpServletRequest {
    // ----------------------------------------------------------- Constructors
    /**
     * Construct a wrapper for the specified request.
     * @param request The request to be wrapped
     */
    public CoyoteRequestFacade(CoyoteRequest request) {
        super(request);
        this.request = request;
    }
    // ----------------------------------------------------- Instance Variables
    /**
     * The wrapped request.
     */
    protected CoyoteRequest request = null;
    // --------------------------------------------------------- Public Methods
    /**
     * Clear facade.
     */
    public void clear() {
        request = null;
    }
    // ------------------------------------------------- ServletRequest Methods
    public Object getAttribute(String name) {
        return request.getAttribute(name);
    }
    public Enumeration getAttributeNames() {
        return request.getAttributeNames();
    }
    public String getCharacterEncoding() {
        return request.getCharacterEncoding();
    }
    public void setCharacterEncoding(String env)
        throws java.io.UnsupportedEncodingException {
        request.setCharacterEncoding(env);
    }
    public int getContentLength() {
        return request.getContentLength();
    }
    public String getContentType() {
        return request.getContentType();
    }
    public ServletInputStream getInputStream()
        throws IOException {
        return request.getInputStream();
    }
    public String getParameter(String name) {
        return request.getParameter(name);
    }
    public Enumeration getParameterNames() {
        return request.getParameterNames();
    }
    public String[] getParameterValues(String name) {
        return request.getParameterValues(name);
    }
    public Map getParameterMap() {
        return request.getParameterMap();
    }
    public String getProtocol() {
        return request.getProtocol();
    }
    public String getScheme() {
        return request.getScheme();
    }
    public String getServerName() {
        return request.getServerName();
    }
    public int getServerPort() {
        return request.getServerPort();
    }
    public BufferedReader getReader()
        throws IOException {
        return request.getReader();
    }
    public String getRemoteAddr() {
        return request.getRemoteAddr();
    }
    public String getRemoteHost() {
        return request.getRemoteHost();
    }
    public void setAttribute(String name, Object o) {
        request.setAttribute(name, o);
    }
    public void removeAttribute(String name) {
        request.removeAttribute(name);
    }
    public Locale getLocale() {
        return request.getLocale();
    }
    public Enumeration getLocales() {
        return request.getLocales();
    }
    public boolean isSecure() {
        return request.isSecure();
    }
    public RequestDispatcher getRequestDispatcher(String path) {
        // TODO : Facade !!
        return request.getRequestDispatcher(path);
    }
    public String getRealPath(String path) {
        return request.getRealPath(path);
    }
    public String getAuthType() {
        return request.getAuthType();
    }
    public Cookie[] getCookies() {
        return request.getCookies();
    }
    public long getDateHeader(String name) {
        return request.getDateHeader(name);
    }
    public String getHeader(String name) {
        return request.getHeader(name);
    }
    public Enumeration getHeaders(String name) {
        return request.getHeaders(name);
    }
    public Enumeration getHeaderNames() {
        return request.getHeaderNames();
    }
    public int getIntHeader(String name) {
        return request.getIntHeader(name);
    }
    public String getMethod() {
        return request.getMethod();
    }
    public String getPathInfo() {
        return request.getPathInfo();
    }
    public String getPathTranslated() {
        return request.getPathTranslated();
    }
    public String getContextPath() {
        return request.getContextPath();
    }
    public String getQueryString() {
        return request.getQueryString();
    }
    public String getRemoteUser() {
        return request.getRemoteUser();
    }
    public boolean isUserInRole(String role) {
        return request.isUserInRole(role);
    }
    public java.security.Principal getUserPrincipal() {
        return request.getUserPrincipal();
    }
    public String getRequestedSessionId() {
        return request.getRequestedSessionId();
    }
    public String getRequestURI() {
        return request.getRequestURI();
    }
    public StringBuffer getRequestURL() {
        return request.getRequestURL();
    }
    public String getServletPath() {
        return request.getServletPath();
    }
    public HttpSession getSession(boolean create) {
        return request.getSession(create);
    }
    public HttpSession getSession() {
        return getSession(true);
    }
    public boolean isRequestedSessionIdValid() {
        return request.isRequestedSessionIdValid();
    }
    public boolean isRequestedSessionIdFromCookie() {
        return request.isRequestedSessionIdFromCookie();
    }
    public boolean isRequestedSessionIdFromURL() {
        return request.isRequestedSessionIdFromURL();
    }
    public boolean isRequestedSessionIdFromUrl() {
        return request.isRequestedSessionIdFromURL();
    }
}

Links

BTP 600 Class Entry
Wikipedia Entry on Facade Pattern
Excalibur Project Site
Excalibur Facade Class Code (via Google! Code Search)
Tomcat Project Site
Tomcat CoyoteRequestFacade Class Code (via Google! Code Search)
Design Pattern in C# and VB.NET Introducing Facade Pattern in PHP5 Design Patterns Facade