Planet Drupal

Subscribe to flux Planet Drupal - aggregated feeds in category Planet Drupal
Mis à jour : il y a 6 min

Cheeky Monkey Media: A Quick Look Back at BADCamp 2014

mar, 30/12/2014 - 18:00

This year, I was invited to attend BADCamp 2014. No, I know what you are thinking, but this is not a camp for bad web developers. In fact, its quite the opposite. Badcamp stands for Bay Area Drupal Camp. This is a four day, annual event held in the San Francisco Bay area. Basically, its a gathering of like-minded web developers discussing and learning about Drupal.

Having never been to a major Drupal event, I jumped on the opportunity to go. It was a fun trip full of learning, networking and maybe an after...Read More

Catégories: Elsewhere

Drupalize.Me: Drupal 8 Upgrade Path

mar, 30/12/2014 - 15:00

All this excited talk of Drupal 8 has a lot of people dreaming of the day they get to start working with it. Some people get to build new sites from scratch all the time, but a lot of Drupal work out there is maintaining and upgrading existing sites. How will the Drupal 8 upgrade path work, and will it be as shiny as Drupal 8 itself? Well, upgrades will be radically different in Drupal 8, and I'd say it has all the shiny you could possibly want.

Catégories: Elsewhere

Open Source Training: Google Maps in Drupal with the GMap Module

mar, 30/12/2014 - 02:04

Several times in the last few weeks, OSTraining students have asked us about maps in Drupal.

The students wanted to set up directories that would show Google maps for each location.

They also wanted to create larger maps that would display multiple locations at once.

We recommended that the students use the GMap module. However, although that module is powerful, it is poorly documented and can be confusing to use.

So, here's a beginners guide to the GMap module.

Catégories: Elsewhere

Code Karate: Drupal 7 Draggable Captcha - a more friendly way to prevent Spam

lun, 29/12/2014 - 01:50
Episode Number: 187

The Drupal 7 Draggable Captcha module is not like most captchas. A captcha is a way to catch or capture spam and prevent a bot from completing a form. This is one of the most widely used ways to prevent SPAM on a website. Drupal has many different types of captchas available and the Draggable Captcha is one of the more fun and easy ones.

Tags: DrupalDrupal 7Drupal PlanetSpam Prevention
Catégories: Elsewhere Yo Hedley!

jeu, 25/12/2014 - 23:00

Bingo! I think we're on to something here. It's called yo hedley - and its one command that brings a true headless Drupal to everybody.

In my last DrupalCon Bof presentation "Gizra - we've got your headless covered" I've taken the time to explain why "headless" was in fact mostly a buzz word. While I encourage you to have a look at the presentation, I'm actually more excited about telling you why I feel this is no longer the case.
Go ahead an check the live demo!

Continue reading…

Catégories: Elsewhere

Drupal Watchdog: The Drupal 6 to 8 Upgrade Challenge - Part 2

mer, 24/12/2014 - 20:23

Nathaniel Catchpole , the Drupal 8 release maintainer and Tag1 Senior Performance Engineer, suggested that Drupal shops everywhere could support the release of Drupal 8 by upgrading their own sites and addressing the issues they find along the way. This is part two of a series chronicling the journey from Drupal 6 to Drupal 8.

Part 1: Readiness Assessment

Part 2: Preparing to Migrate D6 to D8

Having concluded the readiness assessment, we turn next to migrating the content and configuration. In reality, there’s little chance that we would migrate anything but the blogs from our old site, For the sake of giving Migrate in Core a workout with real conditions, however, we’re going to upgrade with core’s Migrate Drupal module rather than rebuilding.

Migrate in core is pretty exciting!

It means that we can:

  • Migrate content from the old site
  • Build new functionality on the new site
  • Continue to migrate content from the D6 site to the D8 site periodically
  • Keep the sites side-by-side until we’re ready to make the new one live
  • Publish

Conceptually, then, the Migrate Drupal module is different than past major version upgrades. There’s no more running and rerunning the monolithic update.php! It means you need two databases, the D6 database and the D8 database.

There’s a lot of documentation on running Migrations available on Here are some key entry points:

What follows is my specific journey and you should return to the main documentation when upgrading your own site.

Get the D8 Compatible Version of Drush

Full documentation for Drush is available at Read the Docs. My directions below are slightly different than the recommended install as I prefer to keep my source files in /usr/local/src, not a user home directory.

  1. Install Composer globally (if you haven’t already).
  2. Install Drush 7.x (dev) which is required for Drupal 8:
    $ sudo mkdir /usr/local/src/drush // create the directory if it doesn't exist $ cd /usr/local/src/drush $ sudo composer require drush/drush:dev-master $ sudo ln -s /usr/local/src/drush/vendor/drush/drush/drush /usr/local/bin/drush $ sudo drush // one time only with root privileges
Prepare the D6 Site Uninstall Disabled Modules

Although access to the legacy site is read-only, it’s not recommended that you run migrations against a production site, so I work from my local development copy with a fresh copy of the prod database.

The only real preparation necessary is uninstalling unused modules. Migrate will try to migrate all the content in the database, including things related to disabled modules.

The command drush pm-list --type=Module --status=disabled shows me what’s available to uninstall:

Package Name Version CCK Content Copy (content_copy) 6.x-2.9 Core - optional Book (book) 6.31 Core - optional Forum (forum) 6.31 Core - optional Poll (poll) 6.31 Core - optional Search (search) 6.31

I’ve uninstalled all of these to eliminate the chance of orphaned data causing an issue with the migration:

$ drush pm-uninstall book forum poll search content_copy -y Delete Unwanted Content, Especially Spam

Many site owners prevent spam from being displayed, but they don’t always delete it. My first try at upgrading was taking a really long time on the comments migration. A quick peek showed me:

MariaDB [tag1dev]> select count(*), status from comments group by status; +----------+--------+ | count(*) | status | +----------+--------+ | 57 | 0 | | 173851 | 1 | | 1024 | 9 | +----------+--------+

Brief investigation told me that 0 is published, 1 is unpublished and 9 is unapproved. Everything not explicitly published appeared to be spam. I took them out with delete from comments where status = 1 or status = 9; and sped up the migration considerably.

See if There’s Evaluated PHP in the Body of Blocks or Nodes

I was reminded of this, too, after running my first migration: There might be PHP in blocks, nodes, or comments that are best found and addressed before upgrading.

One way to do that is run the Security Review module. It’s only partly helpful, though. It will reveal any node with <?php in it, which, if preceded by a <pre> tag is not being interpreted. That sort of usage will cause Security Review to report some false positives. Still, there’s a lot of good information, and you may find other problems you’d like to correct either before or after migrating.

The good news, no untrusted roles were allowed to use the filter. In fact, no roles were. Still, because it was enabled, I did a quick check on blocks and nodes with these snippets from Wesley Tanaka:

MariaDB [tag1dev]> select bid, info from boxes where format in (select format from filters where module = 'php' and delta = 0); MariaDB [tag1dev]> select nid, vid from node_revisions where format in (select format from filters where module = 'php' and delta = 0);

They turned up two blocks as well as the one node I’d already found with Security Review. I removed the php prior to the migration and disabled the php filter since it’s not available for D8 and we wouldn’t want to use it if it were.

Prepare the D8 Site

I wanted to work with the dev branch of D8, not the beta, because I anticipated finding bugs and didn’t want to spend time troubleshooting a bug in beta that had already been fixed in dev. Note that at this point, there’s no upgrade path from D8 to D8, and I wouldn’t want to work with a Beta or consider this project for production deployment until that exists.

I added a new site to apache, eight, and updated /etc/hosts accordingly. You’d set up your localhost web server however you’d normally run a second site on your development machine.

The Dev branch

Since I was working with dev and I might need to submit patches back, I cloned from git. Drupal Core is big, so I just grabbed the development branch for now.

$ mkdir /var/www/eight $ cd /var/www/eight $ git clone --branch 8.0.x --single-branch $ cd drupal

IMPORTANT: From here on out, all commands should be run in the root of your new Drupal 8 site! If you had installed like me, that means all the commands would be run from /var/www/eight/drupal unless otherwise specified.

Install Drupal 8

I performed a standard installation following the directions in the core/INSTALL.txt file.

Prepare the Manifest

Currently, Drush provides the cleanest way to run a Migration. The Migrate user interface is still under development; you can follow along here:

  1. Enable Migrate Drupal and any modules that should be receiving data from your D6 site. I won’t need any contributed modules enabled.
    $ drush en migrate_drupal, migrate -y
  2. Get the latest list of migrations available:
    $ drush config-list | grep migrate

    You’ll see output like the following, but more of it.

    migrate.migration.d6_action_settings migrate.migration.d6_aggregator_feed migrate.migration.d6_aggregator_item migrate.migration.d6_aggregator_settings

    IMPORTANT: If migrate and migrate_drupal are not enabled, you 'll see a message that Migrate is not installed instead.

  3. Make a manifest.yml file. You can actually call this anything.yml that you want since you’ll be calling it by name when you run the migration. To include each of these individual migrations in the manifest, remove the migrate.migration. and replace it with a dash followed by a space, so you’ll have - d6_action_settings, for example. You can use the following to write the manifest file directly:
    $ drush config-list | grep migrate | sed -e 's/migrate.migration./- /' > manifest.yml

I like to include all the migrations in the manifest and use a # symbol to comment out migrations I’m not running. For example, I don’t have anything related to aggregator on the D6 site. Migrate would tell me so if I left the aggregator migrations in the file, with a message like:

Running d6_aggregator_feed [ok] Invalid argument supplied for foreach() RequirementsException.php:63 [warning] Migration d6_aggregator_feed did not meet the requirements. Missing source provider aggregator [error]

I can disable individual migrations by commenting them out with #, thereby avoiding cluttering its output with warnings. In addition, we’re not using book module, so I disabled it. The top of the manifest file looks like:

- d6_action_settings #- d6_aggregator_feed #- d6_aggregator_item #- d6_aggregator_settings - d6_block #- d6_book #- d6_book_settings - d6_cck_field_revision - d6_cck_field_values …

NOTE: In addition to unused modules and deleting spam, I also commented out the following to speed up the process:

# - d6_node_revision # - d6_cck_field_revision # - d6_term_node_revision

I plan to run all three of them once I've worked through any issues I encounter.

Catégories: Elsewhere

Drupal @ Penn State: ELMSLN Year end review

mer, 24/12/2014 - 19:53

This is a review of everything that happened in ELMS Learning Network through 2014. In 2014, we picked up an additional member institution that has been using ELMSLN for online courses. Wisconsin Law School’s Center for Patient Partnerships has been avid supporters of ELMSLN even prior to adoption in the past year and are very happy with the flexibility and control that it gives them over learning environment development.

Catégories: Elsewhere

InternetDevels: DrupalTour in Chernivtsi

mer, 24/12/2014 - 14:17

It all happened on winter holidays eve, on Saturday, 13, when DrupalTour team visited “Little Paris” — Chernivtsi. The second Drupal tourists’ point of destination met us very friendly and was eager to welcome IT-event of completely new kind.

We started our Drupal van at 3 AM and took off to a journey through the country aiming to meet IT-community in Chernivtsi, get acquainted with new cool people and exchange our web development experience. The roads in winter are especially charming and evokes the thoughts about eternity.

Read more
Catégories: Elsewhere

Chapter Three: A Drupal 8 Festivus

mer, 24/12/2014 - 03:22

In the spirit of Festivus some members of our team attempted a Drupal 8 feat of strength to ensure we were able to thoroughly air our grievances about the theme layer in Drupal 8.

Several of our front end developers accepted the challenge to build a simple two-page Drupal 8 theme based off of an older project's design.

Below are the areas that most confused them or slowed them down, or tripped them up during the process. I hope you can take advantage of our collected wisdom to smooth out your own first experience with building a theme in 8.

Catégories: Elsewhere

Lullabot: D8 Accelerate

mar, 23/12/2014 - 23:49

What is D8 Accelerate? Amber Himes Matz chats with Angie Byron and Holly Ross about this new pilot program from the Drupal Association to put $125,000 of community funds toward resolving critical issues and accelerating the release of Drupal 8.

Catégories: Elsewhere

Open Source Training: Using Tokens in Drupal Fields

mar, 23/12/2014 - 22:11

Token is one of the 3 most popular modules in Drupal.

It allows you to use small placeholders to automatically complete tasks. To take a simple example, if you put [site:name] on your site, it will be replaced by the actual name of your site. To take a more complicated example, you can use Token together with the Pathauto module to automatically create URL patterns for your whole site.

However, Token needs other modules to work. If you want to use Token inside fields, there are several options but one of the most reliable is a module called Token Filter.

Catégories: Elsewhere

Drupal Association News: Using Personas in the Community

mar, 23/12/2014 - 20:26

Now that we’ve seen real examples of our personas, you may be thinking, “these personas are pretty cool, but I’m not sure how they affect me."

Beyond just the obvious applications towards redesigning, any member of our community can use the personas to build better Drupal training programs, tutorials, and Drupal events.

Improving Drupal Training

Cathy Theys is a prominent community member who is known for the hard work she puts in to facilitating Drupal training and sprints all around the world. Some of the problems Cathy has consistently seen revolve around language, and the user personas give a starting point for building more friendly wordage in the community.

"I think that re-using these personas at events can help people identify with whether or not they’re supposed to be in a certain sprint, or which part of that sprint they’re supposed to be in,” Cathy said. “For example, at DrupalCons on Friday, our attendance is probably around 450-500. A great deal of what the mentors do is try and figure out when people are walking through the door, where they should sit down and what they should do.

“In Amsterdam we had some signs identifying the three sprint locations— one of them was the main sprint with topic areas, another was a workshop that showed people the absolute basics — how to use the issue queue and interact with the community— and then there was a sprint that was halfway in-between for people who are set up, who have the tools, but maybe aren’t comfortable working on a sprint issue. That’s the mentored sprint area.

“One of the things we planned in advance of DrupalCon Amsterdam was the wording to put on the signs. We wanted to figure out, how does someone identify if that’s the right room for them and if not, what is?"

And when it comes to the personas, Cathy sees the value. “These personas have information that relates to each persona’s amount of contribution and engagement with the community. I can see how that could help out."

Bettering the Issue Queue

Gábor Hojtsy is another well-known person in the Drupal community, and is currently working as the Multilingual team lead. Like Cathy, he sees the potential for using personas to help build the Drupal community.

"I think it would be good to verify that serves these personas. I think that... in a lot of areas in, we serve the Experts and the Masters very well and we don’t serve the rest too well — especially Newcomers. What we do in the Drupal community well is to bring in the Newcomers at events, but we don’t do a good job of bringing in the Newcomers on the site. There’s a lot of text, a lot of things left out of date, a lot of contradicting information — so there’s a lot of space to move downward on this pyramid to serve those people,” he said.

Both Cathy and Gábor recognized how the language can help facilitate improvements to the Drupal project as well — namely, in the issue queues. For Cathy, this often arises when talking to experts in other industries who come in to the Drupal sprints as Learners.

“Right now there is a wording problem, and I think a lot of it revolves around this word novice and how it is misunderstood,” said Cathy. “Sometimes there is an issue in the queue where... for example, a patch is pretty good, but it’s using a deprecated method. So someone has to go find the lines that use the deprecated call and change it to do the newer, better way instead.

"For someone who is an expert at PHP they might feel a little insulted, because they view the task as so easy-- but it lets them focus on learning the actual Drupal contribution workflow. The task itself is simple so that it clears your mind to focus on the things that are new and hard, which are the contribution parts. But if you don’t explain why you’re asking this expert in PHP to do what they might see as menial task, they are insulted and stop contributing."

Gábor has seen the other side of that particular problem.

“People assume if an issue is critical or major, that it would be for Masters only, so they may not even touch that one — but it’s not necessarily true. It would be certainly good to improve the issue queue system to identify better issues for Newcomers and Learners. It’s a lot more difficult, though, because there’s always some sort of domain knowledge required — so the target is not just Skilled in general but Skilled in a specific set of things."

Building Better DrupalCons

When it comes to the biggest Drupal events of all, you can bet that the personas will be used by the planning team.

“We're at the initial phase of incorporating the personas,” said the Association’s Events Manager, Rachel Friesen. “One way we’ve interpreted the Drupal Association’s goal of "Grow the Community" as it relates to DrupalCon is the idea that we need to bring more Learners to DrupalCon. Specifically, we want them to find DrupalCon accessible, which is why we're trying to find new ways to reach out to welcome first time attendees.

“Another Drupal Association goal is to "Accelerate the Project,” and we’ve interpreted that DrupalCon’s role in that is by helping increase the number of contributions that are made to the project. To help foster that, we plan to make it easier for our attendees to transition from Learner to Skilled. Part of that means that we need to not only increase number of first time DrupalCon participants, but also remove barriers for new Drupalers to fit in at DrupalCon, make friends, and feel at home in our community.”

“We’ve been talking about ways to apply these personas,” said Stephanie El-Hajj, the Program Coordinator for the Drupal Association. “Ideally, we bring in Learners, and then they’re tutored and mentored by Experts and Masters. We are seriously looking at using training, summits, sessions and BOFs to move DrupalCon attendees from Learners to Skilled, and using mentoring and sprints to move people from Skilled to Expert and Master.

“Mentoring and giving back via sprints helps people move through the Drupal learning curve,” Stephanie continued, “with sprinting you’re learning how to do stuff hands on, rather than just looking up an answer or being told how to do something, and you’re applying concepts to projects you maybe didn’t tackle at work. It’s that kind of contributing that helps you grow. And if you have a mentor cheering you on, that’s even better.”

Putting the 'Person' in Persona

Ultimately, user personas are not about Drupal, but are about people: specifically, about helping them learn and grow in the Drupal world.

"I’ve had a lot of different jobs in my life,” said Cathy. "I’ve had a university instructor job, I’ve been a dog trainer, I’ve been a breastfeeding counselor, and all of these different things — and this job that I have right now — involves trying to teach people in a way that respects them for what they already know. The way that you explain things to people is so important to get buy-in and make them feel respected and useful at the same time. So it’s not Drupal specific — it’s all about the humans."

Catégories: Elsewhere

Drupal Watchdog: Upgrading Your Themes

mar, 23/12/2014 - 18:55

The rumors are true: pretty much everything has changed in Drupal theming in the latest version.

At first it seems scary, but as you start digging into things, I think you’ll come to realize that the biggest changes are nearly invisible. Yes, there’s a new template engine with a different syntax, but the concept of template files which nest into one another still exists. We still have regions which can be loaded with blocks. We still have display modes. And you’ll still be working with Views. So while almost everything has changed, there’s also a lot that is quickly going to feel quite comfortable.

The biggest change, of course, is the retirement of PHPTemplate in favor of Twig. I have to admit that I’m an old-schooler who didn’t really find PHPTemplate all that difficult. (I will also admit that I’ve been known to throw coding elegance out the window in favor of brute force from time-to-time.) Generally, I don’t buy the argument that Twig, on its own, has reduced the complexity of the themes.

Let me show you what I mean. In PHPTemplate, we might have done something like this:

<?php print render($action_links); ?>

And in Twig, the equivalent statement looks like this:

{{ action_links }}

Yes, the second line is shorter, but it also feels like it has more magic going on. If you’ve been begging to get your code streamlined, I think you’re going to love Twig. Even if you liked the PHPTemplate way of doing things, there are a lot of advantages we’ve gained with the upgrade to Twig.

  1. Twig allows us to simplify themes. You are welcome to embed simple logic statements right into your template files.
  2. Twig makes themes more secure. Even though you can embed logic into your template files, it’s not as powerful as PHPTemplate, as there is no PHP allowed in a Twig file. (Try it! You’ll get errors.)
  3. The team working on Twig has dramatically reduced the complexity of the entire theme system.

I have the utmost respect for those who worked on this process. They didn’t simply duct tape a new templating system onto Drupal. They took the time to carefully comb over Drupal and find the things that were confusing, outdated, or just didn’t belong.

Catégories: Elsewhere

Yuriy Gerasimov: Behat Drupal Extension 3 pass custom cUrl options to goutte driver

mar, 23/12/2014 - 12:38

Behat is great testing tool that there are already has a lot of documentation.

In drupal we have extension that helps us to build tests. Behat tests are configurable in yaml file (like url of your website and other options). Lately I needed to set custom cUrl options (goutte driver) and because Drupal extension 3 uses Guzzle 4 library it was not that obvious how to do that.

Trick is to check how Guzzle expects options and then place in behat.yml file in the following way:

Technically options being added at so if you need to make sure your options were passed, debug that function.

Hope this will save you some time.

Tags: behatdrupal planet
Catégories: Elsewhere

drunomics: High-quality Drupal 8 training material in German available for free!

mar, 23/12/2014 - 11:26

Last October Drupal Austria organized a full day long free workshop for getting started with Drupal 8 in Vienna. drunomics sponsored the event and I had the favour of presenting on Coding with Drupal 8. Meanwhile, Drupal Austria has got the recordings of the workshop up, the result: 4 hours of high-quality Drupal 8 training material in German:

The available tracks are:

Intro - by Nico Grienauer (grienauer)
Sitebuilding Part 1 - by Philipp Melab (pmelab) & Sebastian Siemssen (fubhy)
Sitebuilding Part 2 - by Philipp Melab (pmelab) & Sebastian Siemssen (fubhy)
Theming - by Christian Ziegler (criz)
Coding - by Wolfgang Ziegler (fago)
Entwicklungsumgebung - by Philipp Melab (pmelab) & Sebastian Siemssen (fubhy)

You can find the playlist with all recordings on Youtube here.

Catégories: Elsewhere

Drupal Association News: team week notes #30

lun, 22/12/2014 - 23:43

It’s been awhile since our last week notes post, but before a lot of you will go off to celebrate holidays, we wanted to tell you about some of the recent exciting changes on


As a New Year’s present to all visitors, today we deployed the initial responsive version of Bluecheese theme. This means that will now look much better on small and large screens. subsites on Drupal 7, such as and, will follow as they are tested.

The work on responsifying the theme started at Drupal Dev Days in Szeged earlier this year, with the final testing happening during BadCamp in November.

We’d like to thank our wonderful volunteers for making this happen:
LewisNyman, dasjo, emma.maria, mallezie, Manuel Garcia, sqndr, thamas.

This is the initial deployment, though more page-by-page improvements will be coming. is a big site, with lots of pages that will need specific mobile-first design changes.

Improved user profiles

During the last few months we’ve been slowly migrating user profile fields to Field API fields, which gives us more flexibility to improve profile pages. While migrating the fields, we started to rearrange layout of user profiles. A lot more work will happen on layouts now that field migration is complete, but even now you can see that profiles look much better.

One particular change which happened during fields migration is the ‘My mentors’ field layout. Previous it was just a list of blue links, but now we actually show user pictures of mentors.

New database servers’s database servers were due for a hardware refresh. New hardware was purchased, provisioned and deployed for that has improved page response times across the site. The new hardware brings solid state drives, and quadruples the amount of processors and memory.

As always, we’d like to say thanks to all volunteers who are working with us and to the Drupal Association Supporters, who made it possible for us to work on these projects.

Follow us on Twitter for regular updates: @drupal_org, @drupal_infra


Happy Holidays! Personal blog tags: week notes
Catégories: Elsewhere

EchoDitto Tech Blog: OS X 10.10 Yosemite Local Development Environment: Apache, PHP, and MySQL with Homebrew

lun, 22/12/2014 - 22:38

OS X 10.10 Yosemite comes with Apache and PHP pre-installed, but it's not in a great configuration, requires root to make lots of changes, and can introduce issues with file ownership and permissions. We prefer to use Homebrew to avoid these problems and because it's easier to keep up to date with newer versions of each component and extend customization. We can also set things up to be fully automatic so you can create new websites locally without needing to edit any configuration files.

With the arrival of Yosemite, some of the changes previously used in 10.9 for setting up Apache, PHP, and MySQL with Homebrew don't work quite the same. This guide will walk you through using Homebrew to install Apache, PHP, and MySQL for a "MAMP" development environment. We'll also use DNSMasq and Apache's VirtualDocumentRoot to set up "auto-VirtualHosts" so you don't need to edit configuration files when starting new projects. Finally, we'll add a firewall rule to allow the default http port 80 to be used without running Apache as root.

The following steps are intended for use on a Yosemite system without any previous attempts to use Homebrew for Apache, PHP, or MySQL. If you have attempted to install a similar stack and run into conflicts, or you've upgraded your operating system from 10.9 and things broke, the final section has some troubleshooting pointers. If that fails, leave a comment and I'll try my best to help you out.

At the conclusion of this guide, you'll be able to create a directory like ~/Sites/project and access it immediately at without editing your /etc/hosts file or editing any Apache configuration. We'll configure PHP and MySQL to allow for enough flexibility for development.

Because some of the commands span several lines, each command will be in a separate code block. This means you should copy and paste each code block in its entirety as a single command.

Before diving in, yes, this is a lot of steps. You can do it faster and pay money for something like MAMP Pro, but this is more fun, and you may learn something along the way! And, while you can simplify things with Vagrant or other virtual machine format, some people prefer to run things on "bare metal" and not have the overhead of a virtual machine.

Homebrew Setup

If you've not already installed Homebrew, you can follow the instructions at the bottom of I used to include the command in previous walkthroughs, but it could change after posting, so definitely always check their website to install it properly.

If you do not have git available on your system, either from Homebrew, Xcode, or another source, you can install it with Homebrew now (if you already have it installed, feel free to skip this step to keep the version of git you already have):

brew install -v git PATH Variable

In previous guides on 10.9 and earlier, I added a change to $PATH in ~/.bash_profile to ensure that Homebrew-installed applications would run by default over similar ones that were already installed on OS X. Thankfully, Yosemite's $PATH order is different than earlier OS versions and now includes the default Homebrew location of /usr/local/bin in front. If you installed Homebrew to a custom location, or are not seeing /usr/local/bin at the beginning of your shell's $PATH, check out the file /etc/paths or the directory /etc/paths.d/.


Install MySQL with Homebrew:

brew install -v mysql

Copy the default my-default.cnf file to the MySQL Homebrew Cellar directory where it will be loaded on application start:

cp -v $(brew --prefix mysql)/support-files/my-default.cnf $(brew --prefix)/etc/my.cnf

This will configure MySQL to allow for the maximum packet size, only appropriate for a local or development server. Also, we'll keep each InnoDB table in separate files to keep ibdataN-type file sizes low and make file-based backups, like Time Machine, easier to manage multiple small files instead of a few large InnoDB data files. This is the first of many multi-line single commands. The following is a single, multi-line command; copy and paste the entire block at once:

cat >> $(brew --prefix)/etc/my.cnf <<'EOF'   # Echo & Co. changes max_allowed_packet = 1073741824 innodb_file_per_table = 1 EOF

Uncomment the sample option for innodb_buffer_pool_size to improve performance:

sed -i '' 's/^#[[:space:]]*\(innodb_buffer_pool_size\)/\1/' $(brew --prefix)/etc/my.cnf

Now we need to start MySQL using OS X's launchd, and we'll set it to start when you login. First, create the ~/Library/LaunchAgents folder if it doesn't already exist, copy the startup plist into it, and then start MySQL:

[[ ! -d ~/Library/LaunchAgents ]] && mkdir -v ~/Library/LaunchAgents ln -sfv $(brew --prefix mysql)/homebrew.mxcl.mysql.plist ~/Library/LaunchAgents/ launchctl load -Fw ~/Library/LaunchAgents/homebrew.mxcl.mysql.plist

By default, MySQL's root user has an empty password from any connection. You are advised to run mysql_secure_installation and at least set a password for the root user:

$(brew --prefix mysql)/bin/mysql_secure_installation Apache

Start by stopping the built-in Apache, if it's running, and prevent it from starting on boot. This is one of very few times you'll need to use sudo:

sudo launchctl unload /System/Library/LaunchDaemons/org.apache.httpd.plist 2>/dev/null

The formula for building Apache is not in the default Homebrew repository that you get by installing Homebrew. While we can use the format of brew install external-repo/formula, if an external formula relies on another external formula, you have to use the brew tap command first. I know, it's weird. So, we need to tap homebrew-dupes because "homebrew-apache/httpd22" relies on "homebrew-dupes/zlib". Whew:

brew tap homebrew/dupes

A slight deviation from my prior walkthroughs: we'll install Apache 2.2 with the event MPM and set up PHP-FPM instead of mod_php. If those terms mean anything to you and you're curious as to why I decided to go this route; it's because: 1) switching PHP versions is far easier with PHP-FPM and the default 9000 port instead of also editing the Apache configuration to switch the mod_php module location, and 2) if we're therefore not using mod_php, we don't have to use the prefork MPM and can get better performance with event or worker. As to why I'm using 2.2 instead of 2.4, popular FOSS projects like Drupal and WordPress still ship with 2.2-style .htaccess files. Using 2.4 sometimes means you have to set up "compat" modules, and that's above the requirement for a local environment, in my opinion.

Onward! Let's install Apache 2.2 with the event MPM, and we'll use Homebrew's OpenSSL library since it's more up-to-date than OS X's:

brew install -v homebrew/apache/httpd22 --with-brewed-openssl --with-mpm-event

In order to get Apache and PHP to communicate via PHP-FPM, we'll install the mod_fastcgi module:

brew install -v homebrew/apache/mod_fastcgi --with-brewed-httpd22

To prevent any potential problems with previous mod_fastcgi setups, let's remove all references to the mod_fastcgi module (we'll re-add the new version later):

sed -i '' '/fastcgi_module/d' $(brew --prefix)/etc/apache2/2.2/httpd.conf

Add the logic for Apache to send PHP to PHP-FPM with mod_fastcgi, and reference that we'll want to use the file ~/Sites/httpd-vhosts.conf to configure our VirtualHosts. The parenthesis are used to run the command in a subprocess, so that the exported variables don't persist in your terminal session afterwards. Also, you'll see export USERHOME a few times in this guide; I look up the full path for your user home directory from the operating system wherever a full path is needed in a configuration file and "~" or a literal "$HOME" would not work. This is all one command, so copy and paste the entire code block at once:

(export USERHOME=$(dscl . -read /Users/`whoami` NFSHomeDirectory | awk -F"\: " '{print $2}') ; export MODFASTCGIPREFIX=$(brew --prefix mod_fastcgi) ; cat >> $(brew --prefix)/etc/apache2/2.2/httpd.conf <<EOF   # Echo & Co. changes   # Load PHP-FPM via mod_fastcgi LoadModule fastcgi_module ${MODFASTCGIPREFIX}/libexec/   <IfModule fastcgi_module> FastCgiConfig -maxClassProcesses 1 -idle-timeout 1500   # Prevent accessing FastCGI alias paths directly <LocationMatch "^/fastcgi"> Order Deny,Allow Deny from All Allow from env=REDIRECT_STATUS </LocationMatch>   FastCgiExternalServer /php-fpm -host -pass-header Authorization -idle-timeout 1500 ScriptAlias /fastcgiphp /php-fpm Action php-fastcgi /fastcgiphp   # Send PHP extensions to PHP-FPM AddHandler php-fastcgi .php   # PHP options AddType text/html .php DirectoryIndex index.php index.html </IfModule>   # Include our VirtualHosts Include ${USERHOME}/Sites/httpd-vhosts.conf EOF )

We'll be using the file ~/Sites/httpd-vhosts.conf to configure our VirtualHosts, but the ~/Sites folder doesn't exist by default in newer versions of OS X. We'll also create folders for logs and SSL files:

mkdir -pv ~/Sites/{logs,ssl}

Let's populate the ~/Sites/httpd-vhosts.conf file. The biggest difference from my previous guides are that you'll see the port numbers are 8080/8443 instead of 80/443. OS X 10.9 and earlier had the ipfw firewall which allowed for port redirecting, so we would send port 80 traffic "directly" to our Apache. But ipfw is now removed and replaced by pf which "forwards" traffic to another port. We'll get to that later, but know that "8080" and "8443" are not typos but are acceptable because of later port forwarding. Also, I've now added a basic SSL configuration (though you'll need to acknowledge warnings in your browser about self-signed certificates):

touch ~/Sites/httpd-vhosts.conf (export USERHOME=$(dscl . -read /Users/`whoami` NFSHomeDirectory | awk -F"\: " '{print $2}') ; cat > ~/Sites/httpd-vhosts.conf <<EOF # # Listening ports. # #Listen 8080 # defined in main httpd.conf Listen 8443   # # Use name-based virtual hosting. # NameVirtualHost *:8080 NameVirtualHost *:8443   # # Set up permissions for VirtualHosts in ~/Sites # <Directory "${USERHOME}/Sites"> Options Indexes FollowSymLinks MultiViews AllowOverride All Order allow,deny Allow from all </Directory>   # For http://localhost in the users' Sites folder <VirtualHost _default_:8080> ServerName localhost DocumentRoot "${USERHOME}/Sites" </VirtualHost> <VirtualHost _default_:8443> ServerName localhost Include "${USERHOME}/Sites/ssl/" DocumentRoot "${USERHOME}/Sites" </VirtualHost>   # # VirtualHosts #   ## Manual VirtualHost template for HTTP and HTTPS #<VirtualHost *:8080> # ServerName # CustomLog "${USERHOME}/Sites/logs/" combined # ErrorLog "${USERHOME}/Sites/logs/" # DocumentRoot "${USERHOME}/Sites/" #</VirtualHost> #<VirtualHost *:8443> # ServerName # Include "${USERHOME}/Sites/ssl/" # CustomLog "${USERHOME}/Sites/logs/" combined # ErrorLog "${USERHOME}/Sites/logs/" # DocumentRoot "${USERHOME}/Sites/" #</VirtualHost>   # # Automatic VirtualHosts # # A directory at ${USERHOME}/Sites/webroot can be accessed at # In Drupal, uncomment the line with: RewriteBase / #   # This log format will display the per-virtual-host as the first field followed by a typical log line LogFormat "%V %h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combinedmassvhost   # Auto-VirtualHosts with .dev <VirtualHost *:8080> ServerName dev ServerAlias *.dev   CustomLog "${USERHOME}/Sites/logs/dev-access_log" combinedmassvhost ErrorLog "${USERHOME}/Sites/logs/dev-error_log"   VirtualDocumentRoot ${USERHOME}/Sites/%-2+ </VirtualHost> <VirtualHost *:8443> ServerName dev ServerAlias *.dev Include "${USERHOME}/Sites/ssl/"   CustomLog "${USERHOME}/Sites/logs/dev-access_log" combinedmassvhost ErrorLog "${USERHOME}/Sites/logs/dev-error_log"   VirtualDocumentRoot ${USERHOME}/Sites/%-2+ </VirtualHost> EOF )

You may have noticed that ~/Sites/ssl/ is included multiple times; create that file and the SSL files it needs:

(export USERHOME=$(dscl . -read /Users/`whoami` NFSHomeDirectory | awk -F"\: " '{print $2}') ; cat > ~/Sites/ssl/ <<EOF SSLEngine On SSLProtocol all -SSLv2 -SSLv3 SSLCipherSuite ALL:!ADH:!EXPORT:!SSLv2:RC4+RSA:+HIGH:+MEDIUM:+LOW SSLCertificateFile "${USERHOME}/Sites/ssl/selfsigned.crt" SSLCertificateKeyFile "${USERHOME}/Sites/ssl/private.key" EOF ) openssl req \ -new \ -newkey rsa:2048 \ -days 3650 \ -nodes \ -x509 \ -subj "/C=US/ST=State/L=City/O=Organization/OU=$(whoami)/CN=*.dev" \ -keyout ~/Sites/ssl/private.key \ -out ~/Sites/ssl/selfsigned.crt Start Apache

Start Homebrew's Apache and set to start on login:

ln -sfv $(brew --prefix httpd22)/homebrew.mxcl.httpd22.plist ~/Library/LaunchAgents launchctl load -Fw ~/Library/LaunchAgents/homebrew.mxcl.httpd22.plist Run with port 80

You may notice that httpd.conf is running Apache on ports 8080 and 8443. Manually adding ":8080" each time you're referencing your dev sites is no fun, but running Apache on port 80 requires root. The next two commands will create and load a firewall rule to forward port 80 requests to 8080, and port 443 requests to 8443. The end result is that we don't need to add the port number when visiting a project dev site, like "" instead of "".

The following command will create the file /Library/LaunchDaemons/co.echo.httpdfwd.plist as root, and owned by root, since it needs elevated privileges:

sudo bash -c 'export TAB=$'"'"'\t'"'"' cat > /Library/LaunchDaemons/co.echo.httpdfwd.plist <<EOF <?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" ""> <plist version="1.0"> <dict> ${TAB}<key>Label</key> ${TAB}<string>co.echo.httpdfwd</string> ${TAB}<key>ProgramArguments</key> ${TAB}<array> ${TAB}${TAB}<string>sh</string> ${TAB}${TAB}<string>-c</string> ${TAB}${TAB}<string>echo "rdr pass proto tcp from any to any port {80,8080} -> port 8080" | pfctl -a "" -Ef - &amp;&amp; echo "rdr pass proto tcp from any to any port {443,8443} -> port 8443" | pfctl -a "" -Ef - &amp;&amp; sysctl -w net.inet.ip.forwarding=1</string> ${TAB}</array> ${TAB}<key>RunAtLoad</key> ${TAB}<true/> ${TAB}<key>UserName</key> ${TAB}<string>root</string> </dict> </plist> EOF'

This file will be loaded on login and set up the 80->8080 and 443->8443 port forwards, but we can load it manually now so we don't need to log out and back in:

sudo launchctl load -Fw /Library/LaunchDaemons/co.echo.httpdfwd.plist PHP

The following is for the latest release of PHP, version 5.6. If you'd like to use 5.3, 5.4 or 5.5, simply change the "5.6" and "php56" values below appropriately.

Install PHP and PHP-FPM. Excluding snmp is a workaround for a problem specific to Yosemite:

brew install -v homebrew/php/php56 --with-fpm --without-snmp

Set timezone and change other PHP settings (sudo is needed here to get the current timezone on OS X) to be more developer-friendly, and add a PHP error log (without this, you may get Internal Server Errors if PHP has errors to write and no logs to write to):

(export USERHOME=$(dscl . -read /Users/`whoami` NFSHomeDirectory | awk -F"\: " '{print $2}') ; sed -i '-default' -e 's|^;\(date\.timezone[[:space:]]*=\).*|\1 \"'$(sudo systemsetup -gettimezone|awk -F"\: " '{print $2}')'\"|; s|^\(memory_limit[[:space:]]*=\).*|\1 512M|; s|^\(post_max_size[[:space:]]*=\).*|\1 200M|; s|^\(upload_max_filesize[[:space:]]*=\).*|\1 100M|; s|^\(default_socket_timeout[[:space:]]*=\).*|\1 600|; s|^\(max_execution_time[[:space:]]*=\).*|\1 300|; s|^\(max_input_time[[:space:]]*=\).*|\1 600|; $a\'$'\n''\'$'\n''; PHP Error log\'$'\n''error_log = '$USERHOME'/Sites/logs/php-error_log'$'\n' $(brew --prefix)/etc/php/5.6/php.ini)

Fix a pear and pecl permissions problem:

chmod -R ug+w $(brew --prefix php56)/lib/php

Until this pull request is merged, set the location of php_ini in pear to $(brew --prefix)/etc/php/5.6/pear.conf:

pear config-set php_ini $(brew --prefix)/etc/php/5.6/php.ini system

The included Opcache extension will speed up your PHP environment dramatically, and it's already installed, but needs to be enabled. We'll also bump up the opcache memory limit:

sed -i '' "s|^\(\[opcache\]\)$|\1"\\$'\n'"; Load the opcache extension"\\$'\n'""\\$'\n'"|; s|^;\(opcache\.enable[[:space:]]*=[[:space:]]*\)0|\11|; s|^;\(opcache\.memory_consumption[[:space:]]*=[[:space:]]*\)[0-9]*|\1256|;" $(brew --prefix)/etc/php/5.6/php.ini

If you're not using PHP 5.5 or 5.6 and wish to add the opcache extension: See

Finally, let's put the PHP-FPM launchd plist file in place and start PHP-FPM now:

ln -sfv $(brew --prefix php56)/*.plist ~/Library/LaunchAgents launchctl load -Fw ~/Library/LaunchAgents/homebrew.mxcl.php56.plist

Optional: At this point, if you want to switch between PHP versions, you'd want to stop PHP-FPM by unloading the plist above, run brew unlink php56, repeat all of the above PHP steps for php55/php54/php53, and loading the new plist. No need to touch the Apache configuration at all!


A difference now between what I've shown before, is that we don't have to run on port 53 or run dnsmasq as root. The end result here is that any DNS request ending in .dev reply with the IP address

brew install -v dnsmasq echo 'address=/.dev/' > $(brew --prefix)/etc/dnsmasq.conf echo 'listen-address=' >> $(brew --prefix)/etc/dnsmasq.conf echo 'port=35353' >> $(brew --prefix)/etc/dnsmasq.conf

Similar to how we run Apache and PHP-FPM, we'll symlink a launchd plist to ~/Library/LaunchAgents and start:

ln -sfv $(brew --prefix dnsmasq)/homebrew.mxcl.dnsmasq.plist ~/Library/LaunchAgents launchctl load -Fw ~/Library/LaunchAgents/homebrew.mxcl.dnsmasq.plist

With DNSMasq running, configure OS X to use your local host for DNS queries ending in .dev:

sudo mkdir -v /etc/resolver sudo bash -c 'echo "nameserver" > /etc/resolver/dev' sudo bash -c 'echo "port 35353" >> /etc/resolver/dev'

To test, the command ping -c 3 should return results from If it doesn't work right away, try turning WiFi off and on (or unplug/plug your ethernet cable), or reboot your system.

Great! So, what did I do?

We set up Apache to run on boot on ports 8080 and 8443 with auto-VirtualHosts for directories in the ~/Sites folder and PHP-FPM via mod_fastcgi. The OS X firewall will forward all port 80 traffic to port 8080 and port 443 to port 8443, so we don't have specify the port number when visiting web pages in local web browsers or run Apache as root. MySQL is installed and set to run on boot as well. DNSMasq and some OS X configuration is used to direct any hostname ending in .dev to the local system to work in conjunction with Apache's auto-VirtualHosts.

What do I do now?

You shouldn't need to edit the Apache configuration or edit /etc/hosts for new local development sites. Simply create a directory in ~/Sites and then reference "http://" + that foldername + ".dev/" in your browser to access it.

For example, download Drupal 7 to the directory ~/Sites/firstproject, and it can then be accessed at without any additional configuration. A caveat - you will need to uncomment the line in Drupal's .htaccess containing "RewriteBase /" to work with the auto-VirtualHosts configuration.

What if this "auto-VirtualHost" doesn't work for [other project]?

If you need to create a manual VirtualHost in Apache because the auto-VirtualHost does not work for your configuration, you will need to declare it before the auto-VirtualHosts if you're also going to use .dev as the TLD. Otherwise the auto-VirtualHost block will be accessed first. I have a commented-out sample for a manual VirtualHost entry in "~/Sites/httpd-vhosts.conf" you may use.


The commands above can be run on a fresh Yosemite system without issue as I've tested with fresh installs in VMware. Nearly every problem I've heard about has been related to upgrading from 10.9 or earlier, or switching to this style of setup from another or similar setup. The easiest thing to do would be to brew uninstall each component referenced above, delete all related config files in $(brew --prefix)/etc and ~/Library/LaunchAgents, and start over. If that's a bit heavy-handed, check each of the configuration files edited in this guide and look for duplicate entries or typos.

You can also check log files for error output:

  • Apache: $(brew --prefix)/var/log/apache2/error_log, or run httpd -DFOREGROUND and look for output
  • PHP-FPM: $(brew --prefix)/var/log/php-fpm.log
  • MySQL: $(brew --prefix)/var/mysql/$(hostname).err
  • DNSMasq: no log file, run dnsmasq --keep-in-foreground and look for output

Leave a comment if you have any questions or problems!

Tags: drupalmamplocal development environmentphpapachemysqlhomebrewdnsmasq
Catégories: Elsewhere

Oliver Davies: Configuring the Reroute Email module

lun, 22/12/2014 - 22:35

Reroute Email module uses hook_mail_alter() to prevent emails from being sent to users from non-production sites. It allows you to enter one or more email addresses that will receive the emails instead of delivering them to the original user.

Catégories: Elsewhere

Commerce Guys: Webinar Wrap-Up

lun, 22/12/2014 - 21:34

Whew! 2014 is almost in the books. We wanted to take a moment to say thank you to everyone who attended live or watched a recording of one of our webinars, and provide a recap of all we learned throughout the year. We held 12 Webinars last year on a wide range of topics. We introduced you to new technology partners and showcased beautiful and innovative Drupal Commerce sites. We discussed the upcoming transition to PCI version 3.0 and talked about a new breed of eCommerce sites, focused on the merging of Content & Commerce.

We also kicked off a new type of webinar series, focused on the unique technical aspects of Drupal Commerce. We held 6 Drupal Commerce Tech Talks and covered features and functionality to enhance and redefine how eCommerce is done with Drupal.

And we launched a new cloud development and hosting solution,, and managed to do several live demos (including ones in German and French!) All in all, it was a hugely successful year for our webinar series...and we’re looking forward to continuing that trend in 2015.

We invite you to browse our entire archive, recapped here for you in the form of little gifts that you can give yourself at your own pace. We hope you will find it to be a valuable resource to you in your continued work with Drupal Commerce.

Happy Unwrapping

Catégories: Elsewhere