Tutorials Structure

Travis Schmeisser / 28th January, 2009
Structure is a new way to build ExpressionEngine sites. It forgoes the current template_group/template setup and creates pages that are all editable through a tree sitemap view. Now, traditional page style content and multiple entry pages can live within the same area.

Download & Documentation

This tutorial will expose you to the core of this module and define the major architecture for the back-end of most sites you’ll build this way. We’re assuming you know the basics of EE and where most things are in the control panel. However, since we’re using the template system in a new way, you don’t need advanced knowledge of how it works. Structure adds an alias for every entry within a weblog you set it to manage.

First off, you’ll need to install both Structure and its required dependancy CP jQuery, which is included with EE as of 1.6.5. The documentation has full installation instructions. You’ll also need the demonstration templates to follow along. Replace your site/index and site/site_css templates as well as adding the templates site/news and site/news-detail.

Now that we’ve got everything uploaded and activated we’ll begin configuring Structure, weblogs and templates to run this site. Since Structure works very differently than a traditional EE setup we’ll walk through two specific premises it runs on. Most sites have both:

  • “static” content and…
  • “listing” pages (like news, blogs, etc.)

Some sites also have additional content not related to a specific page and we’ll finish up by covering “assets” that are non-structural, but still need to be edited by your clients and authors.

The Setup

  • Create a new “Static Content Fields” field group with a single text area custom field called “content” (Set the formatting to anything you choose – this example uses Textile)
  • Create a new weblog where “Full Weblog Name” is “Static Content” and the “Short Name” is “static-content”
  • Paths no longer matter, as we’re using all custom URIs
  • Click “Submit” and then “Edit Groups”
  • Select “Static Content Fields, “Default Status Group” and save
  • Go to Modules > Structure > Settings
  • Mark the “Static Content” weblog as “Structure” under the type column
  • Select “site/index” as the default template for your new “Static Content” weblog and save the settings
  • Create a new entry through Publish > Static Content
  • Click the new Structure tab that appears on the publish/edit screen
  • For “Structure URI” add “/” and leave parent set to “NONE
  • Add a title and content to your new entry – this will be the homepage (URL Title doesn’t matter) and click “submit”
  • Repeat these steps for pages and URIs with the names “Services” (URI=services), “About Us” (URI=about), “News” (URI=news) and “Contact Us” (URI=contact)
  • Your Structure screen should now have the following setup. View demo image
  • These are our top level main navigation pages which are hardcoded into the demo templates

Creating Children Pages (or makin’ page babies)

We’ll explore two ways to add children within the interface:

  1. The same method as our top level pages, but assigning a parent
  2. The “add page” feature
  • Create a new entry through Publish > Static Content
  • Click the Structure tab
  • For “Structure URI” add “History” and set “Parent” to “About Us”
  • Add “History” to the title field and a bit of content to your new entry (URL Title doesn’t matter) and click “submit”
  • Revisit Modules > Structure. You should now have a “History” page under “About Us.” View demo image
  • Click “add page” next to “About Us”
  • This creates a new entry within the same weblog as the parent, in this case in the “Static Content” weblog because “About Us” was posted there
  • Click the Structure tab
  • Notice that “Parent” is already set to “About Us” and leave URI alone
  • Add “Mission Statement” to the title field and a bit of content to your new entry (URL Title doesn’t matter) and click “submit”
  • Structure will use the title to automatically create the URI if you don’t enter one, as we skipped above
  • Revisit Modules > Structure to see both pages

Your Pages, Out In The Wild

Click your “My Site” link to visit the public facing site. Your top level pages should now all be showing the content you entered. These are all using the single {exp:weblog:entries} tag to display each page. If you visit the “About Us” page you’ll notice the breadcrumbs at the top and sub-navigation in the right column. View demo image. Structure provides two dynamic tags that generate each for you. They have a standardized output, but a few parameters to control things by. View the documentation for a rundown on their formats and logic. If no children are present the tag won’t display any content. It reads the current URL and outputs the navigation based off it. The sub-navigation adds class="here" to the current page as well as mimics the sorting order you create by dragging pages within the Structure hierarchy.

Getting Your Listing On

So far, we’ve addressed general site content that we often refer to as “static content” to the outside (IE: client) world. Sometimes, we have pages that need to list different types of content that aren’t necessarily pages and that we certainly don’t want appearing in the sub navigation. We’ll be referring to these as “listings” for this demonstration. For safety and our development sanity Structure requires listings to be posted to a seperate weblog than your “static” content.

  • Create a new “News Fields” field group with a text area custom field called “content” and a text input called “source” (Set the formatting to anything you choose – this example uses Textile)
  • Create a new weblog where “Full Weblog Name” is “News” and the “Short Name” is “news”
  • Once again, paths no longer matter, as we’re using all custom URIs
  • Click “Submit” and then “Edit Groups”
  • Select “News Fields, “Default Status Group” and save
  • Go to Modules > Structure > Settings
  • Mark the “News” weblog as “Structure” under the type column
  • Select “site/news-detail” as the default template for your new “News” weblog and save the settings

Note: This is the template we’ll want single entry pages to use, a news detail page, if you will. Do not confuse this with the “News” page that is posting to the “Static Content” weblog. This allows us to provide intro copy before the listing, if needed.

  • Click the title for the page “News”
  • Under the structure tab modify the template dropdown to use the template “site/news”
  • Check the box next to “Listing” and select the “News” weblog from the dropdown
  • Click “Update” to save the entry
  • Go to Modules > Structure

You’ve now created the bridge between “News” and its “listings.” You can now add entries to its listing by clicking the “Add” link next to the page name or edit entries within that weblog by clicking “Edit.” View demo image. This will be the same as adding entries through Publish > News.

  • Click Publish > News
  • Notice the parent page is not editable because of our established connection even when not adding through the Structure interface. You can, however, change the layout per listing entry if needed for advanced customization.
  • Add several entries through this method to the “News” listing
  • Visit your site and see the listings click through to their “detail” page

The main “News” pages runs off site/news using {exp:weblog:entries} to display intro content preceding the listing. This is data posted to the “Static Content” weblog. It also provides a listing using {exp:weblog:entries weblog="news" dynamic="off"} with {page_url} to link through to the detail, which runs off site/news-detail so it can have a different layout and use seperate custom fields. site/news-detail also runs off the same method as site/index with only {exp:weblog:entries} since it’s solely deriving its data from the current URL once again. Note: For site/news to be able to display a listing dynamic="off" must be included.

You can even have sub-navigation under the “News” page that will run independently of the listings, but retain the same logical URL hierarchy.

Bits & Pieces

For any type of content not locked to a specific page, but still accessed by your authors you can create “Asset” weblogs. These appear under the main sitemap view with their own “Add/Edit” links. No Structure data is attached to them and they can be used by placing {exp:weblog:entries weblog="asset-weblog" dynamic="off"} or {exp:weblog:entries entry_id="XX" dynamic="off"} in your templates. The templates do not include code referencing this type. Your uses will greatly vary depending on the site’s needs.

  • Create a new weblog of your choosing
  • Go to Modules > Structure > Settings
  • Mark the new asset weblog as “Asset” under the type column
  • Go to Modules > Structure

Your Structure page now has an extra interface for this weblog at the bottom. View demo image

Members, Authors & The Outside World

We can restrict access to the actions of reordering, adding pages and to the module itself through the settings menu once you give any member group access to the Structure Module and the weblogs it uses. For safety, non-super admin members can only reorder within the same level of parent/children to avoid breaking top level navigation pages. This can be overridden as well by allowing the member group to “Administer Structure,” which gives them total access to all its settings. View Demo of member settings.

Onward!

You’re ready to rock! Have fun using Structure! For more information view the documentation or visit the ExpressionEngine forums.

  • Travis Schmeisser

  • Travis Schmeisser is a designer and partner at nGen Works in Jacksonville, FL. He maintains a personal site, posts as rockthenroll on twitter and is an all-around solid dude.

Comments

  • I’ve been testing out Structure on a site I’m building at the moment. Fred Boyle has been amazingly helpful by the way Travis. My only concern with it is that it feels like an all or nothing choice – like I’ve got to build the site the Structure way, or the traditional EE way. I guess it worries me slightly that later down the line a feature request may call for something that traditionally is simple but not possible with Structure (date archives aren’t possible within Structure for example as everything is a page).

    I know by the way it’s possible to work outside of Structure but to me that almost defeats the purpose of having such a clean structure.

    It’s still very early days for the module though and I know you’ve already make some cool changes in v1.1. I definitely recommend everyone gives it a go. Certain websites are made for this module and the client reaction I’ve had has been great.

  • Glad you’re liking it so far.

    You can definitely still develop the “traditional” way alongside it if needed. Really, it’s made to be an easy way for your authors to access different types of editable content from a single interface. Using template groups and templates you can still build other areas, but just allow them to edit through our method. For example, a date archive could still use traditional URLs and template structure, but the news landing page would be in Structure and have a listing attached to it to post to that weblog. We’ve found the singular interface to be a lot easier for clients than having things in different areas.

    Sometimes, functional pages are great to have outside Structure as well because they don’t necessarily have anything that the client needs to edit on them. An example of this would be a form with no text content or a member login page.

    We also do a lot of string passing for sorting or presenting data different ways. That way, it’s the same template and code, but a little extra PHP can display something different one the same landing page. For example, sorting an event page by the type of event.

    I’d love to hear about a few more specific instances you’ve run into and feel it falls down. That way we can get a better grasp of ways to improve it. It’s also partially tailored to how we build and use EE, so maybe I can help solve some.

    We’d love feedback from anyone else too!

  • Forgot to mention: hopefully you have Structure v1.1 because you can now turn weblogs off, which helps with mixing it with traditional EE methods…

  • It’s an outstanding module, taking care of navigation and breadcrumbs, too! Thank you for releasing it at such a low price.

    My only quibble is the restriction of the subnav to two levels (grandchildren). Anytime you go beyond that, the subnav changes to show all (and only) grandchildren.

    Hrm. I’ll figure it out. The module has definitely made building the site much easier, and I’ll always appreciate that.

  • Michael, there will be updates and extra features for that tag – lots of request for that. Thanks for the feedback!

  • This is a fabulous module, I’m very excited to put it to use on a project. Thank you.

  • On the matter of main/subnav, IIRC you mentioned elsewhere that the current implementation was intended to be used for a particular purpose. If I got that right, can you point us to an example?

    FWIW, I’ve been wishing for a couple of nav features, though not so deeply that I’ve thought through the consequences.

    1. If the field group has a field “weblogname_menu”, use that instead of {title} in the menu. The reason is that a title needs to stand along, but a menu name is viewed in the context of the menu, and can often be shorter. For example, if I have a level named “Chimpanzee” with submenu names “Diet” and “Habitat”, I want the titles to be of the form “Chimpanzee Diet”, but I don’t need to repeat “Chimpanzee” in the “Diet” menu item.

    2. A complete, expanded nav tree, for use in a site map.

    3. A combined main/subnav with each ancestor and sibling of the current page expanded, something like this, where main 2 and sub 3 are ancestors of the current page, subsub 2, and are expanded.:

    * main 1
    * main 2
       * sub 1
       * sub 2
       * sub 3
            * subsub 1
            * subsub 2 (=Here)
            * subsub 3
       * sub 4
       * sub 5
    * main 3
    * main 4
    
  • @Jonathon RE: nav_sub tag – by particular use, I just mean the way it functions now. It shows the children of a page when you are on that page and only shows up to 2 levels at a time. A sitemap tag is in the works for the next release. The other items are more appropriate for the forum, so if you have more questions or ideas please post them there. Thanks for the feedback! Structure forums thread

  • You mention that there is a way to hide a weblog from the Publish menu with this extension? I can’t find it. There is an extension from Mark Huot that does this, but I’d rather not install another extension to do what this one might accomplish.

  • The extension hides the Structure tab within Publish/Edit, but not the weblogs themselves.

  • Very cool, thanks for the tutorial. Definitely easiest to start with Structure from scratch it seems. Any advice on moving from a Pages based site to Structure?

  • Can’t Get Main Nav To Work

    From index page, my other main nav links bring up this type of error.

    *Not Found
    The requested URL /about was not found on this server.*

    http://hwc.ehclients.com

    The about page will successfully show if I go through Structure to view it. And if I manually enter “http://hwc.ehclients.com/index.php/about” it will show up as well.

    <.a {if segment_1 == “”} class=“selected” {/if} id=“button1” href=”/”> <.a {if segment_1 == “about”} class=“selected” {/if} id=“button2” href=”/about”> <.a {if segment_1 == “services”} class=“selected” {/if} id=“button3” href=”/services”> <.a {if segment_1 == “gallery”} class=“selected” {/if} id=“button4” href=”/gallery”> <.a {if segment_1 == “insurance”} class=“selected” {/if} id=“button5” href=”/insurance”> <.a {if segment_1 == “contact”} class=“selected” {/if} id=“button6” href=”/contact”>

    I had to add a . before the a to post the “links” section in this post, because otherwise it wasn’t showing the {if} statement.

    Such a simple problem, what am I missing?

  • <div id="links"> <a class="selected" id="button1" href="/"><span class="alt"></span></a> <a class="selected" id="button2" href="/about"><span class="alt"></span></a> <a class="selected" id="button3" href="/services"><span class="alt"></span></a> <a class="selected" id="button4" href="/gallery"><span class="alt"></span></a> <a class="selected" id="button5" href="/insurance"><span class="alt"></span></a> <a class="selected" id="button6" href="/contact"><span class="alt"></span></a> </div>

  • Dear Travis,

    This module seems like an amazing idea! It really streamlines the development of static content, but I’m also quite interested in how it can interact with the traditional EE publishing method and was wondering if you can elaborate on the following:

    “Using template groups and templates you can still build other areas, but just allow them to edit through our method. For example, a date archive could still use traditional URLs and template structure, but the news landing page would be in Structure and have a listing attached to it to post to that weblog.”

    I’m really in awe at this module, but I think I might be missing out on one some of it’s huge selling points being one of the less technically inclined EE developers (I’m a graphic designer ^^).

    Cheers,
    Danny

  • First, fantastic module.

    Second, there are a couple errors in the tutorial that might make it hard for some to follow along.

    • The hard-coded main navigation in the templates assumes that one has taken index.php out of the URI. If that hasn’t been done then the links will take you to a 404 page. Prepending {path="site_index"} to the links in your template would fix that.
    • Your instructions for setting up the news field groups say to name the fields “source” and “content” but “content” is already used in your default fields so EE throws an error. Your templates actually use a field named “story”. The tutorial just needs to be updated to reflect that.
  • Hi Travis – thank you for taking the time to put together this tutorial. This looks like a fantastic module.

    I’m trying to follow your instruction to get it setup, but when I try to add a new entry the Structure tab says “There are no available weblogs. Please create another weblog to make this page a listing page.”

    If I enter anything into the URI field, it doesn’t get saved and my modules > structure page still says “no data exists”. Any insight would be appreciated. Thank you!

  • I just wanted to let you know what I resolved my issue (above). I was hitting the “quick save” button instead of “submit” on the entries!!

  • I installed structure but I get an error loading lang.pages.php error. I don’t even have Pages installed, I am using expression core.

    Any ideas why this error is happening?

  • NM, Found the problem.

    Great article by the way!

  • Suffie, how did you fix your problem? I had the same thing. Clean install of ExpressionEngine, clean install of Structure, didn’t have Pages installed, when I went to publish » static content I got:

    Error – unable to load the following language file: /lang.pages.php

  • Found it myself:

    KNOWN BUG: Structure currently does not work with the core version of EE by default. We’re using a variable that is shared with the Pages module, so without the proper lang.pages.php file in place it causes errors. To correct this, if needed, place a blank lang.pages.php file in your /system/english/ folder.

    From the first entry at http://expressionengine.com/forums/viewthread/91290/

  • I’m trying to install the Structure module with ExpressionEngine Core at PosnitUbek.com. I did a fresh install of everything:

    1. ExpressionEngine 1.6.7

    2. Structure 1.2.5 (adding the empty lang.pages.php file to /language/english, per http://expressionengine.com/forums/viewthread/91290/

    3. Followed the instructions for installing Structure at http://expressionengine.com/forums/viewthread/91290/

    4. Followed this tutorial.

    Now I’m blocked. All the new top level pages I add get addresses like PosnitUbek.com/-1/, PosnitUbek.com/-2/, etc. In addition to being incorrectly addressed, these links only result in 404 errors.

    If I add a sub-page (/contact/contact_mail), it appears under Modules » Structure as PosnitUbek.com/-4/contact_mail, also broken.

    The only page that works is my homepage—does anybody have an idea what I’m doing wrong, or if I need to modify something about the Structure install to make it work with ExpressionEngine Core?

    I have installed everything three times and have the correct version of PHP. Each time I end up with these negative links for top level pages.

  • Any recommendations for how to eliminate the ‘index.php’ part of the url and still keep Structure happy?

  • I updated this module and now nothing works on my site. Really odd. I had a problem with the drag and drop feature which also still doesn’t work. Anyone similar experience with this and what should I do to fix it?

  • I am not sure if this is the answer to my question – I am looking to build a template for my blog postings which puts content in tabs – like main blog posts on one tab, comments on another tab, supplemental material on another tab, like here:

    http://online.wsj.com/article/SB124455528999797923.html

    can i do this with Structure?

  • The Modules > Structure > Settings doesn’t seem to be working for me. Every time I set and save the assignment settings, it seems to not to go. When I go back to check, everything is reset. Any idea what’s going on?

  • Please help me, I installed structure but I get an error loading lang.pages.php error. I don’t even have Pages installed, I am using expression core.

    Any ideas why this error is happening?

  • Nice tutorial but I have some issues when using nav_sub:

    you have any idea what causes this
    PHP Notice: Undefined index: in C:\inetpub\wwwroot\www.xxxxxxxxxx.xx\site\systeem\modules\structure\mod.structure.php on line 507
    PHP Notice: Undefined index: in C:\inetpub\wwwroot\www.xxxxxxxxxx.xx\site\systeem\modules\structure\mod.structure.php on line 510
    PHP Notice: Undefined offset: 23 in C:\inetpub\wwwroot\www.xxxxxxxxxx.xx\site\systeem\modules\structure\mod.structure.php on line 542
    PHP Warning: array_key_exists() [function.array-key-exists]: The second argument should be either an array or an object in C:\inetpub\wwwroot\www.xxxxxxxxxx.xx\site\systeem\modules\structure\mod.structure.php on line 542

  • Great tutorial! This really got my head around Structure and I love it now.

    QUESTION: Is there any way to re-route back to the the Modules>Structure page after updating a page? Not a big deal I guess.

  • I was curious if you can default to the “Structure” tab when editing or adding a new page?

  • The nav_sub is difficult to style, I can style the children but not the parent without effecting the children and I think it is because nav_sub output is not closiing the list tag that opens with sub_level_0 then encloses the level_1 items.

    anyone else noticed this or had success in styling their sub_nav – please post links to examples and if you would be so kind the css so I can compare to mine.

    Cheers folks

  • Link to templates is wiped out with the new domain. Need to repost a working link.

  • Hey I’m trying to find the demonstration templates but they seemed to be MIA. I’d like to see them so I could look of how you set up the code. Anyway you could point me to where they are?

    thanks!
    Scott

  • Hey Everyone –

    The demo files and images have been fixed.

    Please do no post support questions here, this is a tutorial and not the place for support requests. Either post them to the forum or email me:

    • http://expressionengine.com/forums/viewthread/91290
    • travis [at] rockthenroll.com

    Thanks!

  • For those wondering how to remove index.php and get it working with Structure, the simple answer is:

    • Install Structure as above
    • Install the LG .htaccess Generator (v.1.0.0 as of writing)
    • In the extension settings delete the pipe | between {ee:template_groups} and {ee:pages} in the second to last RewriteCond. It should look like this:
      RewriteCond %{REQUEST_URI} ^/({ee:template_groups}{ee:pages}|members|P[0-9]{2,8}) [NC]
    • Go to System prefs > General configuration and change the ‘Name of your site’s index page’ to blank.

    Now your urls will look like:
    mysite.com/about
    mysite.com/about/subpage
    etc

  • For each listing entry, do I need to add in the detail template?

    For example I have a static (index) entry called News and I want each entry to go to news/detail.

    But if I create a new news entry, the Structure URL just says news/ followed by the input field.

    Is there a way to force this to news/detail/ followed by the input field?

  • You could make a subpage called ‘detail’ and make that a listing for the news weblog. Or you could not use structure at all and just have a template group called news and a template called detail inside. Or you could use a .htaccess rewrite rule to rewrite news/detail/whatever/ to news/detail/ eg:
    RewriteRule ^news/detail/(.*)$ /index.php/news/$1 [QSA,L]

  • Anyway know how to have structure work with a multi-language site using this method.
    http://expressionengine.com/wiki/Multi_language_site_alternative/

    I did a pretty brutal hack for it to make it work by setting it up so that if you typed “English Title fr French Title" in the title field it would just grab everything after fr if the site url had /fr/ in it.

    It works just fine on all aspects of structure but i know as soon as i update structure its toast. I would have liked to have had it so that there was a french title field as well but that was beyond my capabilities to get working with structure

  • @Mark C did this really work for you? It doesn’t appear to do anything different. If that change is made, the htaccess just has your last template group and your first “page” bunched together.

    Anyone else find a solution for removing the .htaccess? I’ve tried typing all of my page names manually into the .htaccess file. No dice.

  • @Dan T

    I assume you are referring to my first post where I set out how to remove the index.php from the url? If so, yes it does work, however I have subsequently found that the regeneration of the htaccess file to be problematic, and so I am using the ‘Exclude’ method which works perfectly. The first condition should list all the files or folders to NOT be rewritten, so for the typical install where the system folder is named ‘system’:

    RewriteEngine on
    RewriteCond $1 !^(images|system|themes|favicon\.ico|robots\.txt|path\.php|index\.php|([a-z0-9-]+).html) [NC]
    RewriteRule ^(.*)$ /index.php/$1 [L]

  • Has anyone had a problem with EE 1.6.8 & Structure 1.3.1? Im getting an error when trying to install structure.

    Parse error: syntax error, unexpected ‘&’, expecting T_VARIABLE or ‘$’ in /[PATH_TO_ROOT]/html/cec/content_cec/modules/structure/mod.structure.php on line 1641

  • I have been using Structure for a couple of months now and am thrilled with it. This module makes it so easy for my clients to update their sites.

    There are two templates I use for pages in Structure: an index template and a section-home template. I want the default for a new page to be index but Structure likes to assign section-home. How can I fix this?

  • @Jenny Turney

    I wrote an extension to force template inheritance:
    http://expressionengine.com/forums/viewthread/131353/

  • @Mark C

    Thanks, Mark! I will check that out.

  • I have been using Structure for a couple of months now and am thrilled with it. This module makes it so easy for my clients to update their sites.

  • @Mark C (or Travis):

    I’ve followed your advice about lg .htaccess generator, and it rewrites the urls fine. However, when clicking the pages, each STUCTURE page is NOT FOUND.

    Did you encounter this when adding the extension? If so, do you remember what you did to fix it?

    Thanks,
    Chuck

  • @Phil – Also looking at how to use Structure with a multi-language site. Any more information you could share?

  • Hi. Im using Structure 2.03, but i can’t seem to get exclude working… and its driving me mad :)

    {exp:structure:nav_sub start_from=”/” show_depth=“0” exclude=“29”}

    This should exclude entry #29 but it just wont work!
    -does anyone know if this is an ‘official’ bug?

    exclude_status works fine

  • @Jenny
    I wanted to use Structure for a multi lingual site but the module has no support for MSM site duplication, and so I had to abort plans to use it.
    Money wasted unfortunately.

    It’s a good module but lacking functionality which should be expected in the price tag.

Comment Form

  • Should you care, Gravatars are enabled.

  • We will link to the URL but we utilise the 'nofollow' attribute value.

  • pmCode is disabled. Textile formatting is available. Code blocks should be wrapped with <pre> and <code> tags. Always play nicely.

Advertisment (Want to advertise here?)