Version 6 (modified by Bart, 10 years ago) (diff)

Install a Drupal module with git

Gitification of Indymedia linksunten


Until May 2012,Indymedia linksunten used the Good Old Fashioned Way™ to keep track of upstream changes to it's Drupal (in fact: Pressflow) core and modules: drush dl mymodule. At least in theory. In reality, the core has been patched twice, many modules even more and some self-written modules do not even exist in a public drupal repository. linksunten has some 80 modules installed and keeping track of updates is wearisome for the non-patched modules and troublesome for the patched ones. We learned that a version control system could ease the error-prone update procedure and as has switched to git we decided to do the same.

Since a Drupal website is not a monolithic bloc and nearly each module is maintained by different developers we needed to find a way to update the core and each module separately from one another. The traditional way git offers for this is a concept called git-submodule. It is complicated, unintuitive and detested by many for good reasons. But as git follows the TMTOWTDI paradigm we could avoid using git-submodule and settled for git-subtree instead which has recently been merged into git core. Besides the possibility to update the core and each module separately and replaying our patches to the updated version automatically, we want the linksunten code to be one git repository which simply "works" after cloning it. After our move to git we will use the features module to version control as much of our configuration data as possible.

Drupal core

We create a new directory, initialise git, tell git which name and email to use, create a temporary file which we commit, delete and commit again to create a master branch:

mkdir liu_d6
cd liu_d6
git init
git config "Indymedia linksunten"
git config "línksunten@índymedí"
touch liu_d6
git add liu_d6
git commit -m "Initial commit Indymedia linksunten Drupal 6."
git rm liu_d6
git commit -m "Created master branch."

We don't want the settings.php file in our repository as it contains database login credentials so we tell git to exclude it:

echo /settings.php >> .git/info/exclude

We add Pressflow 6 as a new remote and fetch it:

git remote add pressflow-6.x git:// master
git fetch pressflow-6.x

Now we can add Drupal core from our pressflow-6.x remote via git-subtree in a subdirectory core. We use the --squash parameter as we do not need the whole commit history of Pressflow in our master branch:

git subtree add --squash --prefix=core pressflow-6.x/drupal-6.26

As we are creating a production environment, we'll delete some of the unnecesary files:

git rm core/install.php core/*.txt
git commit -m "Delete install.php and text files from core directory."

We copy our settings.php to our repository directory, create a symbolic link from inside the core and delete the default.settings.php:

cp ~/settings.php .
cd core/sites/default
ln -s ../../../settings.php
git rm default.settings.php
cd ../../../
git add core/sites/default/settings.php
git commit "Add symbolic link to settings.php."

There are some more modifications to do but they are really linksunten specific (like applying the two core patches via git am which have been created via git format-patch before) so we leave them out.

Drupal modules

Normally, Drupal modules are installed under sites/default/modules. This would be fine with our approach but it would create unnecessary huge merges when updating the core and it keeping all parts separately accessible from the root directory of our installation is much clearer arranged. So we create a modules (and perhaps also a files, libraries and themes) directory and a symbolic link to it:

mkdir modules
cd core/sites/default
ln -s ../../../modules
cd ../../../

Now we install a module in it. As an example we chose the i18n module. At the Drupal project page we click on the green "Version Control" tab and chose "Version to work from: 6.x-1.x". There we get the URL we need to add the project as a remote.

git remote add i18n-6.x-1.x 6.x-1.x
git fetch

Now we do not install the latest version 6.x-1.10 but version 6.x-1.9. The reason is that we have patched that version and we want to use git-subtree and git-rebase to reapply our patches to the newest version. First, we install 6.x-1.9:

git subtree add --squash --prefix="modules/i18n" 6.x-1.9

Then we overwrite the newly imported files with our patched version and commit the patches. At this point, interactive staging might be a good idea.

cp ~/i18n.module modules/i18n
cp ~/i18nsync.module modules/i18n
git add modules/i18n/
git commit -m "i18n: Exchange title with nid in translation box."
git add modules/i18n/i18nsync/i18nsync.module
git commit -m "i18n: Inherit path when syncing."

As our core directory is not empty, we can add the symbolic link to our modules directory:

git add core/sites/default/modules
git commit -m "Add symbolic link to modules directory."

Update a patched module