Search icon CANCEL
Subscription
0
Cart icon
Your Cart (0 item)
Close icon
You have no products in your basket yet
Save more on your purchases! discount-offer-chevron-icon
Savings automatically calculated. No voucher code required.
Arrow left icon
Explore Products
Best Sellers
New Releases
Books
Events
Videos
Audiobooks
Packt Hub
Free Learning
Arrow right icon
timer SALE ENDS IN
0 Days
:
00 Hours
:
00 Minutes
:
00 Seconds

How-To Tutorials

7019 Articles
article-image-drupal-and-ubercart-2x-new-approach-drupal-theming
Packt
31 Mar 2010
3 min read
Save for later

Drupal and Ubercart 2.x: A new Approach to Drupal Theming

Packt
31 Mar 2010
3 min read
Fusion Theming System with Skinr module At the end of this article, we're going to give you a brief reference to the Fusion Theming System. It was introduced only a few months ago and it's still under heavy development. It's a base theme, meaning that you can create your own subthemes easily, using the Fusion Starter, a commented starter theme created especially for this reason. It uses a 960px or fluid 16-column grid, and its main advantage is that, with the help of Skinr module, it creates l ayout and style confi guration options that the site administrator can control using the website's User Interface, without messing with CSS. So, let's see how to install it, and how to use it for simple customizations. First navigate to http://drupal.org/project/skinr, and right after you download the module, upload and unzip to your site folder (/sites/all/modules). Then, activate the module from Administration | Site building | Modules. Navigate to http://drupal.org/project/fusion, and right after you download the theme, upload it and unzip it to your site folder (/sites/all/themes). Then, go to Administration | Site building | Themes, enable both Fusion Core and Fusion Starter themes and set the Fusion Starter theme as the default one. Browse to admin | build | themes | settings | fusion_starter to configure the settings of Fusion Starter theme. There you will find the default settings of every Drupal theme, such as logo image settings or shortcut icon settings. However, there is also a new section, named Fusion theme settings. There, you can easily change the basic styles and the layout of your theme, such as font family, font size, fixed or fluid layout without using any CSS at all. Click on Save configuration to store your settings. Now, if you hover the cursor over any block of your site, you will see a new icon. Clicking on it allows you to configure the properties of this block. You can change the width of the block, the block position, the content alignment, and apply custom styles to the elements of the block, such as padding, border, equal heights, or multi-column menus. There are also special settings for every content type. For example, if you go to Administer | Content Management | Content Types | Product, you will see two new sections, named Skinr node settings and Skinr comment settings, where you can apply custom styles to the product page and the product comments. If you want to create your own custom styles for your theme, and present them in the User Interface, you have to study the documentation of the Skinr module, available at http://www.drupal.org/node/578574.
Read more
  • 0
  • 0
  • 4042

article-image-drupal-and-ubercart-2x-creating-theme-scratch-using-zen-theme
Packt
31 Mar 2010
4 min read
Save for later

Drupal and Ubercart 2.x: Creating a Theme from Scratch Using the Zen Theme

Packt
31 Mar 2010
4 min read
In the previous article, we showed you the easy way to install and customize a ready-made theme. This solution is good enough for many shop owners, but if you want to use a unique design for your store, the only solution is to build a theme from scratch. We are going to use the Zen Theme, ma ybe the most popular theme for Drupal. Zen is actually not just a simple theme, but rather a theming framework, because it allows the creation of subthemes. Using a subtheme, we can use all of the great code of Zen and apply only our design customizations, using some simple tools and writing only a few lines of code. So, don't be afraid but enjoy the process. Just think how proud you'll feel when you will have finished your amazing frontend for your store. You don't have to be a programming Ninja, all you have to know is some HTML and CSS. If you have no programming experience at all, you can follow some very interesting tutorials at http://www.w3schools.com/. The tools We are going to use some simple and free tools, which are easy to download, install, and use. Some of them are extensions for Firefox, so if you are not using this particular browser, you have to download it first from http://www.getfirefox.com. Firebug This is the first extension for Firefox that we are going to use. It's an open source and free tool for editing, debugging, and monitoring HTML, CSS, and JavaScript in our web pages. Using Firebug, you can understand the structure of an Ubercart page and inspect and edit HTML and CSS on the fly. To install it, go to http://getfirebug.com/, skip the terrifying bug, and click on Install Firebug for Firefox. You will be transferred to the Firefox add-ons page. Click on Add to Firefox. A new window opens with a warning about possible malicious software. It's a common warning when you try to install a Firefox extension, so click on Install now. When the download is completed, click on Restart Firefox. When Firefox restarts, Firebug is enabled. You can activate it by clicking on the little bug icon at the bottom-right corner of the window. When Firebug is activated, it splits the browser window into two parts. The top part is the normal page and the bottom part shows the HTML or CSS code of the whole page, or for a selected element. There, you can inspect or edit the code, make tests, and try different alternatives. It is now possible to use Firebug in Internet Explorer, Opera, or Safari, using Firebug Lite. It's a small JavaScript file and you can download it from http://getfirebug.com/lite.html. ColorZilla ColorZilla is also a Firefox extension. It provides useful tools related to color management, such as eyedropper, color picker, or palette viewer. You can download it from http://www.colorzilla.com/firefox/. Click on Install ColorZilla. A new window opens with a warning about possible malicious software, like we saw in the Firebug installation, so click on Install now and then Restart Firefox. When Firefox restarts, ColorZilla is enabled. You can activate it by clicking on the little eyedropper icon at the bottom left corner of the window. A code editor We need it to write and edit our template and CSS files. There are many freeware applications, such as HTML Kit (http://www.chami.com/html-kit/) and Webocton (http://scriptly.webocton.de/9/34/start/englishpage.html), or commercial applications, such as Ultraedit (http://www.ultraedit.com) or Coda (http://www.panic.com/coda/).
Read more
  • 0
  • 0
  • 1837

article-image-installing-coherence-35-and-accessing-data-grid-part-1
Packt
31 Mar 2010
10 min read
Save for later

Installing Coherence 3.5 and Accessing the Data Grid: Part 1

Packt
31 Mar 2010
10 min read
When I first started evaluating Coherence, one of my biggest concerns was how easy it would be to set up and use, especially in a development environment. The whole idea of having to set up a cluster scared me quite a bit, as any other solution I had encountered up to that point that had the word "cluster" in it was extremely difficult and time consuming to configure. My fear was completely unfounded—getting the Coherence cluster up and running is as easy as starting Tomcat. You can start multiple Coherence nodes on a single physical machine, and they will seamlessly form a cluster. Actually, it is easier than starting Tomcat. Installing Coherence In order to install Coherence you need to download the latest release from the Oracle Technology Network (OTN) website. The easiest way to do so is by following the link from the main Coherence page on OTN. At the time of this writing, this page was located at http://www.oracle.com/technology/products/coherence/index.html, but that might change. If it does, you can find its new location by searching for 'Oracle Coherence' using your favorite search engine. In order to download Coherence for evaluation, you will need to have an Oracle Technology Network (OTN) account. If you don't have one, registration is easy and completely free. Once you are logged in, you will be able to access the Coherence download page, where you will find the download links for all available Coherence releases: one for Java, one for .NET, and one for each of the supported C++ platforms. You can download any of the Coherence releases you are interested in while you are there, but for the remainder of this article you will only need the first one. The latter two (.NET and C++) are client libraries that allow .NET and C++ applications to access the Coherence data grid. Coherence ships as a single ZIP archive. Once you unpack it you should see the README.txt file containing the full product name and version number, and a single directory named coherence. Copy the contents of the coherence directory to a location of your choice on your hard drive. The common location on Windows is c:coherence and on Unix/Linux /opt/coherence, but you are free to put it wherever you want. The last thing you need to do is to configure the environment variable COHERENCE_HOME to point to the top-level Coherence directory created in the previous step, and you are done. Coherence is a Java application, so you also need to ensure that you have the Java SDK 1.4.2 or later installed and that JAVA_HOME environment variable is properly set to point to the Java SDK installation directory. If you are using a JVM other than Sun's, you might need to edit the scripts used in the following section. For example, not all JVMs support the -server option that is used while starting the Coherence nodes, so you might need to remove it. What's in the box? The first thing you should do after installing Coherence is become familiar with the structure of the Coherence installation directory. There are four subdirectories within the Coherence home directory: bin: This contains a number of useful batch files for Windows and shell scripts for Unix/Linux that can be used to start Coherence nodes or to perform various network tests doc: This contains the Coherence API documentation, as well as links to online copies of Release Notes, User Guide, and Frequently Asked Questions documents examples: This contains several basic examples of Coherence functionality lib: This contains JAR files that implement Coherence functionality Shell scripts on UnixIf you are on a Unix-based system, you will need to add execute permission to the shell scripts in the bin directory by executing the following command: $ chmod u+x *.sh Starting up the Coherence cluster In order to get the Coherence cluster up and running, you need to start one or more Coherence nodes. The Coherence nodes can run on a single physical machine, or on many physical machines that are on the same network. The latter will definitely be the case for a production deployment, but for development purposes you will likely want to limit the cluster to a single desktop or laptop. The easiest way to start a Coherence node is to run cache-server.cmd batch file on Windows or cache-server.sh shell script on Unix. The end result in either case should be similar to the following screenshot: There is quite a bit of information on this screen, and over time you will become familiar with each section. For now, notice two things: At the very top of the screen, you can see the information about the Coherence version that you are using, as well as the specific edition and the mode that the node is running in. Notice that by default you are using the most powerful, Grid Edition, in development mode. The MasterMemberSet section towards the bottom lists all members of the cluster and provides some useful information about the current and the oldest member of the cluster. Now that we have a single Coherence node running, let's start another one by running the cache-server script in a different terminal window. For the most part, the output should be very similar to the previous screen, but if everything has gone according to the plan, the MasterMemberSet section should reflect the fact that the second node has joined the cluster: MasterMemberSet ( ThisMember=Member(Id=2, ...) OldestMember=Member(Id=1, ...) ActualMemberSet=MemberSet(Size=2, BitSetCount=2 Member(Id=1, ...) Member(Id=2, ...) )RecycleMillis=120000RecycleSet=MemberSet(Size=0, BitSetCount=0)) You should also see several log messages on the first node's console, letting you know that another node has joined the cluster and that some of the distributed cache partitions were transferred to it. If you can see these log messages on the first node, as well as two members within the ActualMemberSet on the second node, congratulations—you have a working Coherence cluster. Troubleshooting cluster start-up In some cases, a Coherence node will not be able to start or to join the cluster. In general, the reason for this could be all kinds of networking-related issues, but in practice a few issues are responsible for the vast majority of problems. Multicast issues By far the most common issue is that multicast is disabled on the machine. By default, Coherence uses multicast for its cluster join protocol, and it will not be able to form the cluster unless it is enabled. You can easily check if multicast is enabled and working properly by running the multicast-test shell script within the bin directory. If you are unable to start the cluster on a single machine, you can execute the following command from your Coherence home directory: $ . bin/multicast-test.sh –ttl 0 This will limit time-to-live of multicast packets to the local machine and allow you to test multicast in isolation. If everything is working properly, you should see a result similar to the following: Starting test on ip=Aleks-Mac-Pro.home/192.168.1.7,group=/237.0.0.1:9000, ttl=0Configuring multicast socket...Starting listener...Fri Aug 07 13:44:44 EDT 2009: Sent packet 1.Fri Aug 07 13:44:44 EDT 2009: Received test packet 1 from selfFri Aug 07 13:44:46 EDT 2009: Sent packet 2.Fri Aug 07 13:44:46 EDT 2009: Received test packet 2 from selfFri Aug 07 13:44:48 EDT 2009: Sent packet 3.Fri Aug 07 13:44:48 EDT 2009: Received test packet 3 from self If the output is different from the above, it is likely that multicast is not working properly or is disabled on your machine. This is frequently the result of a firewall or VPN software running, so the first troubleshooting step would be to disable such software and retry. If you determine that was indeed the cause of the problem you have two options. The first, and obvious one, is to turn the offending software off while using Coherence. However, for various reasons that might not be an acceptable solution, in which case you will need to change the default Coherence behavior, and tell it to use the Well-Known Addresses (WKA) feature instead of multicast for the cluster join protocol. Doing so on a development machine is very simple—all you need to do is add the following argument to the JAVA_OPTS variable within the cache-server shell script: -Dtangosol.coherence.wka=localhost With that in place, you should be able to start Coherence nodes even if multicastis disabled. Localhost and loopback addressOn some systems, localhost maps to a loopback address, 127.0.0.1. If that's the case, you will have to specify the actual IP address or host name for the tangosol.coherence.wka configuration parameter. The host name should be preferred, as the IP address can change as you move from network to network, or if your machine leases an IP address from a DHCP server. As a side note, you can tell whether the WKA or multicast is being used for the cluster join protocol by looking at the section above the MasterMemberSet section when the Coherence node starts. If multicast is used, you will see something similar to the following: Group{Address=224.3.5.1, Port=35461, TTL=4} The actual multicast group address and port depend on the Coherence version being used. As a matter of fact, you can even tell the exact version and the build number from the preceding information. In this particular case, I am using Coherence 3.5.1 release, build 461. This is done in order to prevent accidental joins of cluster members into an existing cluster. For example, you wouldn't want a node in the development environment using newer version of Coherence that you are evaluating to join the existing production cluster, which could easily happen if the multicast group address remained the same. On the other hand, if you are using WKA, you should see output similar to the following instead: WellKnownAddressList(Size=1, WKA{Address=192.168.1.7, Port=8088} ) Using the WKA feature completely disables multicast in a Coherence cluster, and is recommended for most production deployments, primarily due to the fact that many production environments prohibit multicast traffic altogether, and that some network switches do not route multicast traffic properly. That said, configuring WKA for production clusters is out of the scope of this article, and you should refer to Coherence product manuals for details. Binding issues Another issue that sometimes comes up is that one of the ports that Coherence attempts to bind to is already in use and you see a bind exception when attempting to start the node. By default, Coherence starts the first node on port 8088, and increments port number by one for each subsequent node on the same machine. If for some reason that doesn't work for you, you need to identify a range of available ports for as many nodes as you are planning to start (both UDP and TCP ports with the same numbers must be available), and tell Coherence which port to use for the first node by specifying the tangosol.coherence.localport system property. For example, if you want Coherence to use port 9100 for the first node, you will need to add the following argument to the JAVA_OPTS variable in the cache-server shell script: -Dtangosol.coherence.localport=9100
Read more
  • 0
  • 0
  • 4114

article-image-installation-and-configuration-microsoft-content-management-server-part-1
Packt
31 Mar 2010
10 min read
Save for later

Installation And Configuration of Microsoft Content Management Server: Part 1

Packt
31 Mar 2010
10 min read
In this first article of the series we walk you through the installation and configuration of MCMS 2002 Service Pack 2 (SP2), along with SQL Server 2005 and Visual Studio 2005 on a single developer workstation. In addition, we will cover the changes to the SP2 development environment and a number of tips for working within it. This article assumes you are already familiar with the steps necessary to install MCMS 2002 SP1a as detailed in depth in the previous book, Building Websites with Microsoft Content Management Server from Packt Publishing, January 2005 (ISBN 1-904811-16-7). There are two approaches to setting up a development environment for SP2: upgrading from a previous SP1a installation, or starting from scratch and building a fresh installation including SP2. We will cover both approaches in this article. For example, we will be using Windows XP Professional SP2 as our development workstation. However, where there are significant differences for a Windows Server 2003 SP1 machine, those will be noted. All examples assume the logged-on user is a local machine administrator. Overview of MCMS 2002 Service Pack 2 As with other Microsoft Service Packs, one major purpose of SP2 is to provide an integrated installation for a large number of previously released hotfixes. SP2 will now be a prerequisite for any future hotfix releases. While many customers will view SP2 as a regular Service Pack, it also offers support for the latest development platform and tools from Microsoft, namely SQL Server 2005, .NET Framework 2.0 and ASP.NET 2.0, and Visual Studio 2005: SQL Server 2005: MCMS databases can be hosted by SQL Server 2005, offering numerous advantages in security, deployment, and most significantly, performance. .NET Framework 2.0 and ASP.NET 2.0: MCMS applications can be hosted within the .NET Framework 2.0 runtime, and take advantage of v2.0 language features as well as security and performance improvements. In addition, many of the new features of ASP.NET 2.0 such as master pages, themes, navigation, and Membership Providers can be used. This provides numerous opportunities to both refine and refactor MCMS applications, and is the primary focus. Visual Studio 2005: MCMS applications can be developed using Visual Studio 2005. One of the greatest advantages here is the use of the new HTML-editing and designer features in VS.NET along with improved developer productivity. If you wish, you can continue to use SQL Server 2000 for your MCMS applications. However, we recommend upgrading to SQL Server 2005 and will use it throughout the examples in this book. There are numerous versions or Stock Keeping Units (SKUs) of Visual Studio 2005, all of which are supported with SP2. Throughout the examples in this book, we will be using Visual Studio 2005 Professional Edition. Unfortunately, SP2 is not a cumulative service pack and therefore requires an existing installation of SP1a. Likewise, there is no slipstreamed distribution of SP2. The SP2 distribution is suitable for all editions of MCMS. Mainly due to the extremely fast preparation and release of SP2 following the Release to Manufacturing (RTM) of .NET 2.0, Visual Studio 2005, and SQL Server 2005, the Microsoft installation information (KB906145) isn’t particularly well documented and is somewhat confusing. Rest assured that the guidance in this article has been verified and tested for both installation scenarios covered. Obtaining MCMS Service Pack 2 MCMS SP2 can be downloaded from the following locations: English:http://www.microsoft.com/downloads/details.aspx?FamilyId=3DE1E8F0-D660-4A2B-8B14-0FCE961E56FB&displaylang=en French:http://www.microsoft.com/downloads/details.aspx?FamilyId=3DE1E8F0-D660-4A2B-8B14-0FCE961E56FB&displaylang=fr German:http://www.microsoft.com/downloads/details.aspx?FamilyId=3DE1E8F0-D660-4A2B-8B14-0FCE961E56FB&displaylang=de Japanese:http://www.microsoft.com/downloads/details.aspx?FamilyId=3DE1E8F0-D660-4A2B-8B14-0FCE961E56FB&displaylang=ja Installation Approach We cover both an in-place upgrade to SP2 and a fresh installation in this chapter. Which approach you take is down to your specific requirements and your current, if any, MCMS installation. If you wish to perform a fresh install, skip ahead to the Fresh Installation of Microsoft Content Management Server 2002 Service Pack 2 section, later in this article Upgrading to Microsoft Content Management Server 2002 Service Pack 2 This section details the steps required to upgrade an existing installation of MCMS SP1a, which includes the Developer Tools for Visual Studio.NET 2003 component. The outline process for an upgrade is as follows: Install Visual Studio 2005. Install MCMS 2002 Service Pack 2. Configure the development environment. (Optional) Prepare the MCMS database for SQL Server 2005. (Optional) Upgrade SQL Server. (Optional) Install SQL Server 2005 Service Pack 1. We will perform all steps while logged on as a local machine administrator. Installing Visual Studio 2005 Visual Studio 2005 can be installed side by side with Visual Studio.NET 2003. Once we have completed the upgrade, we can remove Visual Studio.NET 2003 if we wish to only develop MCMS applications using SP2 and ASP.NET 2.0. Insert the Visual Studio 2005 DVD, and on the splash screen, click Install Visual Studio 2005. On the Welcome to the Microsoft Visual Studio 2005 installation wizard page, click Next. On the Start Page, select the I accept the terms of the License Agreement checkbox, enter your Product Key and Name, and click Next. On the Options Page, select the Custom radio button, enter your desired Product install path, and click Next. On the second Options page, select the Visual C# and Visual Web Developer checkboxes within the Language Tools section, and the Tools checkbox within the .NET Framework SDK section. Click Install. Feel free to install any additional features you may wish to use. The above selections are all that’s required to follow the examples in this book. Wait (or take a coffee break) while Visual Studio 2005 is installed. When the Finish Page appears, click Finish. From the Visual Studio 2005 Setup dialog, you can choose to install the Product Documentation (MSDN Library) if desired. From the Visual Studio 2005 Setup dialog, click Check for Visual Studio Service Releases to install any updates that may be available. Click Exit. Installing MCMS 2002 Service Pack 2 Next, we will install MCMS Service Pack 2. From the Start Menu, click Run. In the Open textbox, enter IISRESET /STOP and click OK. Wait while the IIS Services are stopped. Double-click the SP2 installation package. On the Welcome to Microsoft Content Management Server 2002 SP2 Installation Wizard page, click Next. Select the I accept the terms of this license agreement radio button, and click Next. On the ready to begin the installation page, click Next. Wait while Service Pack 2 is installed. During installation you may be prompted for the MCMS 2002 SP1a CD-ROM. Once The Installation Wizard has completed page, click Finish. If prompted, click Yes on the dialog to restart your computer, which will complete the installation. Otherwise, from the Start Menu, click Run. In the Open textbox, enter IISRESET /START and click OK to restart the IIS services. Stopping IIS prior to the installation of SP2 avoids potential problems with replacing locked files during the installation, and can prevent the requirement to reboot. Configuring the Development Environment Before continuing, a few additional steps are required to configure the development environment. We will: Configure the shortcut that opens Site Manager to bypass the Connect To dialog. Install the MCMS website and item templates in Visual Studio. Site Manager Shortcut During the installation of SP2 the Site Manager Start-menu shortcut will be overwritten. To configure Site Manager to bypass the Connect To dialog, take the following steps: Select Start | All Programs | Microsoft Content Management Server. Right-click the Site Manager shortcut and click Properties. In the Target textbox, replace"C:Program FilesMicrosoft Content Management ServerClientNRClient.exe" http:///NR/System/ClientUI/login.aspwith"C:Program FilesMicrosoft Content Management ServerClientNRClient.exe" http://localhost/NR/System/ClientUI/login.asp. Click OK. It is possible to configure many different Site Manager shortcuts pointing to different MCMS entry points. However, for this book we will only use the entry point on localhost, which is the only supported configuration for MCMS development. Visual Studio Templates The installation of MCMS Service Pack 2 automatically registers the MCMS developer tools such as MCMS Template Explorer in Visual Studio 2005. However, before we can create MCMS applications with Visual Studio, we need to make the website and item templates available. Select Start | All Programs | Microsoft Visual Studio 2005 | Visual Studio Tools | Visual Studio 2005 Command Prompt. Execute the following commands, replacing MCMS_INSTALL_PATH with the install location of MCMS (usually C:Program FilesMicrosoft Content Management Server) and PATH_TO_MY_DOCUMENTS_FOLDER with the location of your My Documents folder: xcopy "MCMS_INSTALL_PATHDevToolsNewProjectWizards80Visual WebDeveloper" "PATH_TO_MY_DOCUMENTS_FOLDERVisual Studio 2005TemplatesProjectTemplatesVisual Web Developer"/E xcopy "MCMS_INSTALL_PATHDevToolsNewItemWizards80Visual WebDeveloper" "PATH_TO_MY_DOCUMENTS_FOLDERVisual Studio 2005TemplatesItemTemplatesVisual Web Developer"/E Execute the following command to register the templates with VisualStudio 2005: devenv /setup Close the command prompt. This completes the steps to upgrade to SP2, and our environment is now ready for development! We can test our installation by viewing the version number in the SCA, connecting with Site Manager, or by using the Web Author. Of course, any existing MCMS web applications will at this time still be hosted by.NET Framework v1.1. It is not necessary at this stage to register ASP.NET as detailed in the Microsoft Installation Instructions (KB 906145). This registration was performed by the Visual Studio 2005 installer. Additionally it is unnecessary to configure IIS to use ASP.NET 2.0 using the Internet Information Services Snap-In, as Visual Studio 2005 automatically sets this option on each MCMS website application created.However, if you are installing on Windows Server 2003, you must configure the Virtual Website root and the MCMS Virtual Directory to use ASP.NET 2.0, as it is not possible to use two versions of ASP.NET within the same Application Pool. The ActiveX controls that are part of HtmlPlaceholderControl are updated with SP2. Therefore you will be prompted to install this control when first switching to edit mode.If you have pre-installed the controls using regsvr32 or Group Policy as detailed at http://download.microsoft.com/download/4/2/5/4250f79a-c3a1-4003-9272-2404e92bb76a/MCMS+2002+-+(complete)+FAQ.htm#51C0CE4B-FC57-454C-BAAE-12C09421B57B, you might also be prompted, and you will need to update your distribution for the controls. At this stage you can also choose to upgrade SQL Server or move forward. Preparing the MCMS Database for SQL Server 2005 Before upgrading our SQL Server installation to SQL Server 2005, we need to prepare the MCMS database so that it is compatible with SQL Server 2005. Request the following MCMS hotfix from Microsoft:http://support.microsoft.com/?kbid=913401. Run the hotfix executable to extract the files to a local folder, e.g. c:913401. Copy both of the files (_dca.ini and _sp1aTosp2upgrade.sql) to the MCMS SQL install folder (typically c:Program FilesMicrosoft Content Management ServerServerSetup FilesSQL Install). Overwrite the existing files. Delete the temporary folder. Select Start | Microsoft Content Management Server | Data Configuration Application. On the splash screen, click Next. In the Stop Service? dialog, click Yes. On the Select MCMS Database page, click Next. In the Upgrade Required dialog, click Yes. On the Upgrade Database page, click Next. In the Add an Administrator dialog, click No. On the Database Configuration Application page, uncheck the Launch the SCA Now checkbox and click Finish.
Read more
  • 0
  • 0
  • 2364

article-image-documentation-phpdocumentor-part-2
Packt
31 Mar 2010
9 min read
Save for later

Documentation with phpDocumentor: Part 2

Packt
31 Mar 2010
9 min read
Documentation without DocBlocks You have probably already noticed that short of some inline comments, the sample project has no DocBlocks, tags, or anything else added by the programmer for the purpose of documenting the code. Nevertheless, there is quite a bit that phpDocumentor can do with uncommented PHP code. If we are in the directory containing the project directory, we can run phpDocumentor and ask to generate documentation for the project like this: The above command will recursively process all files in the project directory (--directory ./project/), create documentation with a custom title (--title 'Generated Documentation - No DocBlocks'), include a source code listing of each file processed (--sourcecode on), save all documentation to the docs directory (--target ./project/docs), and group everything under a specified package name (--defaultpackagename 'UserAuthentication'). Listing all documentation pages that phpDocumentor generated is impractical, but let's take a look at the outline and at least one of the classes. All we have to do to view the documentation is to open the index.html file in the docs directory where we told phpDocumentor to direct the output with a web browser. Looking at the above screenshot, we see that phpDocumentor correctly found all the class files. Moreover, it identified Accountable as an interface and found index.php, even though it contains no class definitions. All classes and interfaces are grouped together under the AuthenticationUser package name that was specified from the command line. At the same time, we see some of the shortcomings. There is no further classification or grouping and all components are simply listed under the root level. Before we move on, let's also take a look at what information phpDocumentor was able to extract from the Users.php file: It correctly identified the methods of the class, their visibility, and which parameters are required. I think that is a pretty useful start, albeit the description is a bit sparse and we have no idea what methods were actually implemented using the magic __call() method. Another point to note here is that the class property $accounts does not appear in the documentation at all. That is intended behavior because the property has been declared private. If you want elements with private visibility to appear in your documentation, you will have to add the –pp / --parse private command line option or put this option in a config file. Documentation with DocBlocks Of course, this example wouldn't be complete if we didn't proceed to add proper DocBlocks to our code. The following is the exact same code as before, but this time it has been properly marked up with DocBlocks. File project/classes/Accountable.php: <?php /** * @author Dirk Merkel <dirk@waferthin.com> * @package WebServices * @subpackage Authentication * @copyright Waferthin Web Works LLC * @license http://www.gnu.org/copyleft/gpl.html Freely available under GPL */ /** * <i>Accountable</i> interface for authentication * * Any class that handles user authentication <b>must</b> * implement this interface. It makes it almost * trivial to check whether a user is currently * logged in or not. * * @package WebServices * @subpackage Authentication * @author Dirk Merkel <dirk@waferthin.com> * @version 0.2 * @since r12 */ interface Accountable { const AUTHENTICATION_ERR_MSG = 'There is no user account associated with the current session. Try logging in fist.'; /** * Did the current user log in? * * This method simply answers the question * "Did the current user log in?" * * @access public * @return bool */ public function isLoggedIn(); /** * Returns user account info * * This method is used to retrieve the account corresponding * to a given login. <b>Note:</b> it is not required that * the user be currently logged in. * * @access public * @param string $user user name of the account * @return Account */ public function getAccount($user = ''); } ?> File project/classes/Authentication.php: <?php /** * @author Dirk Merkel <dirk@waferthin.com> * @package WebServices * @subpackage Authentication * @copyright Waferthin Web Works LLC * @license http://www.gnu.org/copyleft/gpl.html Freely available under GPL */ /** * <i>Authentication</i> handles user account info and login actions * * This is an abstract class that serves as a blueprint * for classes implementing authentication using * different account validation schemes. * * @see Authentication_HardcodedAccounts * @author Dirk Merkel <dirk@waferthin.com> * @package WebServices * @subpackage Authentication * @version 0.5 * @since r5 */ abstract class Authentication implements Accountable { /** * Reference to Account object of currently * logged in user. * * @access private * @var Account */ private $account = null; /** * Returns account object if valid. * * @see Accountable::getAccount() * @access public * @param string $user user account login * @return Account user account */ public function getAccount($user = '') { if ($this->account !== null) { return $this->account; } else { return AUTHENTICATION_ERR_MSG; } } /** * isLoggedIn method * * Says whether the current user has provided * valid login credentials. * * @see Accountable::isLoggedIn() * @access public * @return boolean */ public function isLoggedIn() { return ($this->account !== null); } /** * login method * * Abstract method that must be implemented when * sub-classing this class. * * @access public * @return boolean */ abstract public function login($user, $password); } ?> File project/classes/Authentication/HardcodedAccounts.php: <?php /** * @author Dirk Merkel <dirk@waferthin.com> * @package WebServices * @subpackage Authentication * @copyright Waferthin Web Works LLC * @license http://www.gnu.org/copyleft/gpl.html Freely available under GPL */ /** * <i>Authentication_HardcodedAccounts</i> class * * This class implements the login method needed to handle * actual user authentication. It extends <i>Authentication</i> * and implements the <i>Accountable</i> interface. * * @package WebServices * @subpackage Authentication * @see Authentication * @author Dirk Merkel <dirk@waferthin.com> * @version 0.6 * @since r14 */ class Authentication_HardcodedAccounts extends Authentication { /** * Referece to <i>Users</i> object * @access private * @var Users */ private $users; /** * Authentication_HardcodedAccounts constructor * * Instantiates a new {@link Users} object and stores a reference * in the {@link users} property. * * @see Users * @access public * @return void */ public function __construct() { $this->users = new Users(); } /** * login method * * Uses the reference {@link Users} class to handle * user validation. * * @see Users * @todo Decide which validate method to user instead of both * @access public * @param string $user account user name * @param string $password account password * @return boolean */ public function login($user, $password) { if (empty($user) || empty($password)) { return false; } else { // both validation methods should work ... // user static method to validate account $firstValidation = Users::validate($user, $password); // use magic method validate<username>($password) $userLoginFunction = 'validate' . $user; $secondValidation = $this->users- >$userLoginFunction($password); return ($firstValidation && $secondValidation); } } } ?> File project/classes/Users.php: <?php /** * @author Dirk Merkel <dirk@waferthin.com> * @package WebServices * @subpackage Accounts * @copyright Waferthin Web Works LLC * @license http://www.gnu.org/copyleft/gpl.html Freely available under GPL */ /** * <i>Users</i> class * * This class contains a hard-coded list of user accounts * and the corresponding passwords. This is merely a development * stub and should be implemented with some sort of permanent * storage and security. * * @package WebServices * @subpackage Accounts * @see Authentication * @see Authentication_HardcodedAccounts * @author Dirk Merkel <dirk@waferthin.com> * @version 0.6 * @since r15 */ class Users { /** * hard-coded user accounts * * @access private * @static * @var array $accounts user name => password mapping */ private static $accounts = array('dirk' => 'myPass', 'albert' => 'einstein'); /** * static validate method * * Given a user name and password, this method decides * whether the user has a valid account and whether * he/she supplied the correct password. * * @see Authentication_HardcodedAccounts::login() * @access public * @static * @param string $user account user name * @param string $password account password * @return boolean */ public static function validate($user, $password) { return self::$accounts[$user] == $password; } /** * magic __call method * * This method only implements a magic validate method * where the second part of the method name is the user's * account name. * * @see Authentication_HardcodedAccounts::login() * @see validate() * @access public * @method boolean validate<user>() validate<user>(string $password) validate a user * @staticvar array $accounts used to validate users & passwords */ public function __call($name, $arguments) { if (preg_match("/^validate(.*)$/", $name, $matches) && count($arguments) > 0) { return self::validate($matches[1], $arguments[0]); } } } ?> File project/index.php: <?php /** * Bootstrap file * * This is the form handler for the login application. * It expects a user name and password via _POST. If * * @author Dirk Merkel <dirk@waferthin.com> * @package WebServices * @copyright Waferthin Web Works LLC * @license http://www.gnu.org/copyleft/gpl.html Freely available under GPL * @version 0.7 * @since r2 */ /** * required class files and interfaces */ require_once('classes/Accountable.php'); require_once('classes/Authentication.php'); require_once('classes/Users.php'); require_once('classes/Authentication/HardcodedAccounts.php'); $authenticator = new Authentication_HardcodedAccounts(); // uncomment for testing $_POST['user'] = 'dirk'; $_POST['password'] = 'myPass'; if (isset($_POST['user']) && isset($_POST['password'])) { $loginSucceeded = $authenticator->login($_POST['user'], $_POST['password']); if ($loginSucceeded === true) { echo "Congrats - you're in!n"; } else { echo "Uh-uh - try again!n"; } } ?> Since none of the functionality of the code has changed, we can skip that discussion here. What has changed, however, is that we have added DocBlocks for each file, class, interface, method, and property. Whereas the version of the project without documentation had a total of 113 lines of code, the new version including DocBlocks has 327 lines. The number of lines almost tripled! But don't be intimidated. Creating DocBlocks doesn't take nearly as much time as coding. Once you are used to the syntax, it becomes second nature. My estimate is that documenting takes about 10 to 20 percent of the time it takes to code. Moreover, there are tools to really speed things up and help you with the syntax, such as a properly configured code editor or IDE. Now let's see how phpDocumentor fared with the revised version of the project. Here is the index page: This time, the heading shows that we are looking at the Web Services package. Furthermore, the classes and interfaces have been grouped by sub-packages in the left-hand index column. Next, here is the documentation page for the Users class: As you can see, this documentation page is quite a bit more informative than the earlier version. For starters, it has a description of what the class does. Similarly, both methods have a description. All the tags and their content are listed and there are helpful links to other parts of the documentation. And, from the method tag we can actually tell that the magic method __call() was used to implement a method of the form validate<user>($password). That is quite an improvement, I would say! To really appreciate how much more informative and practical the documentation has become by adding DocBlocks, you really need to run through this example yourself and browse through the resulting documentation.
Read more
  • 0
  • 0
  • 1947

article-image-customizing-layout-themes-php-nuke
Packt
31 Mar 2010
23 min read
Save for later

Customizing Layout with Themes in PHP-Nuke

Packt
31 Mar 2010
23 min read
Creating a PHP-Nuke theme gives your site its own special look, distinguishing it from other PHP-Nuke-created sites and offers an effective outlet for your creative talents. Creating a theme requires some knowledge of HTML, confidence in working with CSS and PHP, but most important is some imagination and creativity! Unlike the tasks we have tackled in previous articles, where we have been working exclusively through a web browser to control and configure PHP-Nuke, working with themes is the start of a new era in your PHP-Nuke skills; editing the code files of PHP-Nuke itself. Fortunately, the design of PHP-Nuke means that our theme work won't be tampering with the inner workings of PHP-Nuke. However, becoming confident in handling the mixture of HTML and PHP code that is a PHP-Nuke theme will prepare you for the more advanced work ahead, when we really get to grips with PHP-Nuke at the code level. In this article, we will look at: Theme management Templates in themes Changing the page header Working with the stylesheet Changing blocks Changing the format of stories What Does a Theme Control? Despite the fact that we say 'themes control the look and feel of your site', a theme does not determine every aspect of the page output. PHP-Nuke is an incredibly versatile application, but it cannot produce every website imaginable. Appearance First of all, the appearance of the page can be controlled through the use of colors, fonts, font sizes, weights, and so on. This can either be done through the use of CSS styles or HTML. You can also add JavaScript for fancier effects, or even Flash animations, Java applets, or sounds—anything that you can add to a standard HTML page. Graphical aspects of the page such as the site banner, background images, and so on, are under the care of the theme. There are also some modules that allow their standard graphical icons to be overridden with images from a theme. Page Layout Roughly speaking, a PHP-Nuke page consists of three parts; the top bit, the bit in the middle, and the bit at the bottom! The top bit—the header—usually contains a site logo and such things as a horizontal navigation bar for going directly to important parts of your site. The bottom bit—the footer—contains the copyright message. In between the header and the footer, the output is usually divided into three columns. The left-hand column typically contains blocks, displayed one of top each other, the middle column contains the module output, and the right-hand column contains more blocks. The layout of these columns (their width for example) is controlled by the theme. You may have noticed that the right-hand column is generally only displayed on the homepage of a PHP-Nuke site; this too, is something that is controlled by the theme. The appearance of the blocks is controlled by the theme; PHP-Nuke provides the title of the block and its content, and the theme will generally 'frame' these to produce the familiar block look. The theme also determines how the description of stories appears on the homepage. In addition, the theme determines how the full text of the story, its extended text, is displayed. We've talked about how the theme controls the 'look' of things. The theme also allows you to add other site-related data to your page; for example the name of the site can appear, and the site slogan, and you can even add such things as the user's name with a friendly welcome message. Theme Management Basically, a theme is a folder that sits inside the themes folder in your PHP-Nuke installation. Different themes correspond to different folders in the themes folder, and adding or removing a theme is as straightforward as adding or removing the relevant folder from the themes folder. By default, you will find around 14 themes in a standard PHP-Nuke installation. DeepBlue is the default theme. Themes can be chosen in one of two ways: By the administrator: You can simply select the required theme from the General Site Info panel of the Site Preferences administration menu and save the changes. The theme selected by the administrator is the default theme for the site and will be seen by all users of the site, registered or unregistered. By the user: Users can override the default theme set by the administrator from the Themes option of the Your Account module. This sets a new, personal, theme that will be displayed to that user. Note that this isn't a theme especially customized for that user; it is just one chosen from the list of standard themes installed on your site. Unregistered visitors do not have an option to choose a theme; they have to become registered users. Theme File Structure Let's start with the default theme, DeepBlue. If you open up the DeepBlue folder within the themes folder in the root of your PHP-Nuke installation, you will find three folders and two files. The three folders are: forums: This folder contains the theme for the Forums module. This is not strictly a requirement of a PHP-Nuke theme, and not every PHP-Nuke theme has a forums theme. The Forums module (otherwise known as phpBB) has its own theme 'engine'. The purpose of including a theme for the forums is that you have consistency between the rest of your PHP-Nuke display and the phpBB display. images: This folder contains the image files used by your theme. These include the site logo, background images, and graphics for blocks among others. As mentioned earlier, within this folder can be other folders containing images to override the standard icons. style: This folder contains the CSS files for your theme. Usually, there is one CSS file in the style folder, style.css. Each theme will make use of its style.css file, and this is the file into which we will add our style definitions when the time comes. Of the two files, index.html is simply there to prevent people browsing to your themes folder and seeing what it contains; visiting this page in a browser simply produces a blank page. It is a very simple security measure. The themes.php file is a PHP code file, and is where all the action happens. This file must always exist within a theme folder. We will concentrate on this file later when we customize the theme. In other themes you will find more files; we will look at these later. Installing a New Theme Installing and uninstalling themes comes down to adding or removing folders from the themes folder, and whenever a list of available themes is presented, either in the Site Preferences menu or the Your Accounts module, PHP-Nuke refreshes this list by getting the names of the folders in the themes folder. You will find a huge range of themes on the Web. For example, there is a gallery of themes at: http://nukecops.com/modules.php?set_albumName=packs&op=modload&name=Gallery& file=index&include=view_album.php Many of these are themes written for older versions of PHP-Nuke, but most are still compatible with the newer releases. There is also a live demonstration of some themes at: http://www.portedmods.com/styles/ On this page you can select the new theme and see it applied immediately, before you download it. Removing an Existing Theme To remove a theme from your PHP-Nuke site you simply remove the corresponding folder from the themes folder, and it will no longer be available to PHP-Nuke. However, you should be careful when removing themes—what if somebody is actually using that theme? If a user has that theme selected as their personal theme, and you remove that theme, then that user's personal theme will revert to the default theme selected in Site Preferences. If you remove the site's default theme, then you will break your site! Deleting the site's default theme will produce either a blank screen or messages like the following when you attempt to view your site. Warning: head(themes/NonExistentTheme/theme.php)[function.head]: failed to create stream:No such file or directory in c:nukehtmlheader.php on line 31 The only people who can continue to use your site in this situation are those who have selected a personal theme for themselves—and only if that theme is still installed. To correct such a faux pas, make a copy of one of the other themes in your themes folder (unless you happen to have a copy of the theme you just deleted elsewhere), and rename it to the name of the theme you just deleted. In conclusion, removing themes should only be a problem if you somehow manage to remove your site's default theme. For users who have selected the theme you just removed, their theme will revert to the default theme and life goes on for them. A final caveat about the names of theme folders; do not use spaces in the names of the folders in the themes folder—this can lead to strange behavior when the list of themes is displayed in the drop-down menus for users to select from. From an Existing Theme to a New Theme We'll create a new theme for the Dinosaur Portal by making changes to an existing theme. This will not only make you feel like the theme master, but it will also serve to illustrate the nature of the theme-customization problem. We'll be making changes all over the place—adding and replacing things in HTML and PHP files—but it will be worth it. Another thing to bear in mind is that we're creating a completely different looking site without making any changes to the inner parts of PHP-Nuke. At this point, all we are changing is the theme definition. The theme for the Dinosaur Portal will have a warm, tropical feel to it to evoke the atmosphere of a steaming, tropical, prehistoric jungle, and will use lots of orange color on the page. First of all, we need a theme on which to conduct our experiments. We'll work on the 3D-Fantasy theme. Starting Off The first thing we will do is to create a new theme folder, which will be a copy of the 3D-Fantasy theme. Open up the themes folder in your file explorer, and create a copy of the 3D-Fantasy folder. Rename this copy as TheDinosaurPortal. Now log into your site as testuser, and from the Your Account module, select TheDinosaurPortal as the theme. Your site will immediately switch to this theme, but it will look exactly like 3D-Fantasy, because, at the moment, it is! You will also need some images from the code download for this article; you will find them in the SiteImages folder of this article's code. Replacing Traces of the Old Theme The theme that we are about to work on has many occurrences of 3D-Fantasy in a number of files, such as references to images. We will have to remove these first of all, or else our new theme will be looking in the wrong folder for images and other resources. Open each of the files below in your text editor, and replace every occurrence of 3D-Fantasy with TheDinosaurPortal in a text editor, we'll use Wordpad. "You can use the replace functionality of your editor to do this. For example, in Wordpad, select Edit | Replace; enter the text to be replaced, and then click on Replace All to replace all the occurrences in the open file. After making all the changes, save each file: blocks.html footer.html header.html story_home.html story_page.html theme.php tables.php Templates and PHP Files We've just encountered two types of file in the theme folder—PHP code files (theme.php and tables.php) and HTML files (blocks.html, footer.html, and so on). Before we go any further, we need to have a quick discussion of what roles these types of file play in the theme construction. PHP Files The PHP files do the main work of the theme. These files contain the definitions of some functions that handle the display of the page header and how an individual block or article is formatted, among other tasks. These functions are called from other parts of PHP-Nuke when required. We'll talk about them when they are required later in the article. Part of our customization work will be to make some changes to these functions and have them act in a different way when called. Historically, the code for a PHP-Nuke theme consisted of a single PHP file, theme.php. One major drawback of this was the difficulty you would have in editing this file in the 'design' view of an HTML editor. Instead of seeing the HTML that you wished to edit, you probably wouldn't see anything in the 'design' view of most HTML editors, since the HTML was inextricably intertwined with the PHP code. This made creating a new theme, or even editing an existing theme, not something for the faint-hearted—you had to be confident with your PHP coding to make sure you were changing the right places, and in the right way. The theme.php file consists of a number of functions that are called from other parts of PHP-Nuke when required. These functions are how the theme does its work. One of the neat appearances in recent versions of PHP-Nuke is the use of a 'mini-templating' engine for themes. Not all themes make use of this method (DeepBlue is one theme that doesn't), and that is one of the reasons we are working with 3D-Fantasy as our base theme, since it does follow the 'templating' model. Templates The HTML files that we modified above are the theme templates. They consist of HTML, without any PHP code. Each template is responsible for a particular part of the page, and is called into action by the functions of the theme when required. One advantage of using these templates is that they can be easily edited in visual HTML editors, such as Macromedia's Dreamweaver, without any PHP code to interfere with the page design. Another advantage of using these templates is to separate logic from presentation. The idea of a template is that it should determine how something is displayed (its presentation). The template makes use of some data supplied to it, but acquiring and choosing this data (the logic) is not done in the template. The template is processed or evaluated by the 'template engine', and output is generated. The template engine in this case is the theme.php file. To see how the template and PHP-Nuke 'communicate', let's look at an extract from the header.html file in the 3D-Fantasy folder: <a href="index.php"> <img src="themes/3D-Fantasy/images/logo.gif" border="0" alt="Welcome to $sitename" align="left"></a> The $sitename text (shown highlighted) is an example of what we'll call a placeholder. There is a correspondence between these placeholders and PHP variables that have the same name as the placeholder text. Themes that make use of this templating process more or less replace any text beginning with $ in the template by the value of the corresponding PHP variable. This means that you can make use of variables from PHP-Nuke itself in your themes; these could be the name of your site ($sitename), your site slogan, or even information about the user. In fact, you can add your own PHP code to create a new variable, which you can then display from within one of the templates. To complete the discussion, we will look at how the templates are processed in PHP-Nuke. The code below is a snippet from one of the themeheader() function in the theme.php file. This particular snippet is taken from the 3D-Fantasy theme. function themeheader(){ global $user, $banners, $sitename, $slogan, $cookie, $prefix, $anonymous, $db;... code continues ....$tmpl_file = "themes/3D-Fantasy/header.html";$thefile = implode("", file($tmpl_file));$thefile = addslashes($thefile);$thefile = "$r_file="".$thefile."";";eval($thefile);print $r_file;... code continues .... The processing starts with the line where the $tmpl_file variable is defined. This variable is set to the file name of the template to be processed, in this case header.html. The next line grabs the content of the file as a string. Let's suppose the header.html file contained the text You're welcomed to $sitename, thanks for coming!. Then, continuing in the code above, the $thefile variable would eventually hold this: $r_file = " You're welcomed to $sitename, thanks for coming!"; This looks very much like a PHP statement, and that is exactly what PHP-Nuke is attempting to create. The eval() function executes the statement; it defines the variable $r_file as above. This is equivalent to putting this line straight into the code: $r_file = " You're welcomed to $sitename, thanks for coming!"; If this line were in the PHP code, the value of the $sitename variable will be inserted into the string, and this is exactly how the placeholders in the templates are replaced with the values of the corresponding PHP variables. This means that the placeholders in templates can only use variables accessible at the point in the code where the template is processed with the eval() function. This means any parameters passed to the function at the time—global variables that have been announced with the global statement or any variables local to the function that have been defined before the line with the eval() function. This does mean that you will have to study the function processing the template to see what variables are available. In the examples in this article we'll look at the most relevant variables. The templates do not allow for any form of 'computation' within them; you cannot use loops or call PHP functions. You do your computations 'outside' the template in the theme.php file, and the results are 'pulled' into the template and displayed from there. Now that we're familiar with what we're going to be working with, let's get started. Changing the Page Header The first port of call will be creating a new version of the page header. We will make these customizations: Changing the site logo graphic Changing the layout of the page header Adding a welcome message to the user, and displaying the user's avatar Adding a drop-down list of topics to the header Creating a navigation bar Time For Action—Changing the Site Logo Graphic Grab the <>ilogo.gif file from the SiteImages folder in the code download. Copy it to the themes/TheDinosaurPortal/images folder, overwriting the existing logo.gif file. Refresh the page in your browser. The logo will have changed! What Just Happened? The logo.gif file in the images folder is the site logo. We replaced it with a new banner, and immediately the change came into effect. Time For Action—Changing the Site Header Layout In the theme folder is a file called header.html. Open up this file in a text editor, we'll use Wordpad. Replace all the code in this file with the following: <!-- Time For Action—Changing the Site Header Layout --><table border="0" cellspacing="0" cellpadding="6" width="100%" bgcolor="#FFCC33"> <tr valign="middle"> <td width="60%" align="right" rowspan="2"> <a href="index.php"><img src="themes/$GLOBALS[ThemeSel]/images/logo.gif" border="1" alt="Welcome to $sitename"> </a></td> <td width="40%" colspan="2"> <p align="center"><b>WELCOME TO $sitename!</b></td> </tr> <tr> <td width="20%">GAP</td> <td width="20%">GAP</td> </tr></table><!-- End of Time for Action -->$public_msg<br><table cellpadding="0" cellspacing="0" width="99%" border="0" align="center" bgcolor="#ffffff"><tr><td bgcolor="#ffffff" valign="top"> Save the header.html file. Refresh your browser. The site header now looks like this: What Just Happened? The header.html file is the template responsible for formatting the site header. Changing this file will change the format of your site header. We simply created a table that displays the site logo in the left-hand column, a welcome message in the right-hand column, and under that, two GAPs that we will add more to in a moment. We set the background color of the table to an orange color (#FFCC33). We used the $sitename placeholder to display the name of the site from the template. Note that everything after the line: <!-- End of Time for Action --> in our new header.html file is from the original file. (The characters here denote an HTML comment that is not displayed in the browser). This is because the end of the header.html file starts a new table that will continue in other templates. If we had removed these lines, the page output would have been broken. There was another interesting thing we used in the template, the $GLOBALS[ThemeSel] placeholder: <a href="index.php"><img src="themes/$GLOBALS[ThemeSel]/images/logo.gif" ThemeSel is a global variable that holds the name of the current theme—it's either the default site theme or the user's chosen theme. Although it's a global variable, using just $ThemeSel in the template would give a blank, this is because it has not been declared as global by the function in PHP-Nuke that consumes the header.html template. However, all the global variables can be accessed through the $GLOBALS array, and using $GLOBALS[ThemeSel] accesses this particular global variable. Note that this syntax is different from the way you may usually access elements of the $GLOBALS array in PHP. You might use $GLOBALS['ThemeSel'] or $GLOBALS["ThemeSel"]. Neither of these work in the template so we have to use the form without the ' or ". Time For Action—Fixing and Adding the Topics List Next we'll add the list of topics as a drop-down box to the page header. The visitor will be able to select one of the topics from the box, and then the list of stories from that topic will be displayed to them through the News module. Also, the current topic will be selected in the drop-down box to avoid confusion. This task involves fixing some bugs in the current version of the 3D-Fantasy theme. First of all, open the theme.php file and find the following line in the themeheader() function definition: $topics_list = "<select name="topic" onChange='submit()'>n"; Replace this line with these two lines: global $new_topic;$topics_list = "<select name="new_topic" onChange='submit()'>n"; If you move a few lines down in the themeheader() function, you will find this line: if ($topicid==$topic) { $sel = "selected "; } Replace $topic with $new_topic in this line to get: if ($topicid==$new_topic) { $sel = "selected "; } Save the theme.php file. Open the header.html file in your text editor, and where the second GAP is, make the modifications as shown below: <td width="20%">GAP</td> <td width="20%"><form action="modules.php?name=News&new_topic" method="post"> Select a Topic:<br>$topics_list</select></form></td></tr></table><!-- End of Time for Action --> Save the header.html file. Refresh your browser. You will see the new drop-down box in your page header: What just Happened? The themeheader() function is the function in theme.php responsible for processing the header.html template, and outputting the page header. The $topics_list variable has already been created for us in the themeheader() function, and can be used from the header.html template. It is a string of HTML that defines an HTML select drop-down list consisting of the topic titles. However, the first few steps require us to make a change to the $topics_list variable, correcting the name of the select element and also using the correct variable to ensure the current topic (if any) is selected in the drop-down box. The select element needs to have the name of new_topic, so that the News module is able to identify which topic we're after. This is all done with the changes to the theme.php file. First, we add the global statement to access the $new_topic variable, before correcting the name of the select element: global $new_topic;$topics_list = "<select name="new_topic" onChange='submit()'>n"; The next change we made is to make sure we are looking for the $new_topic variable, not the $topic variable, which isn't even defined: if ($topicid==$new_topic) { $sel = "selected "; } Now the $topics_list variable is corrected, all we have to do is add a placeholder for this variable to the header.html template, and some more HTML around it. We added the placeholder for $topics_list to display the drop-down list, and a message to go with it encouraging the reader to select a topic into one of the GAP table cells we created in the new-look header. The list of topics will be contained in a form tag, and when the user selects a topic, the form will be posted back to the server to the News module, and the stories in the selected topic will be displayed. (The extra HTML that handles submitting the form is contained with the $topics_list variable.) <form action="modules.php?name=News" method="post">Select a Topic:<br>$topics_list All that remains now is to close the select tag—the tag was opened in the $topics_list variable but not closed—and then close the form tag: </select></form> When the page is displayed, this is the HTML that PHP-Nuke produces for the topics drop-down list: <form action="modules.php?name=News&new_topic" method="post">Select a Topic:<br><select name="topic" onChange='submit()'><option value="">All Topics</option><option value="1">The Dinosaur Portal</option><option value="2">Dinosuar Hunting</option></select></form>
Read more
  • 0
  • 0
  • 6792
Unlock access to the largest independent learning library in Tech for FREE!
Get unlimited access to 7500+ expert-authored eBooks and video courses covering every tech area you can think of.
Renews at €18.99/month. Cancel anytime
article-image-installing-coherence-35-and-accessing-data-grid-part-2
Packt
31 Mar 2010
10 min read
Save for later

Installing Coherence 3.5 and Accessing the Data Grid: Part 2

Packt
31 Mar 2010
10 min read
Using the Coherence API One of the great things about Coherence is that it has a very simple and intuitive API that hides most of the complexity that is happening behind the scenes to distribute your objects. If you know how to use a standard Map interface in Java, you already know how to perform basic tasks with Coherence. In this section, we will first cover the basics by looking at some of the foundational interfaces and classes in Coherence. We will then proceed to do something more interesting by implementing a simple tool that allows us to load data into Coherence from CSV files, which will become very useful during testing. The basics: NamedCache and CacheFactory As I have briefly mentioned earlier, Coherence revolves around the concept of named caches. Each named cache can be configured differently, and it will typically be used to store objects of a particular type. For example, if you need to store employees, trade orders, portfolio positions, or shopping carts in the grid, each of those types will likely map to a separate named cache. The first thing you need to do in your code when working with Coherence is to obtain a reference to a named cache you want to work with. In order to do this, you need to use the CacheFactory class, which exposes the getCache method as one of its public members. For example, if you wanted to get a reference to the countries cache that we created and used in the console example, you would do the following: NamedCache countries = CacheFactory.getCache("countries"); Once you have a reference to a named cache, you can use it to put data into that cache or to retrieve data from it. Doing so is as simple as doing gets and puts on a standard Java Map: countries.put("SRB", "Serbia");String countryName = (String) countries.get("SRB"); As a matter of fact, NamedCache is an interface that extends Java's Map interface, so you will be immediately familiar not only with get and put methods, but also with other methods from the Map interface, such as clear, remove, putAll, size, and so on. The nicest thing about the Coherence API is that it works in exactly the same way, regardless of the cache topology you use. For now let's just say that you can configure Coherence to replicate or partition your data across the grid. The difference between the two is that in the former case all of your data exists on each node in the grid, while in the latter only 1/n of the data exists on each individual node, where n is the number of nodes in the grid. Regardless of how your data is stored physically within the grid, the NamedCache interface provides a standard API that allows you to access it. This makes it very simple to change cache topology during development if you realize that a different topology would be a better fit, without having to modify a single line in your code. In addition to the Map interface, NamedCache extends a number of lower-level Coherence interfaces. The following table provides a quick overview of these interfaces and the functionality they provide: The "Hello World" example In this section we will implement a complete example that achieves programmatically what we have done earlier using Coherence console—we'll put a few countries in the cache, list cache contents, remove items, and so on. To make things more interesting, instead of using country names as cache values, we will use proper objects this time. That means that we need a class to represent a country, so let's start there: public class Country implements Serializable, Comparable {private String code;private String name;private String capital;private String currencySymbol;private String currencyName;public Country() {}public Country(String code, String name, String capital,String currencySymbol, String currencyName) {this.code = code;this.name = name;this.capital = capital;this.currencySymbol = currencySymbol;this.currencyName = currencyName;}public String getCode() {return code;}public void setCode(String code) {this.code = code;}public String getName() {return name;}public void setName(String name) {this.name = name;}public String getCapital() {return capital;}public void setCapital(String capital) {this.capital = capital;}public String getCurrencySymbol() {return currencySymbol;}public void setCurrencySymbol(String currencySymbol) {this.currencySymbol = currencySymbol;}public String getCurrencyName() {return currencyName;}public void setCurrencyName(String currencyName) {this.currencyName = currencyName;}public String toString() {return "Country(" +"Code = " + code + ", " +"Name = " + name + ", " +"Capital = " + capital + ", " +"CurrencySymbol = " + currencySymbol + ", " +"CurrencyName = " + currencyName + ")";}public int compareTo(Object o) {Country other = (Country) o;return name.compareTo(other.name);}} There are several things to note about the Country class, which also apply to other classes that you want to store in Coherence: Because the objects needs to be moved across the network, classes that are stored within the data grid need to be serializable. In this case we have opted for the simplest solution and made the class implement the java.io.Serializable interface. This is not optimal, both from performance and memory utilization perspective, and Coherence provides several more suitable approaches to serialization. We have implemented the toString method that prints out an object's state in a friendly format. While this is not a Coherence requirement, implementing toString properly for both keys and values that you put into the cache will help a lot when debugging, so you should get into a habit of implementing it for your own classes. Finally, we have also implemented the Comparable interface. This is also not a requirement, but it will come in handy in a moment to allow us to print out a list of countries sorted by name. Now that we have the class that represents the values we want to cache, it is time to write an example that uses it: import com.tangosol.net.NamedCache;import com.tangosol.net.CacheFactory;import ch02.Country;import java.util.Set;import java.util.Map;public class CoherenceHelloWorld {public static void main(String[] args) {NamedCache countries = CacheFactory.getCache("countries");// first, we need to put some countries into the cachecountries.put("USA", new Country("USA", "United States","Washington", "USD", "Dollar"));countries.put("GBR", new Country("GBR", "United Kingdom","London", "GBP", "Pound"));countries.put("RUS", new Country("RUS", "Russia", "Moscow","RUB", "Ruble"));countries.put("CHN", new Country("CHN", "China", "Beijing","CNY", "Yuan"));countries.put("JPN", new Country("JPN", "Japan", "Tokyo","JPY", "Yen"));countries.put("DEU", new Country("DEU", "Germany", "Berlin","EUR", "Euro"));countries.put("FRA", new Country("FRA", "France", "Paris","EUR", "Euro"));countries.put("ITA", new Country("ITA", "Italy", "Rome","EUR", "Euro"));countries.put("SRB", new Country("SRB", "Serbia", "Belgrade","RSD", "Dinar"));assert countries.containsKey("JPN"): "Japan is not in the cache";// get and print a single countrySystem.out.println("get(SRB) = " + countries.get("SRB"));// remove Italy from the cacheint size = countries.size();System.out.println("remove(ITA) = " + countries.remove("ITA"));assert countries.size() == size - 1: "Italy was not removed";// list all cache entriesSet<Map.Entry> entries = countries.entrySet(null, null);for (Map.Entry entry : entries) {System.out.println(entry.getKey() + " = " + entry.getValue());}}} Let's go through this code section by section. At the very top, you can see import statements for NamedCache and CacheFactory, which are the only Coherence classes we need for this simple example. We have also imported our Country class, as well as Java's standard Map and Set interfaces. The first thing we need to do within the main method is to obtain a reference to the countries cache using the CacheFactory.getCache method. Once we have the cache reference, we can add some countries to it using the same old Map.put method you are familiar with. We then proceed to get a single object from the cache using the Map.get method , and to remove one using Map.remove. Notice that the NamedCache implementation fully complies with the Map.remove contract and returns the removed object. Finally, we list all the countries by iterating over the set returned by the entrySet method. Notice that Coherence cache entries implement the standard Map.Entry interface. Overall, if it wasn't for a few minor differences, it would be impossible to tell whether the preceding code uses Coherence or any of the standard Map implementations. The first telltale sign is the call to the CacheFactory.getCache at the very beginning, and the second one is the call to entrySet method with two null arguments. We have already discussed the former, but where did the latter come from? The answer is that Coherence QueryMap interface extends Java Map by adding methods that allow you to filter and sort the entry set. The first argument in our example is an instance of Coherence Filter interface. In this case, we want all the entries, so we simply pass null as a filter. The second argument, however, is more interesting in this particular example. It represents the java.util.Comparator that should be used to sort the results. If the values stored in the cache implement the Comparable interface, you can pass null instead of the actual Comparator instance as this argument, in which case the results will be sorted using their natural ordering (as defined by Comparable.compareTo implementation). That means that when you run the previous example, you should see the following output: get(SRB) = Country(Code = SRB, Name = Serbia, Capital = Belgrade,CurrencySymbol = RSD, CurrencyName = Dinar)remove(ITA) = Country(Code = ITA, Name = Italy, Capital = Rome,CurrencySymbol = EUR, CurrencyName = Euro)CHN = Country(Code = CHN, Name = China, Capital = Beijing, CurrencySymbol= CNY, CurrencyName = Yuan)FRA = Country(Code = FRA, Name = France, Capital = Paris, CurrencySymbol= EUR, CurrencyName = Euro)DEU = Country(Code = DEU, Name = Germany, Capital = Berlin,CurrencySymbol = EUR, CurrencyName = Euro)JPN = Country(Code = JPN, Name = Japan, Capital = Tokyo, CurrencySymbol =JPY, CurrencyName = Yen)RUS = Country(Code = RUS, Name = Russia, Capital = Moscow, CurrencySymbol= RUB, CurrencyName = Ruble)SRB = Country(Code = SRB, Name = Serbia, Capital = Belgrade,CurrencySymbol = RSD, CurrencyName = Dinar)GBR = Country(Code = GBR, Name = United Kingdom, Capital = London,CurrencySymbol = GBP, CurrencyName = Pound)USA = Country(Code = USA, Name = United States, Capital = Washington,CurrencySymbol = USD, CurrencyName = Dollar) As you can see, the countries in the list are sorted by name, as defined by our Country.compareTo implementation. Feel free to experiment by passing a custom Comparator as the second argument to the entrySet method, or by removing both arguments, and see how that affects result ordering. If you are feeling really adventurous and can't wait to learn about Coherence queries, take a sneak peek by changing the line that returns the entry set to: Set<Map.Entry> entries = countries.entrySet(new LikeFilter("getName", "United%"), null); As a final note, you might have also noticed that I used Java assertions in the previous example to check that the reality matches my expectations (well, more to demonstrate a few other methods in the API, but that's beyond the point). Make sure that you specify the -ea JVM argument when running the example if you want the assertions to be enabled, or use the run-helloworld target in the included Ant build file, which configures everything properly for you. That concludes the implementation of our first Coherence application. One thing you might notice is that the CoherenceHelloWorld application will run just fine even if you don't have any Coherence nodes started, and you might be wondering how that is possible. The truth is that there is one Coherence node—the CoherenceHelloWorld application. As soon as the CacheFactory.getCache method gets invoked, Coherence services will start within the application's JVM and it will either join the existing cluster or create a new one, if there are no other nodes on the network. If you don't believe me, look at the log messages printed by the application and you will see that this is indeed the case. Now that you know the basics, let's move on and build something slightly more exciting, and much more useful.
Read more
  • 0
  • 0
  • 1809

article-image-interactive-page-regions-drupal-6-part-1
Packt
31 Mar 2010
9 min read
Save for later

Interactive Page Regions with Drupal 6: Part 1

Packt
31 Mar 2010
9 min read
Lots to do—let's get started! Activity 3-1–Configuring the contact subsystem Navigate to the Contact form admin page (admin/build/contact) and click Add category. The Contact module is installed with Drupal, but is disabled by default. This step requires that the Contact module be enabled. The Contact form will open. The information that we need to provide in it is a title in the Category field, an e-mail address in the Recipients field to which the contact e-mails should be sent. We've made a contact form available. Normally, the form would be shown on a page of its own, but we need the form to be shown in a view, and will eventually point our menu choice to the view instead of the normal contact page. The contact form isn't a node, feed, or any of the typical constituents of a view. So, how do we bring it into one? There are different approaches, but the easiest will be to use another add-on module: Content form blocks. We'll navigate to its administration page under Settings (admin/settings/contact_form_blocks). This step requires that the Contact form blocks module be installed. This step requires that the Contact form blocks module be installed. Information about this module can be found at http://drupal.org/project/contact_form_blocks. The Contact module allows you to create categories of contact, such as feedback to the administrator, contact between users, and so on. On this site, the only contact that will be enabled is from users to the site owner. There's not a whole lot to configure here, since we only have one category of contact configured, but this is where you select which contact category will be available as a form inside a block. The following screenshot shows this configuration form ready to be saved. Having saved that information, the module will have created a block for our use in the contact-us view. Go to the list of blocks (admin/build/block) and see. Remember to scroll down to the Disabled section of the list to find the block, because it's not been assigned to a region yet. Because we named the contact category General, the block will be called Contact form: General. We want to assign the block to appear in the content area of our page, but the theme we are working with has not exposed Content as a region for our use. Let's change that. In the directory sites/all/themes/acquia_slate is the file acquia_slate.info. Edit it. There is no mandatory order within a theme's .info file, but they are small enough that you should be able to find what you need at a glance. Look for a group of lines that each begin with the word 'regions,' as shown below: regions[sidebar_first] = sidebar firstregions[sidebar_last] = sidebar lastregions[banner] = bannerregions[header_top] = header topregions[header_first] = header firstregions[header_middle] = header middleregions[header_bottom] = header bottomregions[preface_sidebar] = front preface sidebarregions[content_top] = inner content topregions[content_bottom] = content bottomregions[postscript_first] = postscript firstregions[postscript_middle] = postscript middleregions[postscript_last] = postscript lastregions[footer] = footerregions[node_bottom] = node bottom Each of those lines defines a region to which blocks can be assigned. We need to add one. Between the regions [content_top] and regions [content_bottom] lines insert the following: regions[content] = content Save the file, and then go to the Performance page (admin/settings/performance) and click the Clear cache button. Return to the blocks page and assign the Contact block to the Content region, as shown in the following screenshot, so that it will appear along with our View content. We need to configure the block, otherwise it will appear along with every piece of content on the site. We'll click configure, and set the block to appear only on a specific page, as shown in the following screenshot. We'll need to provide the path of that page, but it doesn't exist yet. Luckily, the block administration does not validate the path. Since we'll have to do it at some point anyway, we'll create a name for our eventual view, contact-us, and use it here. With the contact form now being hooked into a block, and the block configured to show in a single view, we need to create that view so that we can see the contact form. Activity 3-2–Creating the contact-us view The contact-us view we're going to create is simply going to be the glue for our pieces. By using a content type to provide contact information on the page, the site owner can easily have different versions of the page to use at different times of the year (like Google does on their home page) simply by creating a new node of the Location content type and having the desired one enabled. The view will make use of that content. Go to the views page (admin/build/views) click Add, and choose to create a Node view. At this point, we're not interested in configuring the view to provide any content. In fact, what we want to do is prevent it from showing content. The reason is that the block we created, which will contain the contact form, will appear in the content region of the page showing this view. We don't need any other content at this point. However, we cannot save this view as it is, because, by default, the Row style is set to Fields, and we have no fields selected. So, click on Row style and change it to Node. Having changed the Row style to Node will allow us get past the problem of not having defined any fields, and will allow us to save the view. However, that setting without any filters in place will cause the view to select every node, whereas we want it to select none, for now. There is no filter choice for Null display, but we can accomplish the equivalent easily. Select the filter Post date and set it to a date for which we know there are no posts. Lastly, we want to create a Page display and assign a path to it, so that we can access the view. Name it contact-us. The view is ready to save. The panel settings are shown in the following screenshot. With our skeletal view saved, navigate to its path (contact-us) and get a first look at the current contact form, as shown in the following screenshot: The location information isn't displayed at this time, because we have not yet created that content. The important thing here is the contact form. The site owner wants to capture when someone completes the form, which would not be available given only the form's current fields, namely Company, Street address, and Phone. There isn't an admin mechanism for adding fields to the contact form, but there is a relatively easy way to do it, once you know how, and that's by creating a module. What's a Module? A module is how we can add our own logic to what Drupal does- to add extra functionality, or to alter the behavior of Drupal's existing functionality. With some web applications, the only way to do this is to change the existing code ('core' in Drupal parlance). The problem with that is that when a new version of the application is released, not only will those changes need to be made again to the new version, but in some cases the code you originally changed will be different in the new version, so that the changes you made originally cannot be made in the same way. Fortunately, Drupal's module architecture and the ability to hook into its events remove any need to change the core code. Let's create a module! Activity 3-3–The Guild Builders module We'll go through the steps of creating our module, which will give you the basic knowledge that you need to decide whether you'd like to investigate the topic further. A module typically has up to four core files: the file core to its functionality (the .module file), a file that describes the module to Drupal (the .info file), a file that provides installation and removal instructions to Drupal (the .install file), such as for creating database tables, and sometimes included files to separate out functional parts of the module (.inc files). Our module will only require the former two. Creating the .info file. Open a text editor and add a few lines. name = GBI Custom This line defines the name of the module as it will be displayed in the modules listing in admin. package = Guild Builders Inc. We could omit this line, which would cause the module to be located in the other section of the modules listing. However, we want it to appear in a section of its own, and this line provides a title for that section. description = Custom functions The description line provides the descriptive text that appears alongside the module entry in the modules list. core = 6.x The core entry specifies which major version of Drupal the module is meant to work with, such as 5.x, 6.x, or 7.x. version = "6.x-1.0" Finally, this line specifies the version of our module. It's meant to work with Drupal 6.x and is the first version of our module, and since we will not be releasing a pre-release version (0.x), we'll make it version 1.0. Our file now looks as follows: name = GBI Custompackage = Guild Builders Inc.description = Custom functionscore = 6.xversion = "6.x-1.0" We need to create a directory in which our module will live. We already have the path sites/all/modules in which add-on modules are placed. First, create the path _custom, in which to put our own modules, so that we can find them easily. Put the underscore at the start of the name so that it appears first in the directory list. Next, add the path guildbuilders as the home for this module. So, we now have the path sites/all/modules/_custom/guildbuilders, save our text file to that path as guildbuilders.info.
Read more
  • 0
  • 0
  • 1121

article-image-drupal-and-ubercart-2x-install-ready-made-drupal-theme
Packt
31 Mar 2010
5 min read
Save for later

Drupal and Ubercart 2.x: Install a Ready-made Drupal Theme

Packt
31 Mar 2010
5 min read
Install a ready-made Drupal theme We have to admit that Drupal was not famous for its plethora of available themes. Until recently, the Drupal community was focused on developing the backend, debugging the code, and creating new modules. The release of Drupal 6 made theming much easier and helped the theming community to grow. Now, there are not only thousands of Drupal themes, but also dozens of themes designed and customized especially for Ubercart. Basic principles when choosing a theme Choosing a theme for your online shop is not an easy task. Moreover, it can be even harder considering that you want to promote specific items from your catalog, you need to change first page items often, and you need to rapidly communicate offers and loyalty policies and other business-related stuff. Ubercart-specific themes mostly target the following special areas: Product catalog Shopping cart Product-specific views You should keep these layout regions in mind, while going through the following section on theme selection. Before you search for any kind of theme layout, provide your neurons with enough input to inspire you and help you decide. Perform a quick Google search for online shops in your target market to get some inspiration and track down sites that make you, as a customer, feel comfortable during product searching and navigation. If you decide to search for professional help, a list of existing sites will help you to communicate your preferences much more directly. What better place to search for inspiration and successful practices than Ubercart's live site repository! You will find good practices and see how mostly people like you (without any development background) have solved all the problems that might occur during your search for themes.http://www.ubercart.org/site Next we describe the main user interface components that you should keep in mind when deciding for your online shop: Number of columns: The number of columns depends on the block information you want to provide to your end customers. If you need widgets that display on every page, information about who bought what, and product or kit suggestions, go with three columns. You will find a plethora of two-column Drupal themes and many three-column Drupal themes, while some of them can alternate between two and three columns. Color scheme: From a design perspective, you should choose a color scheme that matches your company logo and business profile. For instance, if your store sells wooden toys, go with something more comic such as rounded corners, but if you are a consulting firm, you should go with something more professional. Many themes let you choose color schemes dynamically; however, always keep in mind that color is a rather easy modification from the CSS. You can get great color combination ideas from COLOURlovers online service (http://www.colourlovers.com/) that match your logo and business colors. Be careful though. If you choose a complex theme with rounded corners, lots of images, and multiple backgrounds, it may be difficult to modify it. Drupal version: Make sure the Drupal theme you choose is compatible with the version of Drupal you are running. Before using a Drupal theme, look up notes on the theme to see if there are any known bugs or problems with it. If you are not a programmer, you do not want a Drupal theme that has open issues. Extra features: Many Drupal themes expose a large set of configuration options to the end users. Various functionality such as post author's visibility or color scheme selection are welcome for managing the initial setup. Moreover, you can change appearance in non-invasive ways for your online marque. Regions available: We have discussed column layouts, but for the Drupal template engine to show its full capabilities and customization, you definitely need multiple regions. The more regions, the more choices you have for where to put blocks of content. Therefore, you can have space for customizing new affiliate ads for instance, or provide information about some special deals, or even configure your main online shop page, as we will see in the next section. Further customization and updates: When you choose your theme, don't just keep the functionality of version 1.0 in mind, but consider all of the future business plans for approaching your target market and raising sales figures. Make a three-year plan and try to visualize any future actions that should be taken into account from day one. Although you can change themes easily, you are better off choosing a more flexible theme ahead of time than having to change the theme as your website grows. Always bear in mind that the famous razor of Occam also applies to online shop theme design. Keep it simple and professional by choosing simple layouts, which allow ease of use for the end user and ease further customize designs and themes (changing colors, adding a custom image header, and so on). Before you start, clearly define your timeline, risks, total theme budget, and skills. Theming is usually 25-40% of the budget of an entire online shop project. Drupal's theming engine closely integrates with actual functionality and many features are encapsulated inside the theme itself. There are a number of different ways in which you can get yourself the best theme for your online store. We will go through all these approaches with useful comments on what options best suits your needs.
Read more
  • 0
  • 0
  • 2562

article-image-installation-and-configuration-microsoft-content-management-server-part-2
Packt
31 Mar 2010
5 min read
Save for later

Installation And Configuration of Microsoft Content Management Server: Part 2

Packt
31 Mar 2010
5 min read
Installing MCMS 2002 Prerequisites Before we can proceed with the installation of MCMS itself, we need to install two prerequisites. Installation of MCMS will be halted if these prerequisites are not met. J# 2.0 redistributable:Elements of MCMS Site Manager require the J# redistributable. Internet Explorer Web Controls for MCMS:Portions of the MCMS Web Author make use of the Internet Explorer Web Controls (IEWC), of which a specific MCMS distribution exists for which compilation is unnecessary. These controls, unlike the standard IEWC, are supported as part of an MCMS installation. As they are a prerequisite for MCMS, IEWC can be utilized within your applications. However, ASP.NET 2.0 offers far richer controls for navigation, as we will see later in this book. J# 2.0 Redistributable We need to install the Visual J# 2.0 Redistributable to enable the installation of the MCMS Site Manager. Download and save the J# 2.0 installer from: http://www.microsoft.com/downloads/details.aspx?familyid=f72c74b3-ed0e-4af8-ae63-2f0e42501be1&displaylang=en Double-click the installer. On the Welcome to Microsoft Visual J# 2.0 Redistributable Package Setup page, click Next. On the End User License Agreement page, check the I accept the terms of the License Agreement checkbox and click Install. Wait while J# 2.0 installs, and when the Setup Complete page appears, click Finish. Internet Explorer Web Controls for MCMS Internet Explorer Web Controls (IEWC) are required by the MCMS Web Author. Download and save the IEWC installer from: http://www.microsoft.com/downloads/details.aspx?FamilyID=FAC6350C-8AD6-4BCA-8860-8A6AE3F64448&displaylang=en Double-click the installer. On the Welcome to the Microsoft Internet Explorer WebControls Setup Wizard page, click Next. On the License Agreement page, select the I Agree radio button and click Next. On the Confirm Installation page, click Next. Wait while the web controls are installed, and when the Installation Complete page appears, click Close. Installing MCMS 2002 SP1a Insert the MCMS 2002 SP1a CD-ROM, and on the splash screen, click Install Components. On the Customer Information page, enter your User Name and Organization along with your Product Key and click Next. On the License Agreement page, click Accept. On the Installation Options page, select the Custom radio button and click Next. On the Custom Installation page, deselect the Site Stager item, and click Next. On the Summary page, click Install. Wait while MCMS 2002 SP1a is installed. On the Installation Completed page, uncheck the Launch MCMS Database Configuration Application checkbox, and click Finish. Remove Temporary Items Now MCMS SP1a is installed, we can tidy up the temporary items we created earlier to trick the installer. Select Start | Run. In the Run dialog, type cmd and click OK. Execute the following commands:cd c:kb915190cscript VS2003ByPass.vbs c:VSTemp remove Use Windows Explorer to delete the folders c:VSTemp and c:kb915190. Install Visual Studio 2005 Insert the Visual Studio 2005 DVD, and on the splash screen, click Install Visual Studio 2005. On the Welcome to the Microsoft Visual Studio 2005 installation wizard page, click Next. On the Start Page, select the I accept the terms of the License Agreement checkbox, enter your Product Key and Name, and click Next. On the Options Page, select the Custom radio button, enter your desired Product install path, and click Next. On the second Options Page, select the Visual C# and Visual Web Developer checkboxes within the Language Tools section, and the Tools checkbox within the .NET Framework SDK section. Ensure that all the other options are not selected and click Install. Feel free to install any additional features you may wish to use. The above selections are all that are required for following the examples in this article. Wait (or take a coffee break) while Visual Studio 2005 is installed. When the Finish Page appears, click Finish. From the Visual Studio 2005 Setup dialog, you can install the product documentation (MSDN Library) if desired, otherwise click Exit. From the Visual Studio 2005 Setup dialog, click Check for Visual Studio Service Releases to install any updates that may be available. Click Exit. Install MCMS SP2 From the Start Menu, click Run. In the Open textbox, enter IISRESET /STOP and click OK. Wait while the IIS Services are stopped. Double-click the SP2 installation package. On the Welcome to Microsoft Content Management Server 2002 SP2 Installation Wizard page, click Next. Select I accept the terms of this license agreement radio button, and click Next. On The wizard is ready to begin the installation page, click Next. Wait while Service Pack 2 is installed. On The Installation Wizard has completed page, click Finish. If prompted, click Yes on the dialog to restart your computer, which will complete the installation. Otherwise, from the Start Menu, click Run. In the Run textbox, enter IISRESET /START and click OK to restart the IIS services. Stopping IIS prior to the installation of SP2 avoids potential problems with replacing locked files during the installation, and can prevent the requirement to reboot.
Read more
  • 0
  • 0
  • 2318
article-image-making-sale-optimizing-product-pages-using-magento-13
Packt
31 Mar 2010
6 min read
Save for later

Making the Sale by Optimizing Product Pages using Magento 1.3

Packt
31 Mar 2010
6 min read
When shoppers land on a product page, you want that page to present the product in the best possible way. The product page should entice, inform, and entertain your shoppers. Adding custom options In Magento, a custom option is a field that enables your customer to specify something that he/she wants customized. For example, suppose you sell sports trophies that can be engraved with the name of the event and the winning team then you would add a custom option to that product, where the shopper enters the text to engrave. If you offer a style of shirt in different sizes and each size is a different product with its own stock number, then that is a configurable product. If you offer a style of shirt that is custom-made on demand, and the customer chooses the measurements for that shirt (chest size, sleeve length, neck size, and so on), then that is a simple product with custom options. In the following example, the customer can add his/her initials as a custom option. Selecting any of the options adds a product, with its own SKU, to the customer's order. How to do it... Let's begin with adding the custom option: Log in to your site's backend or Administrative Panel. Select Catalog | Manage Products. The Manage Products page displays. You will see a list of the products in your store. For the product that you want, select the Edit link. The Product Information page displays. The General tab will be selected for you. Select the Custom Options tab. Click the Add New Option button. A new option appears. You will need to fill in the fields to complete this option. In the Title field, add text that will appear next to the option. The text that you see in the example above, "This is an expensive machine..." and "Extra filter cups...", was entered into the Title field. Selecting the input type: Select the input type for this option. Based upon the type you select, other fields will appear. You will be required to fill in these other fields. If you select this Input type... You will also need to specify... Text The maximum number of characters the shopper can enter into the text field or text area. File   The filename extensions that you will allow the shopper to upload. For example, you might supply the shopper with a detailed form to fill out using Adobe Acrobat Reader and then have them upload the form. In that case, you would specify .pdf as the filename extension.   Select   Each of the selections that they can make. You add selections by clicking on the Add New Row button.   Date   Nothing. This just adds a field where the shopper enters a date and/or time.   Selecting the remaining options: The Is Required drop-down menu determines if the customer must select this custom option to order the product. For example, if you're selling custom-made shirts, then you might require the customer to enter measurements into the custom option fields. The Sort Order field determines the order in which the custom options are displayed. They appear from lowest to highest. The Price is a required field. If you set it to zero, then no price will display. Price Type is Fixed if you always charge the same for that option. Setting it to Percent calculates the price for the option based on the price for the product. SKU is not required, but if the option is another product (like extra parts), then you will want to use it. Save the product, and preview it in your store. How it works... Both custom options and configurable products give your customer a choice. But they are not the same. When a customer chooses a configurable product, the customer is ordering a separate product with its own stock number, price, and inventory. When a customer chooses a custom option, the customer is not choosing a different product. Instead, the customer is choosing an additional feature or part for the product. These custom additions can be free or they can have their own price. Each custom option has its own SKU number. There's more... You can get especially creative with the custom option that allows customers to upload files. For example, you can: Enable customers to upload a graphic that you add to the product, such as a graphic that is silkscreened on a laptop's case. Sell a picture printing and framing service. The customer uploads a digital picture, and you print it on high-quality photographic paper and frame it. Supply customers with a detailed form for specifying a product, and then have the customer upload the form as part of their order. Run a contest for the best picture of a customer using a product. Customers upload the picture under the product. You then add the best pictures to a static page on your site. Adding videos, links, and other HTML to product pages You enter the description for a product on the product page under the General tab: While these fields appear to accept only text, they will accept HTML code. This means that you can add almost anything to the product description that you can add to a standard web page. For example, let's embed a video into the Short Description field. How to do it... Navigate to the video site that contains the video you want to embed. In our example, we're embedding a video from YouTube: Clicking on the Embed video link selects the code that we need to put on our product page. Select and copy the code. Log in to Magento's backend, and go to the Product Information page, General tab. Paste the copied code into either of the description fields. Save the product. How it works... The HTML code that you enter into the description field is displayed when the customer views the product. Any valid HTML code will work. In our example, we embedded the video in the Short Description field, which placed it near the top of the page, under Quick Overview: There's more... Using HTML, you can: Embed videos in your product page Add links to your product page Add the manufacturer's graphic to the product description Just remain aware of how much space the Magento layout gives you for the items that you want to put on the page. For example, the code that we copied from www.youtube.com above makes the video 400 pixels wide which is too wide for our Magento page, so we had to change it to 300 pixels.
Read more
  • 0
  • 0
  • 1548

article-image-build-your-own-application-access-twitter-using-java-and-netbeans-part-3
Packt
31 Mar 2010
7 min read
Save for later

Build your own Application to access Twitter using Java and NetBeans: Part 3

Packt
31 Mar 2010
7 min read
This is the third part of the Twitter Java client tutorial article series! In Build your own Application to access Twitter using Java and NetBeans: Part 2 we: Created a twitterLogin dialog to take care of the login process Added functionality to show your 20 most recent tweets right after logging in Added the functionality to update your Twitter status Showing your Twitter friends’ timeline Open your NetBeans IDE along with your SwingAndTweet project, and make sure you’re in the Design View. Select the Tabbed Pane component from the Palette panel and drag it into the SwingAndTweetUI JFrame component: A new JTabbedPane1 container will appear below the JScrollPane1 control in the Inspector panel. Now drag the JScrollPane1 control into the JTabbedPane1 container: The jScrollPane1 control will merge with the jTabbedPane1 and a tab will appear. Double-click on the tab, replace its default name –tab1– with Home, and press Enter: Resize the jTabbedPane1 control so it takes all the available space from the main window: Now drag a Scroll Pane container from the Palette panel and drop it into the white area of the jTabbedPane1 control:   A new tab will appear, containing the new jScrollPane2 object you’ve just dropped in. Now drag a Panel container from the Palette panel and drop it into the white area of the jTabbedPane1 control: A JPanel1 container will appear inside the jScrollPane2 container, as shown in the next screenshot: Change the name of the new tab to Friends and then click on the Source tab to change to the Source view. Once your app code shows up, locate the btnLoginActionPerformed method and type the following code at the end of this method, right below the jTextArea1.updateUI() line: //code for the Friends timeline try { java.util.List<Status> statusList = twitter.getFriendsTimeline(); jPanel1.setLayout(new GridLayout(statusList.size(),1)); for (int i=0; i<statusList.size(); i++) { statusText = new JLabel(String.valueOf(statusList.get(i).getText())); statusUser = new JLabel(statusList.get(i).getUser().getName()); JPanel individualStatus = new JPanel(new GridLayout(2,1)); individualStatus.add(statusUser); individualStatus.add(statusText); jPanel1.add(individualStatus); } } catch (TwitterException e) { JOptionPane.showMessageDialog (null, "A Twitter error ocurred!");} jPanel1.updateUI(); The next screenshot shows how the code in your btnLoginActionPerformed method should look like after adding the code: One important thing you should notice is that there will be 6 error icons due to the fact that we need to declare some variables and write some import statements. Scroll up the code window until you locate the import twitter4j.*; and the import javax.swing.JOptionPane; lines, and add the following lines right after them: import java.awt.GridLayout; import javax.swing.JLabel; import javax.swing.JPanel; Now scroll down the code until you locate the Twitter twitter; line you added in Swinging and Tweeting with Java and NetBeans: Part 2 of this tutorial series and add the following lines: JLabel statusText; JLabel statusUser; If you go back to the buttonUpdateStatusActionPerformed method, you’ll notice the errors have disappeared. Now everything is ready for you to test the new functionality in your Twitter client! Press F6 to run your SwingAndTweet application and log in with your Twitter credentials. The main window will show your last 20 tweets, and if you click on the Friends tab, you will see the last 20 tweets of the people you’re following, along with your own tweets: Close your SwingAndTweet application to return to NetBeans. Let’s examine what we did in the previous exercise. On steps 2-5 you added a JTabbedPane container and created a Home tab where the JScrollPane1 and JTextArea1 controls show your latest tweets, and then on steps 6-8 you added the JPanel1 container inside the JScrollPane2 container. On step 9 you changed the name of the new tab to Friends and then added some code to show your friends’ latest tweets. As in previous exercises, we need to add the code inside a try-catch block because we are going to call the Twitter4J API to get the last 20 tweets on your friends timeline. The first line inside the try block is: java.util.List<Status> statusList = twitter.getFriendsTimeline(); This line gets the 20 most recent tweets from your friends’ timeline, and assigns them to the statusList variable. The next line, jPanel1.setLayout(new GridLayout(statusList.size(),1)); sets your jPanel1 container to use a layout manager called GridLayout, so the components inside jPanel1 can be arranged into rows and columns. The GridLayout constructor requires two parameters; the first one defines the number of rows, so we use the statusList.size() function to retrieve the number of tweets obtained with the getFriendsTimeline() function in the previous line of code. The second parameter defines the number of columns, and in this case we only need 1 column. The next line, for (int i=0; i<statusList.size(); i++) { starts a for loop that iterates through all the tweets obtained from your friends’ timeline. The next 6 lines are executed inside the for loop. The next line in the execution path is statusText = new JLabel(String.valueOf(statusList.get(i).getText())); This line assigns the text of an individual tweet to a JLabel control called statusText. You can omit the String.valueOf function in this line because the getText() already returns a string value –I used it because at first I was having trouble getting NetBeans to compile this line, I still haven’t found out why, but as soon as I have an answer, I’ll let you know. As you can see, the statusText JLabel control was created programmatically; this means we didn’t use the NetBeans GUI interface. The next line, statusUser = new JLabel(statusList.get(i).getUser().getName()); creates a JLabel component called statusUser, gets the name of the user that wrote the tweet through the statusList.get(i).getUser().getName() method and assigns this value to the statusUser component. The next line, JPanel individualStatus = new JPanel(new GridLayout(2,1)); creates a JPanel container named individualStatus to contain the two JLabels we created in the last two lines of code. This panel has a GridLayout with 2 rows and one column. The first row will contain the name of the user that wrote the tweet, and the second row will contain the text of that particular tweet. The next two lines, individualStatus.add(statusUser); individualStatus.add(statusText); add the name of the user (statusUser) and the text of the individual tweet (statusText) to the individualStatus container, and the next line, jPanel1.add(individualStatus); adds the individualStatus JPanel component – which contains the username and text of one individual tweet –to the jPanel1 container. This is the last line of code inside the for loop. The catch block shows an error message in case an error occurs when executing the getFriendsTimeline() function, and the jPanel1.updateUI(); line updates the jPanel1 container so it shows the most recent information added to it. Now you can see your friends’ latest tweets along with your own tweets, but we need to improve the way tweets are displayed, don’t you think so? Improving the way your friends’ tweets are displayed For starters, let’s change some font attributes to show the user name in bold style and the text of the tweet in plain style. Then we’ll add a black border to separate each individual tweet. Add the following line below the other import statements in your code: import java.awt.Font; Scroll down until you locate the btnLoginActionPerformed method and add the following two lines below the statusUser = new JLabel(statusList.get(i).getUser().getName()) line: Font newLabelFont = new Font(statusUser.getFont().getName(),Font.PLAIN,statusUser.getFont().getSize()); statusText.setFont(newLabelFont); The following screenshot shows the btnLoginActionPerformed method after adding those two lines:   Press F6 to run your SwingAndTweet application. Now you will be able to differentiate the user name from the text of your friends’ tweets: And now let’s add a black border to each individual tweet. Scroll up the code until you locate the import declarations and add the following lines below the import statement you added on step 1 of this exercise: import javax.swing.BorderFactory; import java.awt.Color; Scroll down to the btnLoginActionPerformed method and add the following line right after the individualStatus.add(statusText) line: individualStatus.setBorder(BorderFactory.createLineBorder(Color.black)); The next screenshot shows the appearance of your friends’ timeline tab with a black border separating each individual tweet:
Read more
  • 0
  • 0
  • 2671

article-image-interactive-page-regions-drupal-6-part-2
Packt
31 Mar 2010
5 min read
Save for later

Interactive Page Regions with Drupal 6: Part 2

Packt
31 Mar 2010
5 min read
Activity 3-4–Adding CAPTCHA to the Contact form These days, there's a factor of spam form completion to legitimate that seems like 10:1. To prevent that, we're going to add a CAPTCHA to the form. This activity requires that the CAPTCHA module be installed and configured. Information about this can be found at http://drupal.org/project/captcha. CAPTCHA is a means of ensuring that the author of information being submitted is a human and not a 'robot' or 'web crawler.' Sometimes the user is asked to identify characters that appear in a graphic, sometimes they must identify the object shown in an image,or complete a simple math problem, and so on. We can begin by navigating to the CAPTCHA settings page (admin/user/captcha). The page lists the contact_mail_page and contact_user_page as forms that can have CAPTCHA set for them, but neither applies in this case, since we're using a form in a block in a view. We'll enable the CAPTCHA challenge for the user from the user form itself, but here we need to turn on the admin link to do so, so check the box labeled Add CAPTCHA administration links to forms which will provide a link on the form for us as long as we're logged in as the administrator. Having saved that change, return to our form. There, find a new link that opens as shown in the following screenshot: This brings up a dialog that allows us to choose the CAPTCHA type. Choose the type that provides an easy math equation. The result is the link changing on the form, to show us that CAPTCHA will be enabled. Why can't we see the CAPTCHA challenge, though? Because admins don't have to submit to a CAPTCHA challenge, so log out and look at the form. Adding a Contact info Attachment view With our contact form complete, it's time to complete our Contact Us page. We're going to add an attachment display to the Contact Us view that will provide other contact options. Actually, we have other options available to us. We could create this display as a block, or, since our current view has no node to display and the additional contact information will be a node, we could just have it shown by the existing Page display. We'll use an Attachment display instead of a block display simply because we don't want to use one of the block regions for the output, and we're already using the Content region for a block (the form). We've chosen not to use the Page display because it's easier to theme the output with one part of the content being a separate display. Then, its content is provided in a separate variable for us, so we'll use an Attachment display. Activity 3-5–Creating the contact-us Attachment view We need to create the content for the Attachment view. We'll be using a custom content type, Location, for this. Let's create the content (node/add/location). We'll give the content a title, Guild Builders Contact Information. For the body, we'll create a <div> and put the contact information in it. This step requires the embed_gmap module. Information about this module can be found at http://drupal.org/project/embed_gmap. Next, we'll get to the field that makes this content type different, the map. The embed_gmap module takes the content of the map field and uses it to produce and embed a Google map. Enter the address in this field. We'll save the content, which is shown in the following screenshot. With our content created, we're ready to create our Attachment display. Edit our Contact us view (admin/build/views/edit/contact_us). Create a title for the view, and name it Guild Builders Contact Information, also create the header information, to appear beneath the title. The next thing to do is create an Attachment display for our view. That takes us to the View control panel. We'll start with the Filters pane. Click on the Node: Post date filter we have, and click Override, so that our changes only affect the Attachment display. Then click Remove, because we don't want this filter for our Attachment. Click the + icon to add a filter. We created a piece of content, of the Location content type. Therefore, we can create a filter to select only the Node: Type of Location, and another to specify that the node is published, in case we ever have more than one version of that content, so that only the one that is published will be selected. In the settings dialog for the filter, specify that Published should be Yes. Next, we'll specify that the Attachment be attached to the Page display. The last thing we need to do is add a small entry to our CSS file, so that our map and contact information will appear side-by-side. /* Contact-Us page settings */#contact-us-info, .field-field.map { float: left}#contact-us-info { margin-right: 1em;} And with that, and two images that show our Attachment display (which is too large to fit on the page in one image), we're done! Summary We learned what the default Contact system does, and how to add just a little pizazz with an Attachment view. We learned how to add the Contact form to a view, and used Drupal's module architecture and hook mechanism to modify that form by creating a small module. Finally, we created an Attachment view to add content to our Contact page. [ 1 | 2 ] If you have read this article you may be interested to view : Interactive Page Regions with Drupal 6: Part 1 Drupal 6: Attachment Views, Page Views, and Theming
Read more
  • 0
  • 0
  • 1328
article-image-managing-discussion-forums-using-php-nuke
Packt
30 Mar 2010
8 min read
Save for later

Managing the Discussion Forums Using PHP-Nuke

Packt
30 Mar 2010
8 min read
PHP-Nuke has an awesome discussion board module, the Forums module, which is a complete application. phpBB—the leading free, open-source discussion board application—has been 'refitted' as a PHP-Nuke module, providing integration with the PHP-Nuke user accounts. Forum Structure Rather than having a single discussion area, with topics intermingling with other topics, themes of conversation are organized into a number of different containers, rather like the folder and file structure of your hard disk. The top-level of organization is the category. Note that the categories here are different from the categories we have met in the other modules! Within categories, the next level of organization is into forums. Forums consist of topics, and finally, users are able to creating postings on these topics. Thus categories, forums, and topics act like folders, with postings being analogous to the files, to continue the file system analogy. Only forum administrators can create categories and forums. Topics (and obviously postings, since they are the real body of a discussion area) can be added by users of the forum. A topic is essentially a 'first' posting, with subsequent postings on that topic being replies to the topic subject. Here is a diagram of the forums hierarchy: Although a forum is contained in a category, the term 'forum' is generally used informally to refer to the whole discussion environment, covering categories, forums, topics, and postings. When you 'post to a forum', you are actually posting to a topic in a particular forum of a certain category! The general term 'board' or 'discussion board' is usually used to refer to the whole forum experience. Access to categories and forums can be restricted to groups of users. These restricted categories and forums can also be made invisible to those unable to access them. This is in contrast with other modules in PHP-Nuke where you restrict access to the entire module. In general, visitors either see all the contents of the module or none of it. The Forums module enables a set of 'mini-administrators', forum moderators, who are able to control who is able to post what, and where. We'll see more about that later. The Forums Administration Area The Forums administration area is accessed through the PHP-Nuke Administration area, in the same way as for any other module. This brings you to an area very different from the other PHP-Nuke module administration areas. This is the phpBB administration area, and is the nerve center of your phpBB forums. The page has a frame-based layout, with the left-hand frame being the navigation panel, giving you links to the various phpBB administration tasks. The right-hand frame holds the main page content. This screen shows you some statistics about your board, and the details of current, online visitors. Clicking on the Admin Index link will return you to this page, with the Forum Index link taking you into your forums. The Preview Forum link also takes you to your forums, but opens them up in the right-hand frame of the browser, retaining the phpBB administration navigation in the left-hand frame, so you can continue to work in the phpBB administration area if you need to. phpBB is truly awesome. It is arguably one of the most impressive free, open-source PHP web applications available, and we can only scratch the surface of its true power here.. Here we will step through the tasks of creating the structure to allow users to make postings, follow the posting process, and also see how to make some basic configuration changes. Forum Configuration Just as with PHP-Nuke where we began by making changes to PHP-Nuke's site configuration, here too, we begin with some global configuration settings for phpBB. Clicking on the Configuration link in the General Admin part of the left-hand panel takes you to the phpBB configuration area. There are many options; only some of the top ones are shown here: The Domain Name, Site name, and Site description fields are similar to the Site URL, Site Name, and Slogan fields of the PHP-Nuke preferences. The Domain Name field holds the domain name of your site, and we'll set the Site name and Site description fields to match those in our PHP-Nuke site configuration. We will also set the Cookie Domain to our site domain name, and the Cookie name to dinoportalforum. Note that if you change these settings after your site has gone live with people having visited the forums and logged in, then they won't be able to log in automatically since the Forums module will be looking for a different cookie from the one they have stored in their browser. PHP-Nuke generally uses the PHP mail() function to send its emails, but the Forums module offers the option to use an SMTP server to send mail. If you know the details of an SMTP server that you can use (possibly your Internet Service Provider has given you access to an SMTP server), then you can enter the settings for this in the Email Settings panel. If you don't have access to an SMTP server, then the default action of the Forums module is to use the PHP mail() function, as PHP-Nuke would normally do. Scrolling down the screen you will find a Submit button that will save your changes. Creating a Category Click on the Management link in the Forum Admin panel to begin creating the forum structure. First, you will need to create a category: Once you enter the name for the category into the box and click on the Create new category button, you have a category. Creating a Forum When the page reloads after creating the category, you are presented with a screen confirming the creation of your forum, and a Click Here to return to Forum Administration link. Clicking this link brings you to a page with the list of current categories displayed, along with links to edit, delete, or change their ordering in the list. You are also able to continue creating new categories. Immediately underneath our new category is a box for entering the name of a new forum for that category, and clicking on the Create new forum button will create a forum of that name: When the page reloads, you will be given a screen into which you can enter a description of the forum, and set some properties for it. You can assign the forum to another category from the Category dropdown, or you can set the Forum Status. The Forum Status is Locked or Unlocked. An Unlocked forum is free for all to view and contribute to; a Locked forum requires the user to have specific access to write or post to it. There are also 'pruning' options available for removing topics that haven't seen enough activity in the forum. These options will be useful for keeping your 'board' clean over time. Clicking on the Create new forum button creates the forum: Now we have forums, we are ready for topics. It is only a matter of time before we are posting! The Visitor Experience Open a new browser window, visit your PHP-Nuke site, and click on the Forums link. The visitor is welcomed to the Forums module with a list of the categories: Clicking on the Who is Online link presents you with a list of people who are currently viewing the forum, and where they are in the forum. Clicking on one of the forums takes you to the list of topics in that forum. At the moment, our forum is empty. As the screen is encouraging us to do, we can click on the new topic button to post a new topic to the forum. We do not have to be an administrator to do this, but we do have to be a registered user of the PHP-Nuke site. Posting a Topic The form for posting a new topic is rather exciting: You can enter the Subject of your topic, and enter the body of the topic in the Message body box. You are able to use a range of formatting effects within the body of your posting, including inserting those the little emoticons by clicking on them to add them to your text. Before posting your topic, it is worth taking a moment to preview it by clicking on the Preview Post button: If you are happy with the posting as it is, click on the Submit button and the posting is submitted. Your new topic is displayed in the forum's topic list: Clicking on the topic title brings up the submitted postings for that topic. At this point, we have only one—the topic posting: Users can now continue the discussion by posting a reply to this post. The author of the post is able to reply to, edit, or delete his or her own post with the aid of the three icons in the top right-hand corner of the post before any replies have been posted to the posting.
Read more
  • 0
  • 0
  • 3941

article-image-slowly-changing-dimension-scd-type-6
Packt
30 Mar 2010
6 min read
Save for later

Slowly Changing Dimension (SCD) Type 6

Packt
30 Mar 2010
6 min read
The Example We will apply SCD’s to maintain the history of Product dimension, specifically the history of changes of Product's Product Group. The PRODUCT_SK column is the surrogate key of the Product dimension table. PRODUCT_SK PRODUCT_CODE PRODUCT_NAME PRODUCT_GROUP_CODE PRODUCT_GROUP_NAME 1 11 PENCIL 1 WRITING SUPPLY 2 22 PEN 1 WRITING SUPPLY 3 33 TONER 2 PRINTING SUPPLY 4 44 NOTEBOOK 4 NON ELECTRONIC SUPPL SCD Type 1 We will apply SCD Type 1 to the PENCIL product in the Product dimension table. Let’s say PENCIL changes its product group into 4. Effecting this change by applying SCD Type 1 just updates the existing row of PENCIL on its product group. We do not have record of its previous product group; in other words, we do not maintain its product group history. The updated PENCIL’s product group is shown highlighted in blue. PRODUCT_SK PRODUCT_CODE PRODUCT_NAME PRODUCT_GROUP_CODE PRODUCT_GROUP_NAME 1 11 PENCIL 4 NON ELECTRONIC SUPPLY 2 22 PEN 1 WRITING SUPPLY 3 33 TONER 2 PRINTING SUPPLY 4 44 NOTEBOOK 4 NON ELECTRONIC SUPPLY SCD Type 2 SCD Type 2 is essentially the opposite of Type 1. When we apply SCD Type 2, we never update or delete any existing product group. To apply SCD Type 2 we need an effective date and an expiry date. Effective date 31-Dec-99 means the row is not expired. It is the most current version of the product. PRODUCT_SK PRODUCT_CODE PRODUCT_NAME PRODUCT_GROUP_CODE PRODUCT_GROUP_NAME EFFECTIVE_DATE EXPIRY_DATE 1 11 PENCIL 1 WRITING SUPPLY 1-Jan-09 31-Dec-99 2 22 PEN 1 WRITING SUPPLY 1-Jan-09 31-Dec-99 3 33 TONER 2 PRINTING SUPPLY 1-Jan-09 31-Dec-99 4 44 NOTEBOOK 4 NON ELECTRONIC SUPPLY 1-Jan-09 31-Dec-99 Assuming the product group change of PENCIL is effective 1 April 2010, we update the expiry date of its existing row to 31 March 2010, one day before the effective date of the effective date of the change, and insert a new row that represents its new, current version. PRODUCT_SK PRODUCT_CODE PRODUCT_NAME PRODUCT_ GROUP _CODE PRODUCT_GROUP _NAME EFFECTIVE_DATE EXPIRY_DATE 1 11 PENCIL 1 WRITING SUPPLY 1-Jan-09 31-Mar-10 2 22 PEN 1 WRITING SUPPLY 1-Jan-09 31-Dec-99 3 33 TONER 2 PRINTING SUPPLY 1-Jan-09 31-Dec-99 4 44 NOTEBOOK 4 NON ELECTRONIC SUPPLY 1-Jan-09 31-Dec-99 5 11 PENCIL 4 NON ELECTRONIC SUPPLY 1-Apr-09 31-Dec-99 SCD Type 3 With SCD Type 3 we maintain history but in one record only. We have one column for each version of the product group. You need to have as many columns as the number of versions you want to keep. One of the most common SCD Type 3 applications is to maintain two versions of product group: the original version and the current version. When there is no product group change yet, the current product group is the same as the original product group. PRODUCT_SK PRODUCT_CODE PRODUCT_ NAME PRODUCT_ GROUP_ CODE PRODUCT_ GROUP_NAME EFFECTIVE_ DATE EXPIRY_ DATE   CURRENT_ PRODUCT_ GROUP_ CODE CURRENT_ PRODUCT_ GROUP_NAME 1 11 PENCIL 1 WRITING SUPPLY 1-Jan-09 31-Dec-99   1 WRITING SUPPLY 2 22 PEN 1 WRITING SUPPLY 1-Jan-09 31-Dec-99   1 WRITING SUPPLY 3 33 TONER 2 PRINTING SUPPLY 1-Jan-09 31-Dec-99   2 PRINTING SUPPLY 4 44 NOTEBOOK 4 NON ELECTRONIC SUPPLY 1-Jan-09 31-Dec-99     4 NON ELECTRONIC SUPPLY When the pencil’s product group changes, let’s say on 1 April 2010, we expire its original product group by changing the expiry date to a day earlier (30 March 2010), and replace its current product group to the new product group. PRODUCT_SK PRODUCT_CODE PRODUCT_ NAME PRODUCT_ GROUP_CODE PRODUCT_ GROUP_NAME EFFECTIVE_ DATE EXPIRY_ DATE   CURRENT_ PRODUCT_ GROUP_ CODE CURRENT_ PRODUCT_ GROUP_ NAME 1 11 PENCIL 1 WRITING SUPPLY 1-Jan-09 31-Mar-10     4 NON ELECTRONIC SUPPLY 2 22 PEN 1 WRITING SUPPLY 1-Jan-09 31-Dec-99   1 WRITING SUPPLY 3 33 TONER 2 PRINTING SUPPLY 1-Jan-09 31-Dec-99   2 PRINTING SUPPLY 4 44 NOTEBOOK 4 NON ELECTRONIC SUPPLY 1-Jan-09 31-Dec-99     4 NON ELECTRONIC SUPPLY When its product group changes again in the future, we will replace just the current product group with the new product group. The expiry date does not change. It gets updated once only the first time its product group changes. SCD Type 6 SCD Type 6 combines the three basic types. Type 6 is particularly applicable if you want to maintain complete history and would also like have an easy way to effect on current version. Let’s apply Type 6 instead of Type 3 only. We have applied Type 3 by having two versions of product group. When the pencil’s product group changes we update its existing current product group (that is Type 1 update). We also apply Type 2 by adding a new row. PRODUCT_SK PRODUCT_CODE PRODUCT_ NAME PRODUCT_ GROUP_ CODE PRODUCT_ GROUP_ NAME EFFECTIVE_ DATE EXPIRY_ DATE   CURRENT_ PRODUCT_ GROUP_ CODE CURRENT_ PRODUCT_ GROUP_ NAME 1 11 PENCIL 1 WRITING SUPPLY 1-Jan-09 31-Mar-10     4 NON ELECTRONIC SUPPLY 2 22 PEN 1 WRITING SUPPLY 1-Jan-09 31-Dec-99   1 WRITING SUPPLY 3 33 TONER 2 PRINTING SUPPLY 1-Jan-09 31-Dec-99   2 PRINTING SUPPLY 4 44 NOTEBOOK 4 NON ELECTRONIC SUPPLY 1-Jan-09 31-Dec-99     4 NON ELECTRONIC SUPPLY 5 11 PENCIL 4 NON ELECTRONIC SUPPLY 1-Apr-10 31-Dec-99     4 NON ELECTRONIC SUPPLY On the next pencil’s product group change (1 July 2010), we will again apply all three SCD types. PRODUCT _SK PRODUCT _CODE PRODUCT _NAME PRODUCT_ GROUP_ CODE PRODUCT_ GROUP _NAME EFFECTIVE_ DATE EXPIRY_ DATE   CURRENT_ PRODUCT_ GROUP_ CODE CURRENT_ PRODUCT_ GROUP_ NAME 1 11 PENCIL 1 WRITING SUPPLY 1-Jan-09 31-Mar-10     5 LEGACY SUPPLY 2 22 PEN 1 WRITING SUPPLY 1-Jan-09 31-Dec-99   1 WRITING SUPPLY 3 33 TONER 2 PRINTING SUPPLY 1-Jan-09 31-Dec-99   2 PRINTING SUPPLY 4 44 NOTEBOOK 4 NON ELECTRONIC SUPPLY 1-Jan-09 31-Dec-99     4 NON ELECTRONIC SUPPLY 5 11 PENCIL 4 NON ELECTRONIC SUPPLY 1-Apr-10 30-Jun-10   5 LEGACY SUPPLY 6 11 PENCIL 5 LEGACY SUPPLY 1-Jul-10 31-Dec-99   5 LEGACY SUPPLY QUERY Let’s next see how our Type 6 in the Product dimension works on a sales fact. (In a real sales fact data you will have some other dimensions, meaning the fact table will have more surrogate key columns than just the product surrogate key) If our interest is in the current version, our SQL query will use the current product group column. An example SQL query will look like: SELECT current_product_group_name, SUM(sales_amt)FROM sales_fact s, product_dim pWHEREs.product_sk = p.product_skAND product_name = ‘PENCIL’GROUP BY current_product_group_code The output of the query will be: The reason of applying SCD Type 2 is to have a complete history that tracks changes. SQL queries that take into account dimension history use the product group column: SELECT product_group_name, SUM(sales_amt)FROM sales_fact s, product_dim p, date_dim dWHEREs.product_sk = p.product_skAND product_name = ‘PENCIL’GROUP BY product_group_code The output of the query will be: SUMMARY This article discusses what SCD Type 6 is, when to apply it, and how it works. The name Type 6 comes from the ‘sum’ of the three basic SCD types (6 = 1 + 2 + 3).
Read more
  • 0
  • 0
  • 11469
Modal Close icon
Modal Close icon