DevOps Workflows

Overview

Anka Build solution can be used to setup a self-service macOS cloud to execute iOS and macOS CI and also for manual testing. You can follow these steps if you are a Devops user responsible for setting up infrastructure for macOS/iOS CI.

Anka build components include the following:

  • ankaBuild.pkg Mac application
  • Anka Controller & Registry
  • Jenkins and Teamcity plugins for Anka Build Cloud
  • Anka Controller REST APIs for integration with other third party CI systems

Preparing your project VM Environments

Install ankabuild.pkg on the mac machine on which you will create the macOS VMs. This could be your mac laptop or one of the build mac machines. Then, use anka create command to create the VM.

Note - > While creating VM with anka create, make sure to specify enough --disk-size. Currently, it’s not possible to change the disk size for an existing VM.

Once, you have created the VM, you can also modify the vCPU, RAM properties of the VM using the anka modify command.

anka modify --help
Usage: anka modify [OPTIONS] VM_ID COMMAND [ARGS]...

  Modifies a VM settings

Options:
  --help  Show this message and exit.  [optional]

Commands:
  add
  SubCommands:
    hard-drive
  	network-card
  	optical-drive
  	port-forwarding
  	usb-device
  delete
  SubCommands:
  	custom-variable
  	hard-drive
  	network-card
  	optical-drive
  	port-forwarding
  	usb-device
  set
  SubCommands:
  	cpu              set number of cpu cores
    custom-variable
    description      set textual description of the VM
    hyper-threading  set hyper-threading mode 1 for on or 0 for...
    memory-prefetch  set memory-prefetch mode 1 for on or 0 for...
    name             set new name for the VM
    nested           enable nested virtualization (this feature is...
    network-card     modify network card settings
    ram              set memory size
    vnc              set vnc on or off port is auto assigned when...
  show
  SubCommands:
  	custom-variables   
    

Use the custom-variable to set hardware model related properties. This is useful if you are creating VMs to emulate different Apple hardware setups.

anka modify <vm> set custom-variable hw.serial <serial>
anka modify <vm> set custom-variable hw.product <product>
anka modify <vm> set custom-variable hw.family <family>

You can use this command to enable SIP in the VM. By default, Anka Vms are created with SIP/KEXT consent disabled and it’s recommended to keep this setting.

anka modify VMNAME set custom-variable sys.csr-active-config 0x0

Bootstrapping the VM for iOS/macOS build and test

Prepare and install all project dependencies and packages in your base macOS Anka VM with either using anka run or ssh into the VM and run your existing bootstrapping scipts (Ansible, Chef etc). Check here https://veertu.com/bootstrapping-anka-macos-vm/ for an example.

How to SSH to a VM

In order to ssh to an anka VM, first you need to enable port forwarding. Stop the VM and use anka modify command to enable port forwarding on the VM. This is also required for integrating Anka Build with jenkins and teamcity using the available plugins.

anka modify vm add port-forwarding --help
Usage: anka modify add port-forwarding [OPTIONS] RULE_NAME

Options:
  -p, --host-port INTEGER   the port to listen on the host
  -g, --guest-port INTEGER  the port to forward to on the vm  [required]
  --protocol TEXT           protocol to forward (tcp by default)
  -l, --host-ip TEXT        the forwarding server will listen to this ip
                            address, defaults to 0.0.0.0 (all)
  --guest-ip TEXT           specifies guest ip, in case the guest has multiple
                            ips
  --card-index INTEGER      specify the network cards index in case there is
                            more than one  [default: 0]
  --help                    Show this message and exit.


anka modify sierrav40c1 add port-forwarding --host-port 0 --guest-port 22 --protocol tcp ssh
rule added successfully

-p, --host-port is the port to listen on the host. Value of 0 takes the default value. Currently port forwarding auto assignment port range default is hardcoded to start from 10000+. Some users could have limitations on port ranges due to firewalls/network rules used. You can change this default setting using this command.

anka config portfwd_base 40000

This will start it from 40000. If there are multiple nodes(hosts) in your cloud, then you need to execute this command on all the hosts/nodes.

Do anka show to get the IP of the VM.

anka show sierrav40c1
+-----------------------+--------------------------------------+
| uuid                  | 4ffd7f26-67f1-11e7-a726-acbc32ad1d59 |
+-----------------------+--------------------------------------+
| ram                   | 2G                                   |
+-----------------------+--------------------------------------+
| name                  | sierrav40c1 (v1)                     |
+-----------------------+--------------------------------------+
| cpu_cores             | 2                                    |
+-----------------------+--------------------------------------+
| hard_drive            | 40 GB (8260849664 bytes on disk)     |
+-----------------------+--------------------------------------+
| status                | running                              |
+-----------------------+--------------------------------------+
| ip                    | 192.168.64.179                       |
+-----------------------+--------------------------------------+
| vnc_connection_string | vnc://:admin@10.0.1.8:5900           |
+-----------------------+--------------------------------------+
| view_vm_display       | anka view sierrav40c1                |
+-----------------------+--------------------------------------+

Then, use ssh -l usr IPADDRESS to ssh into the VM from the host.

In order to ssh into the VM from another machine(not the host on which it’s running), you will use the following command.

ssh -l usr HOST_ADDRESS -p PORTFORWARDING_PORT

You can also mount independent partitions or drive from the host to the VM and execute build/test actions.

Using anka run

Use anka run (similar to docker run) to install packages etc inside the Anka macOS VM. Check the anka run --help to see all the flags available. Check here for examples on using anka run - https://veertu.com/anka-run-interface-for-anka-macos-vm/.

anka run --help
Usage: anka run [OPTIONS] VM_NAME COMMAND [ARGS]...

  Run commands inside VM environment

Options:
  -w, --workdir PATH              Working directory inside the VM  [optional]
  -v, --volumes-from, --volume PATH
                                  Mount host directory (current directory by default)
                                  into VM . '--volumes-from' is deprecated form
                                  [optional]
  -n, --no-volumes-from, --no-volume
                                  Use this flag to prevent implicit mounting of current
                                  folder (see --volume option). '--no-volumes-from' is
                                  deprecated form  [optional]
  -E, -e, --env                   Inherit environment variables. '-e' is deprecated form
                                  [optional]
  -f, --env-file PATH             Provide environment variables from file  [optional]
  -N, --wait-network              Wait till guest network interface up  [optional]
  --help                          Show this message and exit.  [optional]
  

anka run implicitly mounts current working directory by default. When local host artifacts like project sources, scripts and packages etc are not needed, only resources are being downloaded from internet while anka run command execution (for example installing brew, xcversion, gitlab-runner) it’s recommended to anka run -n, to speedup execution. If no -w option specified, anka run [-v…] starts from mountpoint, while anka run -n starts from $HOME.

Note - anka run on timeout returns 125.

Examples:

Install brew, homebrew in Anka macOS VM.

anka run -n myhisierravm ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"

xcode-install in Anka macOS VM.

anka run -n myhisierravm sudo gem install xcode-install
FASTLANE_PASSWORD=”passwd” FASTLANE_USER=”usr” anka run -nE myhisierravm xcversion install 9.2

-n option of anka run prevents implicit mounting of current folder inside the VM. -E enables inheriting env variables (eg : FASTLANE variables) in the Anka macOS VM.

Mount provisioning profiles from the host inside the VM. anka mount myhisierravm ~/Library/…/Provisioning\ Profiles /Users/anka/Library/…/Provisioning\ Profiles

Mounting independent partitions.

anka modify VM add hard-drive --file /dev/rdiskNsM (add partition M on disk N)

Mounting entire drive.

anka modify VM add hard-drive --file /dev/rdiskN

Note - anka mount/unmount return 231 on timeout.

Working with your VM

Use anka clone command to clone your VM.

anka clone --help
Usage: anka clone [OPTIONS] VM_ID NEW_VM_NAME
Clones a VM
Options
-c, --consolidate  Consolidate snapshots into a single VM image instead[optional]
                    

Suspend the VM anka suspend VMNAME/VMID before uploading it to Anka Registry. This will save the VM in an Instant Start/Fast boot mode. Then, when it’s pulled from the registry and started or cloned and started, it will boot instantaneously.

Accessing the host from within Anka VM

The host from Anka VM has fixed IP address of 192.168.64.1.

Uploading to Anka Registry

Once your VM is ready, push it to Anka Registry, so it can be used for the CI jobs. Refer to Using Registry to connect your machine to the registry and push VMs.

Connecting to Anka Central Controller

The Anka Controller module is the central management for your macOS Anka private cloud. In order to configure your private macOS cloud, you will need to connect each individual piece of Apple hardware (Anka Build Nodes) running ankabuild.pkg (used for build or test) to the Anka Controller. This will enable the Controller to manage and create on-demand VMs on this hardware based on the requests it receives from the CI system. Refer to Using Controller for instructions on connecting your build/test mac machines to the Controller.

Your macOS private cloud setup is now complete! If you use Jenkins as your CI system, then use the Anka Jenkins plugin to provision your build/test environments on-demand on the Anka macOS private cloud. Refer to Integrating with Jenkins for more information. For any other CI system, you can integrate using the Controller REST APIs.

Updating your base build/test VM environments

After pushing/uploading your initial version of build/test environments, you can update them with new dependencies (Example: new Xcode versions), very easily.

First, download the previous version from the Anka Registry using the anka registry pull command. Then, update the VM with the changes. Next, push this updated VM to the registry with a different version tag using the anka registry push VMNAME --tag command. Now, you can configure your CI system use this updated VM environment for build/test jobs.

You retain your older environments in the registry and can go back to those, when required, for debugging purposes.