This article will give you the tools to setup fully automated an apache solr multicore locally for drupal.
The advantages: When you have new projects you will only have to create a new apache solr core based on previous configuration. This will save you valuable time.
How does it work? Whatever we have done manually we can script using bash. This is exactly what we have done to install the apache solr multicore locally.
The script depends on drush and curl. The script will detect these dependencies and will try to download them.
Here is the script to install apachesolr and setup the multicore. We will use a second script to setup our cores later.
#!/bin/bash
#Validate if the executing user is root
if [ "$(id -u)" != "0" ]; then
echo "This script must be run as root" 1>&2
exit 1
fi
# ********* #
# Functions #
# ********* #
#Install drush
function install_drush () {
version=$1
# Set tag to latest of each version
drush5_tag='5.10.0'
drush6_tag='6.2.0'
drush7_tag='master' # drush 7 doesn't have a stable release tag yet - 12/01/2013
case "$version" in
5)
if [[ `php -r "echo version_compare(PHP_VERSION,'5.2.0','>=') ? '1' : '0';"` == '1' ]];
then
drush_tag=$drush5_tag
else
echo -e "\e[00;31m ERROR:You cannot install drush 5 with PHP less than 5.2.0. Please update PHP. \e[00m"
return 1
fi
;;
6)
if [[ `php -r "echo version_compare(PHP_VERSION,'5.3.0','>=') ? '1' : '0';"` == '1' ]];
then
drush_tag=$drush6_tag
else
echo -e "\e[00;31m ERROR:You cannot install drush 6 with PHP less than 5.3.0. Please update PHP. \e[00m"
return 1
fi
;;
7)
if [[ `php -r "echo version_compare(PHP_VERSION,'5.3.0','>=') ? '1' : '0';"` == '1' ]];
then
drush_tag=$drush7_tag
else
echo -e "\e[00;31m ERROR:You cannot install drush 7 with PHP less than 5.3.0. Please update PHP. \e[00m"
return 1
fi
;;
esac
# Set the file to be downloaded
drush_zip="${drush_tag}.zip"
# Set the URL for the file to be downloaded
drush_url="http://github.com/drush-ops/drush/archive/${drush_zip}"
# Set the directory for the files to be extracted to
drush_dir="/opt/drush${version}"
# Download the files to /tmp
wget -nc $drush_url -O /tmp/drush-${drush_zip}
# Extract the files to their proper place
unzip /tmp/drush-${drush_zip} -d ${drush_dir}/
# Link them so they are usable
drush_bin="/usr/local/bin/drush${version}"
ln -s ${drush_dir}/drush $drush_bin
# Run drush once to make sure all libraries are downloaded
$drush_bin > /dev/null &2>1
echo -e "\e[00;33m NOTICE:Drush $version installed \e[00m"
return 0
}
function set_primary_drush () {
version=$1
if [ -f /usr/local/bin/drush${version} ]
then
ln -fs /usr/local/bin/drush${version} /usr/local/bin/drush
else
echo "/usr/local/bin/drush${version} does not exist! Have you installed drush ${version} yet?"
exit
fi
}
#Test the connection to the solr installation
function solr_install_test_connection {
response=$(curl --write-out %{http_code} --silent --output /dev/null http://127.0.0.1:8983/solr/)
if [ $response != 200 ]; then
echo -e "\e[00;31m ERROR:Solr installation failed manual intervention needed. Solr reponds at http://127.0.0.1:8983/solr/ with http code: $reponse \e[00m"
else
echo -e "\e[00;32m NOTICE:Solr reponds at http://127.0.0.1:8983/solr/ with http code:$response \e[00m"
fi
}
# ****** #
# Script #
# ****** #
#Install the needed sources if needed: drush, curl and java
DRUSH=`command -v drush`
if [ -z "$DRUSH" ]; then
install_drush 5
install_drush 6
install_drush 7
set_primary_drush 6
else
echo -e "\e[00;33m WARNING:Drush already installed at '$DRUSH' \e[00m"
fi
CURL=`command -v curl`
if [ -z "$CURL" ]; then
yum install curl
echo -e "\e[00;33m NOTICE:Curl installed \e[00m"
else
echo -e "\e[00;33m WARNING:Curl already installed at '$CURL' \e[00m"
fi
JAVA=`command -v java`
if [ -z "$JAVA" ]; then
yum install java-1.6.0-openjdk
echo -e "\e[00;32m NOTICE:Java installed \e[00m"
else
echo -e "\e[00;33m WARNING:Java already installed at '$JAVA' \e[00m"
fi
SOLR_VERSION='4.6.0'
# Download Solr
SOURCE=solr-${SOLR_VERSION}.tgz
FOLDER=solr-${SOLR_VERSION}
FILE=/opt/$SOURCE
if [ ! -e $FILE ]; then
mkdir -p /opt
cd /opt
wget -nc http://apache.tradebit.com/pub/lucene/solr/${SOLR_VERSION}/${SOURCE}
echo -e "\e[00;32m NOTICE:Sources downloaded \e[00m"
else
echo -e "\e[00;33m WARNING:Source already downloaded. skipping \e[00m"
fi
# Extract Solr
SOLR_HOME=/opt/$FOLDER
if [ ! -d $SOLR_HOME ]; then
echo -e "\e[00;32m NOTICE:Extracting sources \e[00m"
cd /opt
tar xzf solr-4.6.0.tgz
echo -e "\e[00;32m NOTICE:Apachesolr dir created \e[00m"
else
echo -e "\e[00;33m WARNING:Apachesolr dir already exists, skipping \e[00m"
fi
# Create the solr multicore structure, and base core to copy later
SOLR_HOME_DRUPAL=${SOLR_HOME}/drupal
if [ ! -d $SOLR_HOME_DRUPAL ]; then
mkdir -p ${SOLR_HOME_DRUPAL}/cores/core0/conf
# Copy the necessary files and folders
cp -rf ${SOLR_HOME}/example/{contexts,etc,lib,resources,start.jar,webapps} ${SOLR_HOME_DRUPAL}/
cp -rf ${SOLR_HOME}/example/solr/collection1/conf/* ${SOLR_HOME_DRUPAL}/cores/core0/conf
echo -e "\e[00;32m NOTICE:Drupalsolr dir created \e[00m"
else
echo -e "\e[00;33m WARNING:Drupalsolr dir already exists, skipping \e[00m"
fi
# Create the discovery solr.xml file
FILE=${SOLR_HOME_DRUPAL}/cores/solr.xml
if [ -e $FILE ]; then
NEW=`grep core0 ${FILE} 2>dev/null 1>&2`
if [ -z "$NEW" ]; then
rm ${FILE}
fi
fi
if [ ! -e $FILE ]; then
echo '<solr></solr>' > ${FILE}
echo -e "\e[00;32m NOTICE:Solr.xml multicore setup complete \e[00m"
else
echo -e "\e[00;33m WARNING:Solr.xml already installed, skipping \e[00m"
fi
## APACHESOLR Drupal module setup
cd ${SOLR_HOME_DRUPAL}
DIR=${SOLR_HOME_DRUPAL}/apachesolr
if [ ! -d $DIR ]; then
# Download drupal module so we can use the correct configuration
drush dl apachesolr
cd $DIR
# Create the core conf directory
apachesolr_version=$(grep version ${DIR}/apachesolr.info | sed -e 's#version = "\([^"]\+\)"#\1#g')
apachesolr_solrdir='base_apachesolr-'${apachesolr_version}'_conf'
if [ ! -d ${SOLR_HOME_DRUPAL}/cores/${apachesolr_solrdir}/conf ]; then
mkdir -p ${SOLR_HOME_DRUPAL}/cores/${apachesolr_solrdir}/conf
# We'll need to patch the solrconfig.xml first because of changes in solr 4.5+
wget -nc http://drupal.org/files/2107417-2.patch
patch -p1 < 2107417-2.patch
# And copy the necessary stock configuration files
cp -r ${SOLR_HOME}/example/solr/collection1/conf/{elevate.xml,mapping-ISOLatin1Accent.txt,stopwords.txt,synonyms.txt} ${SOLR_HOME_DRUPAL}/cores/${apachesolr_solrdir}/conf/
# Then copy the module's config files over
cp -rfb ${DIR}/solr-conf/solr-4.x/* ${SOLR_HOME_DRUPAL}/cores/${apachesolr_solrdir}/conf/
# Rename the directory with the version, for posterity
mv ${DIR} ${DIR}-${apachesolr_version}
echo -e "\e[00;32m NOTICE:Apachesolr ${apachesolr_version} settings installed \e[00m"
else
echo -e "\e[00;33m WARNING:Apachesolr settings already there, skipping \e[00m"
fi
else
rm -rf $DIR
fi
# Do the same for search_api_solr
## SEARCH_API_SOLR Drupal module setup
cd ${SOLR_HOME_DRUPAL}
DIR=${SOLR_HOME_DRUPAL}/search_api_solr
if [ ! -d $DIR ]; then
# Download drupal module so we can use the correct configuration
drush dl search_api_solr
cd $DIR
# Create the core conf directory
search_api_solr_version=$(grep version ${DIR}/search_api_solr.info | sed -e 's#version = "\([^"]\+\)"#\1#g')
search_api_solr_solrdir='base_search_api_solr-'${search_api_solr_version}'_conf'
if [ ! -d ${SOLR_HOME_DRUPAL}/cores/${search_api_solr_solrdir}/conf ]; then
mkdir -p ${SOLR_HOME_DRUPAL}/cores/${search_api_solr_solrdir}/conf
# We'll need to patch the solrconfig.xml first because of changes in solr 4.5+
wget -nc http://drupal.org/files/issues/2122391-2.patch
patch -p1 < 2122391-2.patch
# Then copy the module's config files over
cp -rfb ${DIR}/solr-conf/4.x/* ${SOLR_HOME_DRUPAL}/cores/${search_api_solr_solrdir}/conf/
# Rename the directory with the version, for posterity
mv ${DIR} ${DIR}-${search_api_solr_version}
echo -e "\e[00;32m NOTICE:Search API Solr ${search_api_solr_version} settings installed \e[00m"
else
echo -e "\e[00;33m WARNING:Search API Solr settings already there, skipping \e[00m"
fi
else
rm -rf $DIR
fi
#Create the start|stop|restart script /etc/init.d/solr4
INIT_FILE=/etc/init.d/solr4
if [ ! -e $INIT_FILE ]; then
echo '#!/bin/sh -e
# Starts, stops, and restarts Apache Solr.
#
# chkconfig: 2345 64 36
# description: Starts and stops Apache Solr
SOLR_DIR="'${SOLR_HOME_DRUPAL}'"
JAVA_BIN="/usr/bin/java"
JAVA_HEAP="-Xmx1024m"
JETTY_STOP_OPTIONS="-DSTOP.PORT=8079 -DSTOP.KEY=stopkey"
JETTY_PORT="-Djetty.port=8983"
SOLR_HOME="-Dsolr.solr.home=cores"
JAVA_OPTIONS="$JAVA_HEAP $JETTY_STOP_OPTIONS $JETTY_PORT $SOLR_HOME"
LOG_FILE="/var/log/solr/solr.log"
COMMAND="$JAVA_BIN $JAVA_OPTIONS -jar start.jar"
case $1 in
start)
echo "Starting Solr '${SOLR_VERSION}'"
cd $SOLR_DIR
$COMMAND 1>&2 2> $LOG_FILE &
;;
stop)
echo "Stopping Solr '${SOLR_VERSION}'"
cd $SOLR_DIR
$COMMAND --stop
;;
restart)
$0 stop
sleep 1
$0 start
;;
*)
echo "Usage: $0 {start|stop|restart}" >&2
exit 1
;;
esac' > ${INIT_FILE}
#Set permissions
chmod a+rx ${INIT_FILE}
chkconfig --add $(basename ${INIT_FILE})
${INIT_FILE} start
sleep 5
#verify the connection
solr_install_test_connection
echo -e "\e[00;32m NOTICE:Solr installation completed \e[00m"
else
echo -e "\e[00;33m WARNING:Solr already installed, skipping \e[00m"
fi
#Exit output
echo -e '\e[00;32m Use the solr-instance script to install cores for your project. Execute sudo "./create-solr-instance.sh". \e[00m'
How to use it?
Create a file called solr-install.sh and paste the above code in it. Then execute as root:
If everything goes as planned you will see this:
Create solr multicore instances with this script
#!/bin/bash
#Validate if executing user is root
if [ "$(id -u)" != "0" ]; then
echo "This script must be run as root" 1>&2
exit 1
fi
PROJECT=$1
SOLR_MODULE=${2:-apachesolr}
SOLR_MODULE_VERSION=${3:-'7.x-1.6'}
SOLR_VERSION='4.6.0'
FOLDER=solr-${SOLR_VERSION}
SOLR_HOME=/opt/$FOLDER
SOLR_HOME_DRUPAL=${SOLR_HOME}/drupal
if [[ -z $PROJECT ]]; then
echo -e "\e[00;31m please provide a projectname as 1st variable \e[00m"
echo -e "\e[00;31m please provide an optional 2nd var to indicate to use the apachesolr or search_api_solr drupal module configuration, and the drupal module version as 3rd variable \e[00m"
echo ' '
exit
else
echo ' '
echo '*************Solr core creation started**************'
echo ' '
fi
# ******** #
# Functions #
# ******** #
function apachesolr_config {
## APACHESOLR Drupal module setup
cd ${SOLR_HOME_DRUPAL}
DIR=${SOLR_HOME_DRUPAL}/apachesolr
if [ ! -d $DIR ]; then
# Download drupal module so we can use the correct configuration
drush dl apachesolr-${SOLR_MODULE_VERSION}
mv apachesolr apachesolr-${SOLR_MODULE_VERSION}
DIR=${DIR}-${SOLR_MODULE_VERSION}
cd $DIR
# Create the core conf directory
apachesolr_version=$(grep version ${DIR}/apachesolr.info | sed -e 's#version = "\([^"]\+\)"#\1#g')
apachesolr_solrdir='base_apachesolr-'${apachesolr_version}'_conf'
if [ ! -d ${SOLR_HOME_DRUPAL}/cores/${apachesolr_solrdir}/conf ]; then
mkdir -p ${SOLR_HOME_DRUPAL}/cores/${apachesolr_solrdir}/conf
# We'll need to patch the solrconfig.xml first because of changes in solr 4.5+
wget -nc http://drupal.org/files/2107417-2.patch
patch -p1 < 2107417-2.patch
# And copy the necessary stock configuration files
cp -r ${SOLR_HOME}/example/solr/collection1/conf/{elevate.xml,mapping-ISOLatin1Accent.txt,stopwords.txt,synonyms.txt} ${SOLR_HOME_DRUPAL}/cores/${apachesolr_solrdir}/conf/
# Then copy the module's config files over
cp -rfb ${DIR}/solr-conf/solr-4.x/* ${SOLR_HOME_DRUPAL}/cores/${apachesolr_solrdir}/conf/
echo -e "\e[00;32m NOTICE:Apachesolr ${apachesolr_version} settings installed \e[00m"
else
echo -e "\e[00;33m WARNING:Apachesolr settings already there, skipping \e[00m"
fi
else
rm -rf $DIR
fi
}
function search_api_solr_config {
## SEARCH_API_SOLR Drupal module setup
cd ${SOLR_HOME_DRUPAL}
DIR=${SOLR_HOME_DRUPAL}/search_api_solr
if [ ! -d $DIR ]; then
# Download drupal module so we can use the correct configuration
drush dl search_api_solr-${SOLR_MODULE_VERSION}
mv search_api_solr search_api_solr-${SOLR_MODULE_VERSION}
DIR=${DIR}-${SOLR_MODULE_VERSION}
cd $DIR
# Create the core conf directory
search_api_solr_version=$(grep version ${DIR}/search_api_solr.info | sed -e 's#version = "\([^"]\+\)"#\1#g')
search_api_solr_solrdir='base_search_api_solr-'${search_api_solr_version}'_conf'
if [ ! -d ${SOLR_HOME_DRUPAL}/cores/${search_api_solr_solrdir}/conf ]; then
mkdir -p ${SOLR_HOME_DRUPAL}/cores/${search_api_solr_solrdir}/conf
# We'll need to patch the solrconfig.xml first because of changes in solr 4.5+
wget -nc http://drupal.org/files/issues/2122391-2.patch
patch -p1 < 2122391-2.patch
# Then copy the module's config files over
cp -rfb ${DIR}/solr-conf/4.x/* ${SOLR_HOME_DRUPAL}/cores/${search_api_solr_solrdir}/conf/
echo -e "\e[00;32m NOTICE:Search API Solr ${search_api_solr_version} settings installed \e[00m"
else
echo -e "\e[00;33m WARNING:Search API Solr settings already there, skipping \e[00m"
fi
else
rm -rf $DIR
fi
}
#Test connection to apache solr
function solr_install_test_connection {
response=$(curl --write-out %{http_code} --silent --output /dev/null http://127.0.0.1:8983/solr/)
if [ $response != 200 ]; then
rm /etc/init.d/solr
echo -e "\e[00;31m ERROR:Solr installation failed manual intervention needed. Solr reponds at http://127.0.0.1:8983/solr/ with http code: $reponse \e[00m"
else
echo -e "\e[00;32m NOTICE:Solr reponds at http://127.0.0.1:8983/solr/ with http code:$response \e[00m"
fi
}
# ****** #
# Script #
# ****** #
#Variables
SOLR_CORES=${SOLR_HOME_DRUPAL}/cores
#Copy a preconfigured core to use as a basis for our (see solr-install.sh)
DIR="${SOLR_CORES}/${PROJECT}"
if [ -d $DIR ]; then
echo -e "\e[00;33m $DIR exists, skipping SOLR core creation\e[00m"
else
if [ $SOLR_MODULE == apachesolr ]; then
apachesolr_config
elif [ $SOLR_MODULE == search_api_solr ]; then
search_api_solr_config
else
echo -e "\e[00;32m NOTICE:Please enter only 'apachesolr' or 'search_api_solr'. You entered '$SOLR_MODULE' \e[00m"
exit
fi
cp -r ${SOLR_CORES}/base_${SOLR_MODULE}-${SOLR_MODULE_VERSION}_conf ${SOLR_CORES}/${PROJECT}
echo -e "\e[00;32m Solr core $PROJECT created in ${SOLR_CORES}/${PROJECT} \e[00m"
fi
# CREATE the core via CoreAdmin API
curl 'http://localhost:8983/solr/admin/cores?action=CREATE&name='${PROJECT}
sleep 5
solr_install_test_connection
#Exit output
echo -e "\e[00;32m Now you can use 'http://127.0.0.1:8983/solr/#/"$PROJECT"'.
Check out all your cores at http://127.0.0.1:8983/solr/#/~cores \e[00m"
How to use it?
./create-solr-instance.sh [projectname] [optional: apachesolr or search_api_solr] [required with module: module_version]
Use the second optional parameter if you want to install apache solr multicore for the module (suffix with d6 or d7). By default the settings from the module will be installed. So dont use the second param if you are using those modules.
./create-solr-instance.sh drupalsolrsite
You should get a result like this:
Go through this script piece by piece so you can learn some bash and learn to use this to your advantage. As drupal developers we are more or less php developers but learning some bash can be a great time saver. For example this script saved me countless hours. Everytime I had to install a multicore on a vm or on somebodies installation I m coaching, we are winning valueable time. You could even use this to control your production installation too.
Read the comments carefully and understand what every step does. We can be lazy by letting the automated scripts do the work for us but we can't allow ourselves to become stupid. You still need to understand what happens. You will need to know how it works because automated stuff always breaks sooner or later.
As already told this script just saves time by automating a repetitive task. But there are some other advantages.
I also use this as an instrument to teach junior drupal developers about apache solr without having them loose to much time on the details. They can set up a solr instance quickly and continue to be productive. In their training time and/or spare time they can pick apart the script like we will do now and learn about the details.
Another advantage is: You know by using the script to install an apache solr multicore locally that everyone has the same configuration. There are so much tutorials on how to set up solr on the web it becomes very possible that everyone in the team has a differten version/setup.
Using scripts to automate these tasks like installing apache solr is highly recommended. But you should always know what you are executing. Always be carefully to review things so you know what to do if the automations break down .