Setup Gitlab & Jenkins on Raspberry Pi 2

Objective:

Installing and configuring Gitlab and Jenkins on Raspberry Pi 2

 

Background:

I currently have extra Raspberry Pi and would like to use for something useful. I found Jenkins and Gitlab are able to install on Raspberry Pi.

This article is to share the step by step guide how to setup Gitlab and Jenkins to Raspberry Pi 2.

 

Preparation:

1 x Raspberry Pi 2

 

Step By Step:

  1. Install Raspbian to Raspberry Pi 2
    • Omit the installation part as it is quite straightforward.
  2. Setup static IP address
    • Omit as Google will tell you how to do.
    • In my Pi, I set 192.168.1.201
  3. Increase swap memory
    • Since both applications are memory intensive, I increased swap memory
      $ sudo nano /etc/dphys-swapfile

      Change CONF_SWAPFILE=100 to CONF_SWAPFILE=1000

  4. Install Gitlab
    • Run following commands
      $ sudo apt-get install curl openssh-server ca-certificates postfix apt-transport-https
      $ curl https://packages.gitlab.com/gpg.key | sudo apt-key add -
      $ sudo curl -sS https://packages.gitlab.com/install/repositories/gitlab/raspberry-pi2/script.deb.sh | sudo bash
      $ sudo apt-get install gitlab-ce
      $ sudo gitlab-ctl reconfigure
      
    • Detailed instruction available in https://about.gitlab.com/installation/#raspberry-pi-2
  5. Install Jenkins
    • Run following commands
      $ sudo update-alternatives --config java
      $ mkdir jenkins && cd jenkins
      $ wget -q -O - https://jenkins-ci.org/debian/jenkins-ci.org.key | sudo apt-key add -
      $ sudo sh -c 'echo deb http://pkg.jenkins-ci.org/debian binary/ > /etc/apt/sources.list.d/jenkins.list'
      $ sudo apt-get update
      $ sudo apt-get install jenkins
    • Detailed instruction available in http://ifahrentholz.de/2017/setup-jenkins-on-raspberry/
  6. Access Gitlab – http://192.168.1.201:80
  7. Update Gitlab configuration file for changing a port
    • Since I didn’t want to use 80 as default port, I updated the port to 8080.
    • Run following command
      $ sudo nano /etc/gitlab/gitlab.rb

      Update following configuration parameters

      external_url "http://192.168.1.201:8081"
      nginx['listen_port'] = 8081
      unicorn['port'] = 8082
    • Run following command
      $ sudo gitlab-ctl reconfigure
  8. Access Gitlab – http://192.168.1.201:8081
  9. Create new password for account
  10. Login with root and password
  11. Then you will see this screen
  12. Access Jenkins – http://192.168.1.201:8080
  13. Get initial password for unlocking Jenkins
    $ sudo cat /var/lib/jenkins/secrets/initialAdminPassword
  14. In the screen “Customize Jenkins”, click “Install suggested plugins” and wait for installing plugins
  15. Create first administrator user
  16. Click “Start using Jenkins”
  17. If the display language is not English or you prefer different display language, then install Locale plugin and force to set desired language as main language.If the display language is not English or you prefer different display language, then install Locale plugin and force to set desired language as main language.
    • Plugin page: https://wiki.jenkins.io/display/JENKINS/Locale+Plugin
    • Go to “Manage Jenkins” -> “Manage Plugins”
    • Click “Available” tab
    • Find “Locale plugin” and check checkbox
    • Click “Install without restart” button
    • After finishing installation, go to “Manage Jenkins” -> “Configure System”
    • Find “Locale” section -> “Default Language”
    • Enter desired language code such as en for English
    • And check “Ignore browser preference and force this language to all users”
    • Click “Save” button
  18. After you finish setting, you should see following screen

[따라하기] 아두이노 기초 – 초음파센서 사용하기 by ODIY 한국과학창의재단

[따라하기] 아두이노 기초 – 초음파센서 사용하기 by ODIY 한국과학창의재단

 

 

Ardunio – Ultrasound sensor with LED

 

 

 

 

 

#define TRIG 2  // Sending out ultrasound
#define ECHO 3  // Receiving ultrasound
#define LED 9   // Controlling LED

void setup() {
  // put your setup code here, to run once:
  pinMode(TRIG, OUTPUT);
  pinMode(ECHO, INPUT);
}

void loop() {
  // put your main code here, to run repeatedly:
  digitalWrite(TRIG, LOW);  // Turn off ultrasound
  delayMicroseconds(2);     
  digitalWrite(TRIG, HIGH); // Turn on ultrasound
  delayMicroseconds(2);
  digitalWrite(TRIG, LOW);

  long distance = pulseIn(ECHO, HIGH)/58.2; // Calculate distance by CM (58.2)

  analogWrite(LED, map(distance, 0, 30, 0, 150));
  //delay(100);
}

 

 

 

[따라하기] 아두이노 기초 – LED와 버튼 제어하기 by ODIY 한국과학창의재단

[따라하기] 아두이노 기초 – LED와 버튼 제어하기 by ODIY 한국과학창의재단

 

 

 

Arduino – LED Wave

 

 

 

#define DELAY_TIME 100


void setup() {
  // put your setup code here, to run once:
  pinMode(2, OUTPUT);
  pinMode(3, OUTPUT);
  pinMode(4, OUTPUT);
  pinMode(5, OUTPUT);
  pinMode(6, OUTPUT); 
}

void loop() {
  // put your main code here, to run repeatedly:
  digitalWrite(6, LOW);
  digitalWrite(2, HIGH);
  delay(DELAY_TIME);
  digitalWrite(2, LOW);
  digitalWrite(3, HIGH);
  delay(DELAY_TIME);
  digitalWrite(3, LOW);
  digitalWrite(4, HIGH);
  delay(DELAY_TIME);
  digitalWrite(4, LOW);
  digitalWrite(5, HIGH);
  delay(DELAY_TIME);
  digitalWrite(5, LOW);
  digitalWrite(6, HIGH);
  delay(DELAY_TIME);
}

 

Arduino – LED with button

 

 

#define LED 12
#define BUTTON 7

void setup() {
  // put your setup code here, to run once:
  pinMode(LED, OUTPUT);
  pinMode(BUTTON, INPUT);
}

void loop() {
  // put your main code here, to run repeatedly:
  if(digitalRead(BUTTON) == HIGH){
    digitalWrite(LED, HIGH);
    delay(1000);
    digitalWrite(LED, LOW);
    delay(1000);
  }
}

 

Missing Authroization header in request

When developing REST API in Yii2, I found some development environments do not populate Authorization header in the request; as a result, I was not able to use HttpBearerAuth because the headers were missing in the request. Note that I still can use QueryParamAuth; although, I insist on using HttpBearerAuth instead of QueryParamAuth.

 

The issue is caused by CGI/FastCGI mode in Apache. I didn’t want to update server-side configuration; thus, do following changes in .htaccess:

  1. Update .htaccess
    SetEnvIf Authorization .+ HTTP_AUTHORIZATION=$0
    
    RewriteEngine on
    
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteCond %{REQUEST_FILENAME} !-d
    
    RewriteRule . index.php

     

Above changes will create $_SERVER parameters including REDIRECT_HTTP_AUTHORIZATION and the REDIRECT_HTTP_AUTHORIZATION parameter contains Authorization header value.

 

But Yii2 HttpBearerAuth does not check $_SERVER[‘REDIRECT_HTTP_AUTHORIZATION’] value. Therefore, above .htaccess still not work for HttpBearerAuth.

 

To workaround the issue, I override HttpBearerAuth and add the code for checking $_SERVER parameter.

  1. Create a folder filters/auth
  2. Create a file HttpBearerAuth.php
    <?php
        /**
         * @link http://www.yiiframework.com/
         * @copyright Copyright (c) 2008 Yii Software LLC
         * @license http://www.yiiframework.com/license/
         */
    
        namespace app\filters\auth;
    
        /**
         * HttpBearerAuth is an action filter that supports the authentication method based on HTTP Bearer token.
         *
         * You may use HttpBearerAuth by attaching it as a behavior to a controller or module, like the following:
         *
         * ```php
         * public function behaviors()
         * {
         *     return [
         *         'bearerAuth' => [
         *             'class' => \yii\filters\auth\HttpBearerAuth::className(),
         *         ],
         *     ];
         * }
         * ```
         *
         * @author Qiang Xue <qiang.xue@gmail.com>
         * @since 2.0
         */
        class HttpBearerAuth extends \yii\filters\auth\AuthMethod
        {
            /**
             * @var string the HTTP authentication realm
             */
            public $realm = 'api';
    
    
            /**
             * @inheritdoc
             */
            public function authenticate($user, $request, $response)
            {
                $authHeader = $request->getHeaders()->get('Authorization');
    
                // Added following lines to support fastcgi issue.
                // To support this, must update .htaccess as below:
                //  # Authorization Headers
                //  RewriteCond %{HTTP:Authorization} .
                //  RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
    
                if($authHeader == null && isset($_SERVER['REDIRECT_HTTP_AUTHORIZATION']) && $_SERVER['REDIRECT_HTTP_AUTHORIZATION'] != "") {
                    $authHeader = $_SERVER['REDIRECT_HTTP_AUTHORIZATION'];
                }
    
                if ($authHeader !== null && preg_match('/^Bearer\s+(.*?)$/', $authHeader, $matches)) {
                    $identity = $user->loginByAccessToken($matches[1], get_class($this));
                    if ($identity === null) {
                        $this->handleFailure($response);
                    }
                    return $identity;
                }
    
                return null;
            }
    
            /**
             * @inheritdoc
             */
            public function challenge($response)
            {
                $response->getHeaders()->set('WWW-Authenticate', "Bearer realm=\"{$this->realm}\"");
            }
        }
    
  3. Update controller
    <?php
        namespace app\modules\v1\controllers;
    
        use yii\rest\ActiveController;
    
        class SampleController extends ActiveController
        {
            public $modelClass = 'app\models\Sample';
    
            public function __construct($id, $module, $config = [])
            {
                parent::__construct($id, $module, $config);
    
            }
    
            public function behaviors()
            {
                $behaviors = parent::behaviors();
    
                $behaviors['authenticator'] = [
                    'class' => yii\filters\auth\CompositeAuth::className(),
                    'authMethods' => [
                        app\filters\auth\HttpBearerAuth::className(),
                    ],
    
                ];
    
                return $behaviors;
            }
        }