added iOS source code
[wl-app.git] / iOS / Pods / RealmSwift / build.sh
1 #!/bin/bash
2
3 ##################################################################################
4 # Custom build tool for Realm Objective-C binding.
5 #
6 # (C) Copyright 2011-2015 by realm.io.
7 ##################################################################################
8
9 # Warning: pipefail is not a POSIX compatible option, but on OS X it works just fine.
10 #          OS X uses a POSIX complain version of bash as /bin/sh, but apparently it does
11 #          not strip away this feature. Also, this will fail if somebody forces the script
12 #          to be run with zsh.
13 set -o pipefail
14 set -e
15
16 source_root="$(dirname "$0")"
17
18 # You can override the version of the core library
19 : ${REALM_CORE_VERSION:=$(sed -n 's/^REALM_CORE_VERSION=\(.*\)$/\1/p' ${source_root}/dependencies.list)} # set to "current" to always use the current build
20
21 : ${REALM_SYNC_VERSION:=$(sed -n 's/^REALM_SYNC_VERSION=\(.*\)$/\1/p' ${source_root}/dependencies.list)}
22
23 : ${REALM_OBJECT_SERVER_VERSION:=$(sed -n 's/^REALM_OBJECT_SERVER_VERSION=\(.*\)$/\1/p' ${source_root}/dependencies.list)}
24
25 # You can override the xcmode used
26 : ${XCMODE:=xcodebuild} # must be one of: xcodebuild (default), xcpretty, xctool
27
28 # Provide a fallback value for TMPDIR, relevant for Xcode Bots
29 : ${TMPDIR:=$(getconf DARWIN_USER_TEMP_DIR)}
30
31 PATH=/usr/libexec:$PATH
32
33 if ! [ -z "${JENKINS_HOME}" ]; then
34     XCPRETTY_PARAMS="--no-utf --report junit --output build/reports/junit.xml"
35     CODESIGN_PARAMS="CODE_SIGN_IDENTITY= CODE_SIGNING_REQUIRED=NO"
36 fi
37
38 usage() {
39 cat <<EOF
40 Usage: sh $0 command [argument]
41
42 command:
43   clean:                clean up/remove all generated files
44   download-core:        downloads core library (binary version)
45   download-object-server:  downloads and installs the Realm Object Server
46   download-sync:        downloads sync library (binary version, core+sync)
47   build:                builds all iOS  and OS X frameworks
48   ios-static:           builds fat iOS static framework
49   ios-dynamic:          builds iOS dynamic frameworks
50   ios-swift:            builds RealmSwift frameworks for iOS
51   watchos:              builds watchOS framwork
52   watchos-swift:        builds RealmSwift framework for watchOS
53   tvos:                 builds tvOS framework
54   tvos-swift:           builds RealmSwift framework for tvOS
55   osx:                  builds OS X framework
56   osx-swift:            builds RealmSwift framework for OS X
57   analyze-osx:          analyzes OS X framework
58   test:                 tests all iOS and OS X frameworks
59   test-all:             tests all iOS and OS X frameworks in both Debug and Release configurations
60   test-ios-static:      tests static iOS framework on 32-bit and 64-bit simulators
61   test-ios-dynamic:     tests dynamic iOS framework on 32-bit and 64-bit simulators
62   test-ios-swift:       tests RealmSwift iOS framework on 32-bit and 64-bit simulators
63   test-ios-devices:     tests ObjC & Swift iOS frameworks on all attached iOS devices
64   test-ios-devices-objc:  tests ObjC iOS framework on all attached iOS devices
65   test-ios-devices-swift: tests Swift iOS framework on all attached iOS devices
66   test-tvos:            tests tvOS framework
67   test-tvos-swift:      tests RealmSwift tvOS framework
68   test-tvos-devices:    tests ObjC & Swift tvOS frameworks on all attached tvOS devices
69   test-osx:             tests OS X framework
70   test-osx-swift:       tests RealmSwift OS X framework
71   verify:               verifies docs, osx, osx-swift, ios-static, ios-dynamic, ios-swift, ios-device in both Debug and Release configurations, swiftlint
72   verify-osx-object-server:  downloads the Realm Object Server and runs the Objective-C and Swift integration tests
73   docs:                 builds docs in docs/output
74   examples:             builds all examples
75   examples-ios:         builds all static iOS examples
76   examples-ios-swift:   builds all Swift iOS examples
77   examples-osx:         builds all OS X examples
78   get-version:          get the current version
79   set-version version:  set the version
80   cocoapods-setup:      download realm-core and create a stub RLMPlatform.h file to enable building via CocoaPods
81
82
83 argument:
84   version: version in the x.y.z format
85
86 environment variables:
87   XCMODE: xcodebuild (default), xcpretty or xctool
88   CONFIGURATION: Debug or Release (default)
89   REALM_CORE_VERSION: version in x.y.z format or "current" to use local build
90   REALM_EXTRA_BUILD_ARGUMENTS: additional arguments to pass to the build tool
91   REALM_XCODE_VERSION: the version number of Xcode to use (e.g.: 8.1)
92 EOF
93 }
94
95 ######################################
96 # Xcode Helpers
97 ######################################
98
99 xcode_version_major() {
100     echo "${REALM_XCODE_VERSION%%.*}"
101 }
102
103 xcode() {
104     mkdir -p build/DerivedData
105     CMD="xcodebuild -IDECustomDerivedDataLocation=build/DerivedData $@"
106     echo "Building with command:" $CMD
107     eval "$CMD"
108 }
109
110 xc() {
111     # Logs xcodebuild output in realtime
112     : ${NSUnbufferedIO:=YES}
113     args="$@ SWIFT_VERSION=$REALM_SWIFT_VERSION $REALM_EXTRA_BUILD_ARGUMENTS"
114     if [[ "$XCMODE" == "xcodebuild" ]]; then
115         xcode "$args"
116     elif [[ "$XCMODE" == "xcpretty" ]]; then
117         mkdir -p build
118         xcode "$args" | tee build/build.log | xcpretty -c ${XCPRETTY_PARAMS} || {
119             echo "The raw xcodebuild output is available in build/build.log"
120             exit 1
121         }
122     elif [[ "$XCMODE" == "xctool" ]]; then
123         xctool "$args"
124     fi
125 }
126
127 copy_bcsymbolmap() {
128     find "$1" -name '*.bcsymbolmap' -type f -exec cp {} "$2" \;
129 }
130
131 build_combined() {
132     local scheme="$1"
133     local module_name="$2"
134     local os="$3"
135     local simulator="$4"
136     local scope_suffix="$5"
137     local version_suffix="$6"
138     local config="$CONFIGURATION"
139
140     local destination=""
141     local os_name=""
142     if [[ "$os" == "iphoneos" ]]; then
143         os_name="ios"
144         destination="iPhone 6"
145     elif [[ "$os" == "watchos"  ]]; then
146         os_name="$os"
147         destination="Apple Watch - 42mm"
148     elif [[ "$os" == "appletvos"  ]]; then
149         os_name="tvos"
150         if (( $(xcode_version_major) >= 9 )); then
151             destination="Apple TV"
152         else
153             destination="Apple TV 1080p"
154         fi
155     fi
156
157     # Derive build paths
158     local build_products_path="build/DerivedData/Realm/Build/Products"
159     local product_name="$module_name.framework"
160     local binary_path="$module_name"
161     local os_path="$build_products_path/$config-$os$scope_suffix/$product_name"
162     local simulator_path="$build_products_path/$config-$simulator$scope_suffix/$product_name"
163     local out_path="build/$os_name$scope_suffix$version_suffix"
164
165     # Build for each platform
166     xc "-scheme '$scheme' -configuration $config -sdk $os"
167     xc "-scheme '$scheme' -configuration $config -sdk $simulator -destination 'name=$destination' ONLY_ACTIVE_ARCH=NO"
168
169     # Combine .swiftmodule
170     if [ -d $simulator_path/Modules/$module_name.swiftmodule ]; then
171       cp $simulator_path/Modules/$module_name.swiftmodule/* $os_path/Modules/$module_name.swiftmodule/
172     fi
173
174     # Copy *.bcsymbolmap to .framework for submitting app with bitcode
175     copy_bcsymbolmap "$build_products_path/$config-$os$scope_suffix" "$os_path"
176
177     # Retrieve build products
178     clean_retrieve $os_path $out_path $product_name
179
180     # Combine ar archives
181     LIPO_OUTPUT="$out_path/$product_name/$module_name"
182     xcrun lipo -create "$simulator_path/$binary_path" "$os_path/$binary_path" -output "$LIPO_OUTPUT"
183
184     if [[ "$destination" != "" && "$config" == "Release" ]]; then
185         sh build.sh binary-has-bitcode "$LIPO_OUTPUT"
186     fi
187 }
188
189 clean_retrieve() {
190   mkdir -p "$2"
191   rm -rf "$2/$3"
192   cp -R "$1" "$2"
193 }
194
195 move_to_clean_dir() {
196     rm -rf "$2"
197     mkdir -p "$2"
198     mv "$1" "$2"
199 }
200
201 test_ios_static() {
202     destination="$1"
203     xc "-scheme 'Realm iOS static' -configuration $CONFIGURATION -sdk iphonesimulator -destination '$destination' build"
204     if (( $(xcode_version_major) < 9 )); then
205         xc "-scheme 'Realm iOS static' -configuration $CONFIGURATION -sdk iphonesimulator -destination '$destination' test 'ARCHS=\$(ARCHS_STANDARD_32_BIT)'"
206     fi
207
208     # Xcode's depending tracking is lacking and it doesn't realize that the Realm static framework's static library
209     # needs to be recreated when the active architectures change. Help Xcode out by removing the static library.
210     settings=$(xcode "-scheme 'Realm iOS static' -configuration $CONFIGURATION -sdk iphonesimulator -destination '$destination' -showBuildSettings")
211     path=$(echo "$settings" | awk '/CONFIGURATION_BUILD_DIR/ { cbd = $3; } /EXECUTABLE_PATH/ { ep = $3; } END { printf "%s/%s\n", cbd, ep; }')
212     rm "$path"
213
214     xc "-scheme 'Realm iOS static' -configuration $CONFIGURATION -sdk iphonesimulator -destination '$destination' test"
215 }
216
217 ######################################
218 # Device Test Helper
219 ######################################
220
221 test_devices() {
222     local serial_numbers=()
223     local awk_script="
224     /^ +Vendor ID: / { is_apple = 0; }
225     /^ +Vendor ID: 0x05[aA][cC] / { is_apple = 1; }
226     /^ +Serial Number: / {
227         if (is_apple) {
228             match(\$0, /^ +Serial Number: /);
229             print substr(\$0, RLENGTH + 1);
230         }
231     }
232     "
233     local serial_numbers_text=$(/usr/sbin/system_profiler SPUSBDataType | /usr/bin/awk "$awk_script")
234     while read -r number; do
235         if [[ "$number" != "" ]]; then
236             serial_numbers+=("$number")
237         fi
238     done <<< "$serial_numbers_text"
239     if [[ ${#serial_numbers[@]} == 0 ]]; then
240         echo "At least one iOS/tvOS device must be connected to this computer to run device tests"
241         if [ -z "${JENKINS_HOME}" ]; then
242             # Don't fail if running locally and there's no device
243             exit 0
244         fi
245         exit 1
246     fi
247     local sdk="$1"
248     local scheme="$2"
249     local configuration="$3"
250     local failed=0
251     for device in "${serial_numbers[@]}"; do
252         xc "-scheme '$scheme' -configuration $configuration -destination 'id=$device' -sdk $sdk test" || failed=1
253     done
254     return $failed
255 }
256
257 ######################################
258 # Docs
259 ######################################
260
261 build_docs() {
262     local language="$1"
263     local version=$(sh build.sh get-version)
264
265     local xcodebuild_arguments="--objc,Realm/Realm.h,--,-x,objective-c,-isysroot,$(xcrun --show-sdk-path),-I,$(pwd)"
266     local module="Realm"
267     local objc="--objc"
268
269     if [[ "$language" == "swift" ]]; then
270         sh build.sh set-swift-version
271         xcodebuild_arguments="-scheme,RealmSwift"
272         module="RealmSwift"
273         objc=""
274     fi
275
276     touch Realm/RLMPlatform.h # jazzy will fail if it can't find all public header files
277     jazzy \
278       ${objc} \
279       --clean \
280       --author Realm \
281       --author_url https://realm.io \
282       --github_url https://github.com/realm/realm-cocoa \
283       --github-file-prefix https://github.com/realm/realm-cocoa/tree/v${version} \
284       --module-version ${version} \
285       --xcodebuild-arguments ${xcodebuild_arguments} \
286       --module ${module} \
287       --root-url https://realm.io/docs/${language}/${version}/api/ \
288       --output docs/${language}_output \
289       --head "$(cat docs/custom_head.html)"
290
291     rm Realm/RLMPlatform.h
292 }
293
294 ######################################
295 # Input Validation
296 ######################################
297
298 if [ "$#" -eq 0 -o "$#" -gt 3 ]; then
299     usage
300     exit 1
301 fi
302
303 ######################################
304 # Downloading
305 ######################################
306
307 kill_object_server() {
308 # Based on build.sh conventions we always run ROS from a path ending in 'ros/bin/ros'.
309     pkill -f ros/bin/ros\ start
310 }
311
312 download_object_server() {
313     rm -rf ./test-ros-instance
314     mkdir -p ./test-ros-instance/ros
315     chmod 777 ./test-ros-instance
316     /usr/local/bin/node /usr/local/bin/npm install --scripts-prepend-node-path=auto --prefix ./test-ros-instance/ros \
317         -g realm-object-server@${REALM_OBJECT_SERVER_VERSION}
318 }
319
320 download_common() {
321     local download_type=$1 tries_left=3 version url error temp_dir temp_path tar_path
322
323     if [ "$download_type" == "core" ]; then
324         version=$REALM_CORE_VERSION
325         url="https://static.realm.io/downloads/core/realm-core-${version}.tar.xz"
326     elif [ "$download_type" == "sync" ]; then
327         version=$REALM_SYNC_VERSION
328         url="https://static.realm.io/downloads/sync/realm-sync-cocoa-${version}.tar.xz"
329     else
330         echo "Unknown dowload_type: $download_type"
331         exit 1
332     fi
333
334     echo "Downloading dependency: ${download_type} ${version}"
335
336     if [ -z "$TMPDIR" ]; then
337         TMPDIR='/tmp'
338     fi
339     temp_dir=$(dirname "$TMPDIR/waste")/${download_type}_bin
340     mkdir -p "$temp_dir"
341     tar_path="${temp_dir}/${download_type}-${version}.tar.xz"
342     temp_path="${tar_path}.tmp"
343
344     while [ 0 -lt $tries_left ] && [ ! -f "$tar_path" ]; do
345         if ! error=$(/usr/bin/curl --fail --silent --show-error --location "$url" --output "$temp_path" 2>&1); then
346             tries_left=$[$tries_left-1]
347         else
348             mv "$temp_path" "$tar_path"
349         fi
350     done
351
352     if [ ! -f "$tar_path" ]; then
353         printf "Downloading ${download_type} failed:\n\t$url\n\t$error\n"
354         exit 1
355     fi
356
357     (
358         cd "$temp_dir"
359         rm -rf "$download_type"
360         tar xf "$tar_path" --xz
361         mv core "${download_type}-${version}"
362     )
363
364     rm -rf "${download_type}-${version}" core
365     mv "${temp_dir}/${download_type}-${version}" .
366     ln -s "${download_type}-${version}" core
367 }
368
369 download_core() {
370     download_common "core"
371 }
372
373 download_sync() {
374     download_common "sync"
375 }
376
377 ######################################
378 # Variables
379 ######################################
380
381 COMMAND="$1"
382
383 # Use Debug config if command ends with -debug, otherwise default to Release
384 # Set IS_RUNNING_PACKAGING when running packaging steps to avoid running iOS static tests with Xcode 8.3.3
385 case "$COMMAND" in
386     *-debug)
387         COMMAND="${COMMAND%-debug}"
388         CONFIGURATION="Debug"
389         ;;
390     package-*)
391         IS_RUNNING_PACKAGING=1
392         ;;
393 esac
394 export CONFIGURATION=${CONFIGURATION:-Release}
395 export IS_RUNNING_PACKAGING=${IS_RUNNING_PACKAGING:-0}
396
397 # Pre-choose Xcode and Swift versions for those operations that do not set them
398 REALM_XCODE_VERSION=${xcode_version:-$REALM_XCODE_VERSION}
399 REALM_SWIFT_VERSION=${swift_version:-$REALM_SWIFT_VERSION}
400 source "${source_root}/scripts/swift-version.sh"
401 set_xcode_and_swift_versions
402
403 ######################################
404 # Commands
405 ######################################
406
407 case "$COMMAND" in
408
409     ######################################
410     # Clean
411     ######################################
412     "clean")
413         find . -type d -name build -exec rm -r "{}" +
414         exit 0
415         ;;
416
417     ######################################
418     # Object Server
419     ######################################
420     "download-object-server")
421         download_object_server
422         exit 0
423         ;;
424
425     "reset-ros-server-state")
426         rm -rf "./test-ros-instance/data"
427         rm -rf "./test-ros-instance/realm-object-server"
428         exit 0
429         ;;
430
431     "reset-ros-client-state")
432         rm -rf ~/Library/Application\ Support/xctest
433         rm -rf ~/Library/Application\ Support/io.realm.TestHost
434         rm -rf ~/Library/Application\ Support/xctest-child
435         exit 0
436         ;;
437
438     "reset-object-server")
439         kill_object_server
440         # Add a short delay, so file system doesn't complain about files in use
441         sleep 1
442         sh build.sh reset-ros-server-state
443         sh build.sh reset-ros-client-state
444         # Add another delay to ensure files are actually gone from file system
445         sleep 1
446         exit 0
447         ;;
448
449     ######################################
450     # Core
451     ######################################
452     "download-core")
453         if [ "$REALM_CORE_VERSION" = "current" ]; then
454             echo "Using version of core already in core/ directory"
455             exit 0
456         fi
457         if [ -d core -a -d ../realm-core -a ! -L core ]; then
458           # Allow newer versions than expected for local builds as testing
459           # with unreleased versions is one of the reasons to use a local build
460           if ! $(grep -i "${REALM_CORE_VERSION} Release notes" core/release_notes.txt >/dev/null); then
461               echo "Local build of core is out of date."
462               exit 1
463           else
464               echo "The core library seems to be up to date."
465           fi
466         elif ! [ -L core ]; then
467             echo "core is not a symlink. Deleting..."
468             rm -rf core
469             download_core
470         # With a prebuilt version we only want to check the first non-empty
471         # line so that checking out an older commit will download the
472         # appropriate version of core if the already-present version is too new
473         elif ! $(grep -m 1 . core/release_notes.txt | grep -i "${REALM_CORE_VERSION} RELEASE NOTES" >/dev/null); then
474             download_core
475         else
476             echo "The core library seems to be up to date."
477         fi
478         exit 0
479         ;;
480
481     ######################################
482     # Sync
483     ######################################
484     "download-sync")
485         if [ "$REALM_SYNC_VERSION" = "current" ]; then
486             echo "Using version of core already in core/ directory"
487             exit 0
488         fi
489         if [ -d core -a -d ../realm-core -a -d ../realm-sync -a ! -L core ]; then
490           echo "Using version of core already in core/ directory"
491         elif ! [ -L core ]; then
492             echo "core is not a symlink. Deleting..."
493             rm -rf core
494             download_sync
495         elif [[ "$(cat core/version.txt)" != "$REALM_SYNC_VERSION" ]]; then
496             download_sync
497         else
498             echo "The core library seems to be up to date."
499         fi
500         exit 0
501         ;;
502
503     ######################################
504     # Swift versioning
505     ######################################
506     "set-swift-version")
507         version=${2:-$REALM_SWIFT_VERSION}
508
509         SWIFT_VERSION_FILE="RealmSwift/SwiftVersion.swift"
510         CONTENTS="let swiftLanguageVersion = \"$version\""
511         if [ ! -f "$SWIFT_VERSION_FILE" ] || ! grep -q "$CONTENTS" "$SWIFT_VERSION_FILE"; then
512             echo "$CONTENTS" > "$SWIFT_VERSION_FILE"
513         fi
514
515         exit 0
516         ;;
517
518     "prelaunch-simulator")
519         sh ${source_root}/scripts/reset-simulators.sh
520         ;;
521
522     ######################################
523     # Building
524     ######################################
525     "build")
526         sh build.sh ios-static
527         sh build.sh ios-dynamic
528         sh build.sh ios-swift
529         sh build.sh watchos
530         sh build.sh watchos-swift
531         sh build.sh tvos
532         sh build.sh tvos-swift
533         sh build.sh osx
534         sh build.sh osx-swift
535         exit 0
536         ;;
537
538     "ios-static")
539         build_combined 'Realm iOS static' Realm iphoneos iphonesimulator "-static"
540         exit 0
541         ;;
542
543     "ios-dynamic")
544         build_combined Realm Realm iphoneos iphonesimulator
545         exit 0
546         ;;
547
548     "ios-swift")
549         sh build.sh ios-dynamic
550         build_combined RealmSwift RealmSwift iphoneos iphonesimulator '' "/swift-$REALM_SWIFT_VERSION"
551         cp -R build/ios/Realm.framework build/ios/swift-$REALM_SWIFT_VERSION
552         exit 0
553         ;;
554
555     "watchos")
556         build_combined Realm Realm watchos watchsimulator
557         exit 0
558         ;;
559
560     "watchos-swift")
561         sh build.sh watchos
562         build_combined RealmSwift RealmSwift watchos watchsimulator '' "/swift-$REALM_SWIFT_VERSION"
563         cp -R build/watchos/Realm.framework build/watchos/swift-$REALM_SWIFT_VERSION
564         exit 0
565         ;;
566
567     "tvos")
568         build_combined Realm Realm appletvos appletvsimulator
569         exit 0
570         ;;
571
572     "tvos-swift")
573         sh build.sh tvos
574         build_combined RealmSwift RealmSwift appletvos appletvsimulator '' "/swift-$REALM_SWIFT_VERSION"
575         cp -R build/tvos/Realm.framework build/tvos/swift-$REALM_SWIFT_VERSION
576         exit 0
577         ;;
578
579     "osx")
580         xc "-scheme Realm -configuration $CONFIGURATION"
581         clean_retrieve "build/DerivedData/Realm/Build/Products/$CONFIGURATION/Realm.framework" "build/osx" "Realm.framework"
582         exit 0
583         ;;
584
585     "osx-swift")
586         sh build.sh osx
587         xc "-scheme 'RealmSwift' -configuration $CONFIGURATION build"
588         destination="build/osx/swift-$REALM_SWIFT_VERSION"
589         clean_retrieve "build/DerivedData/Realm/Build/Products/$CONFIGURATION/RealmSwift.framework" "$destination" "RealmSwift.framework"
590         cp -R build/osx/Realm.framework "$destination"
591         exit 0
592         ;;
593
594     ######################################
595     # Analysis
596     ######################################
597
598     "analyze-osx")
599         xc "-scheme Realm -configuration $CONFIGURATION analyze"
600         exit 0
601         ;;
602
603     ######################################
604     # Testing
605     ######################################
606     "test")
607         set +e # Run both sets of tests even if the first fails
608         failed=0
609         sh build.sh test-ios-static || failed=1
610         sh build.sh test-ios-dynamic || failed=1
611         sh build.sh test-ios-swift || failed=1
612         sh build.sh test-ios-devices || failed=1
613         sh build.sh test-tvos-devices || failed=1
614         sh build.sh test-osx || failed=1
615         sh build.sh test-osx-swift || failed=1
616         exit $failed
617         ;;
618
619     "test-all")
620         set +e
621         failed=0
622         sh build.sh test || failed=1
623         sh build.sh test-debug || failed=1
624         exit $failed
625         ;;
626
627     "test-ios-static")
628         test_ios_static "name=iPhone 6"
629         exit 0
630         ;;
631
632     "test-ios-dynamic")
633         xc "-scheme Realm -configuration $CONFIGURATION -sdk iphonesimulator -destination 'name=iPhone 6' build"
634         if (( $(xcode_version_major) < 9 )); then
635             xc "-scheme Realm -configuration $CONFIGURATION -sdk iphonesimulator -destination 'name=iPhone 6' test 'ARCHS=\$(ARCHS_STANDARD_32_BIT)'"
636         fi
637         xc "-scheme Realm -configuration $CONFIGURATION -sdk iphonesimulator -destination 'name=iPhone 6' test"
638         exit 0
639         ;;
640
641     "test-ios-swift")
642         xc "-scheme RealmSwift -configuration $CONFIGURATION -sdk iphonesimulator -destination 'name=iPhone 6' build"
643         if (( $(xcode_version_major) < 9 )); then
644             xc "-scheme RealmSwift -configuration $CONFIGURATION -sdk iphonesimulator -destination 'name=iPhone 6' test 'ARCHS=\$(ARCHS_STANDARD_32_BIT)'"
645         fi
646         xc "-scheme RealmSwift -configuration $CONFIGURATION -sdk iphonesimulator -destination 'name=iPhone 6' test"
647         exit 0
648         ;;
649
650     "test-ios-devices")
651         failed=0
652         trap "failed=1" ERR
653         sh build.sh test-ios-devices-objc
654         sh build.sh test-ios-devices-swift
655         exit $failed
656         ;;
657
658     "test-ios-devices-objc")
659         test_devices iphoneos "Realm" "$CONFIGURATION"
660         exit $?
661         ;;
662
663     "test-ios-devices-swift")
664         test_devices iphoneos "RealmSwift" "$CONFIGURATION"
665         exit $?
666         ;;
667
668     "test-tvos")
669         if (( $(xcode_version_major) >= 9 )); then
670             destination="Apple TV"
671         else
672             destination="Apple TV 1080p"
673         fi
674         xc "-scheme Realm -configuration $CONFIGURATION -sdk appletvsimulator -destination 'name=$destination' test"
675         exit $?
676         ;;
677
678     "test-tvos-swift")
679         if (( $(xcode_version_major) >= 9 )); then
680             destination="Apple TV"
681         else
682             destination="Apple TV 1080p"
683         fi
684         xc "-scheme RealmSwift -configuration $CONFIGURATION -sdk appletvsimulator -destination 'name=$destination' test"
685         exit $?
686         ;;
687
688     "test-tvos-devices")
689         test_devices appletvos TestHost "$CONFIGURATION"
690         ;;
691
692     "test-osx")
693         COVERAGE_PARAMS=""
694         if [[ "$CONFIGURATION" == "Debug" ]]; then
695             COVERAGE_PARAMS="GCC_GENERATE_TEST_COVERAGE_FILES=YES GCC_INSTRUMENT_PROGRAM_FLOW_ARCS=YES"
696         fi
697         xc "-scheme Realm -configuration $CONFIGURATION test $COVERAGE_PARAMS"
698         exit 0
699         ;;
700
701     "test-osx-swift")
702         xc "-scheme RealmSwift -configuration $CONFIGURATION test"
703         exit 0
704         ;;
705
706     "test-osx-object-server")
707         xc "-scheme 'Object Server Tests' -configuration $CONFIGURATION -sdk macosx test"
708         exit 0
709         ;;
710
711     ######################################
712     # Full verification
713     ######################################
714     "verify")
715         sh build.sh verify-cocoapods
716         sh build.sh verify-docs
717         sh build.sh verify-osx
718         sh build.sh verify-osx-debug
719         sh build.sh verify-osx-swift
720         sh build.sh verify-osx-swift-debug
721         sh build.sh verify-ios-static
722         sh build.sh verify-ios-static-debug
723         sh build.sh verify-ios-dynamic
724         sh build.sh verify-ios-dynamic-debug
725         sh build.sh verify-ios-swift
726         sh build.sh verify-ios-swift-debug
727         sh build.sh verify-ios-device-objc
728         sh build.sh verify-ios-device-swift
729         sh build.sh verify-watchos
730         sh build.sh verify-tvos
731         sh build.sh verify-tvos-debug
732         sh build.sh verify-tvos-device
733         sh build.sh verify-swiftlint
734         sh build.sh verify-osx-object-server
735         ;;
736
737     "verify-cocoapods")
738         if [[ -d .git ]]; then
739           # Verify the current branch, unless one was already specified in the sha environment variable.
740           if [[ -z $sha ]]; then
741             export sha=$(git rev-parse --abbrev-ref HEAD)
742           fi
743
744           if [[ $(git log -1 @{push}..) != "" ]] || ! git diff-index --quiet HEAD; then
745             echo "WARNING: verify-cocoapods will test the latest revision of $sha found on GitHub."
746             echo "         Any unpushed local changes will not be tested."
747             echo ""
748             sleep 1
749           fi
750         fi
751
752         cd examples/installation
753         sh build.sh test-ios-objc-cocoapods
754         sh build.sh test-ios-objc-cocoapods-dynamic
755         sh build.sh test-ios-swift-cocoapods
756         sh build.sh test-osx-objc-cocoapods
757         sh build.sh test-osx-swift-cocoapods
758         sh build.sh test-watchos-objc-cocoapods
759         sh build.sh test-watchos-swift-cocoapods
760         ;;
761
762     "verify-osx-encryption")
763         REALM_ENCRYPT_ALL=YES sh build.sh test-osx
764         exit 0
765         ;;
766
767     "verify-osx")
768         sh build.sh test-osx
769         sh build.sh analyze-osx
770         sh build.sh examples-osx
771
772         (
773             cd examples/osx/objc/build/DerivedData/RealmExamples/Build/Products/$CONFIGURATION
774             DYLD_FRAMEWORK_PATH=. ./JSONImport >/dev/null
775         )
776         exit 0
777         ;;
778
779     "verify-osx-swift")
780         sh build.sh test-osx-swift
781         exit 0
782         ;;
783
784     "verify-ios-static")
785         sh build.sh test-ios-static
786         sh build.sh examples-ios
787         ;;
788
789     "verify-ios-dynamic")
790         sh build.sh test-ios-dynamic
791         ;;
792
793     "verify-ios-swift")
794         sh build.sh test-ios-swift
795         sh build.sh examples-ios-swift
796         ;;
797
798     "verify-ios-device-objc")
799         sh build.sh test-ios-devices-objc
800         exit 0
801         ;;
802
803     "verify-ios-device-swift")
804         sh build.sh test-ios-devices-swift
805         exit 0
806         ;;
807
808     "verify-docs")
809         sh build.sh docs
810         for lang in swift objc; do
811             undocumented="docs/${lang}_output/undocumented.json"
812             if ruby -rjson -e "j = JSON.parse(File.read('docs/${lang}_output/undocumented.json')); exit j['warnings'].length != 0"; then
813               echo "Undocumented Realm $lang declarations:"
814               cat "$undocumented"
815               exit 1
816             fi
817         done
818         exit 0
819         ;;
820
821     "verify-watchos")
822         sh build.sh watchos-swift
823         exit 0
824         ;;
825
826     "verify-tvos")
827         sh build.sh test-tvos
828         sh build.sh test-tvos-swift
829         sh build.sh examples-tvos
830         sh build.sh examples-tvos-swift
831         exit 0
832         ;;
833
834     "verify-tvos-device")
835         sh build.sh test-tvos-devices
836         exit 0
837         ;;
838
839     "verify-swiftlint")
840         swiftlint lint --strict
841         exit 0
842         ;;
843
844     "verify-osx-object-server")
845         sh build.sh download-object-server
846         sh build.sh test-osx-object-server
847         sh build.sh reset-object-server
848         exit 0
849         ;;
850
851     ######################################
852     # Docs
853     ######################################
854     "docs")
855         build_docs objc
856         build_docs swift
857         exit 0
858         ;;
859
860     ######################################
861     # Examples
862     ######################################
863     "examples")
864         sh build.sh clean
865         sh build.sh examples-ios
866         sh build.sh examples-ios-swift
867         sh build.sh examples-osx
868         sh build.sh examples-tvos
869         sh build.sh examples-tvos-swift
870         exit 0
871         ;;
872
873     "examples-ios")
874         sh build.sh prelaunch-simulator
875         workspace="examples/ios/objc/RealmExamples.xcworkspace"
876         pod install --project-directory="$workspace/.." --no-repo-update
877         xc "-workspace $workspace -scheme Simple -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
878         xc "-workspace $workspace -scheme TableView -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
879         xc "-workspace $workspace -scheme Migration -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
880         xc "-workspace $workspace -scheme Backlink -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
881         xc "-workspace $workspace -scheme GroupedTableView -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
882         xc "-workspace $workspace -scheme RACTableView -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
883         xc "-workspace $workspace -scheme Encryption -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
884         xc "-workspace $workspace -scheme Draw -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
885
886         if [ ! -z "${JENKINS_HOME}" ]; then
887             xc "-workspace $workspace -scheme Extension -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
888         fi
889
890         exit 0
891         ;;
892
893     "examples-ios-swift")
894         sh build.sh prelaunch-simulator
895         workspace="examples/ios/swift/RealmExamples.xcworkspace"
896         if [[ ! -d "$workspace" ]]; then
897             workspace="${workspace/swift/swift-$REALM_SWIFT_VERSION}"
898         fi
899
900         xc "-workspace $workspace -scheme Simple -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
901         xc "-workspace $workspace -scheme TableView -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
902         xc "-workspace $workspace -scheme Migration -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
903         xc "-workspace $workspace -scheme Encryption -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
904         xc "-workspace $workspace -scheme Backlink -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
905         xc "-workspace $workspace -scheme GroupedTableView -configuration $CONFIGURATION -destination 'name=iPhone 6' build ${CODESIGN_PARAMS}"
906         exit 0
907         ;;
908
909     "examples-osx")
910         xc "-workspace examples/osx/objc/RealmExamples.xcworkspace -scheme JSONImport -configuration ${CONFIGURATION} build ${CODESIGN_PARAMS}"
911         ;;
912
913     "examples-tvos")
914         workspace="examples/tvos/objc/RealmExamples.xcworkspace"
915         if (( $(xcode_version_major) >= 9 )); then
916             destination="Apple TV"
917         else
918             destination="Apple TV 1080p"
919         fi
920
921         xc "-workspace $workspace -scheme DownloadCache -configuration $CONFIGURATION -destination 'name=$destination' build ${CODESIGN_PARAMS}"
922         xc "-workspace $workspace -scheme PreloadedData -configuration $CONFIGURATION -destination 'name=$destination' build ${CODESIGN_PARAMS}"
923         exit 0
924         ;;
925
926     "examples-tvos-swift")
927         workspace="examples/tvos/swift/RealmExamples.xcworkspace"
928         if [[ ! -d "$workspace" ]]; then
929             workspace="${workspace/swift/swift-$REALM_SWIFT_VERSION}"
930         fi
931
932         if (( $(xcode_version_major) >= 9 )); then
933             destination="Apple TV"
934         else
935             destination="Apple TV 1080p"
936         fi
937
938         xc "-workspace $workspace -scheme DownloadCache -configuration $CONFIGURATION -destination 'name=$destination' build ${CODESIGN_PARAMS}"
939         xc "-workspace $workspace -scheme PreloadedData -configuration $CONFIGURATION -destination 'name=$destination' build ${CODESIGN_PARAMS}"
940         exit 0
941         ;;
942
943     ######################################
944     # Versioning
945     ######################################
946     "get-version")
947         version_file="Realm/Realm-Info.plist"
948         echo "$(PlistBuddy -c "Print :CFBundleShortVersionString" "$version_file")"
949         exit 0
950         ;;
951
952     "set-version")
953         realm_version="$2"
954         version_files="Realm/Realm-Info.plist"
955
956         if [ -z "$realm_version" ]; then
957             echo "You must specify a version."
958             exit 1
959         fi
960         # The bundle version can contain only three groups of digits separated by periods,
961         # so strip off any -beta.x tag from the end of the version string.
962         bundle_version=$(echo "$realm_version" | cut -d - -f 1)
963         for version_file in $version_files; do
964             PlistBuddy -c "Set :CFBundleVersion $bundle_version" "$version_file"
965             PlistBuddy -c "Set :CFBundleShortVersionString $realm_version" "$version_file"
966         done
967         sed -i '' "s/^VERSION=.*/VERSION=$realm_version/" dependencies.list
968         exit 0
969         ;;
970
971     ######################################
972     # Bitcode Detection
973     ######################################
974
975     "binary-has-bitcode")
976         BINARY="$2"
977         # Although grep has a '-q' flag to prevent logging to stdout, grep
978         # behaves differently when used, so redirect stdout to /dev/null.
979         if otool -l "$BINARY" | grep "segname __LLVM" > /dev/null 2>&1; then
980             exit 0
981         fi
982         # Work around rdar://21826157 by checking for bitcode in thin binaries
983
984         # Get architectures for binary
985         archs="$(lipo -info "$BINARY" | rev | cut -d ':' -f1 | rev)"
986
987         archs_array=( $archs )
988         if [[ ${#archs_array[@]} -lt 2 ]]; then
989             exit 1 # Early exit if not a fat binary
990         fi
991
992         TEMPDIR=$(mktemp -d $TMPDIR/realm-bitcode-check.XXXX)
993
994         for arch in $archs; do
995             lipo -thin "$arch" "$BINARY" -output "$TEMPDIR/$arch"
996             if otool -l "$TEMPDIR/$arch" | grep -q "segname __LLVM"; then
997                 exit 0
998             fi
999         done
1000         exit 1
1001         ;;
1002
1003     ######################################
1004     # CocoaPods
1005     ######################################
1006     "cocoapods-setup")
1007         if [ ! -d core ]; then
1008           sh build.sh download-sync
1009           rm core
1010           mv sync-* core
1011           mv core/librealm-ios.a core/librealmcore-ios.a
1012           mv core/librealm-macosx.a core/librealmcore-macosx.a
1013           mv core/librealm-tvos.a core/librealmcore-tvos.a
1014           mv core/librealm-watchos.a core/librealmcore-watchos.a
1015         fi
1016
1017         if [[ "$2" != "swift" ]]; then
1018           if [ ! -d Realm/ObjectStore/src ]; then
1019             cat >&2 <<EOM
1020
1021
1022 ERROR: One of Realm's submodules is missing!
1023
1024 If you're using Realm and/or RealmSwift from a git branch, please add 'submodules: true' to
1025 their entries in your Podfile.
1026
1027
1028 EOM
1029             exit 1
1030           fi
1031
1032           rm -rf include
1033           mkdir -p include
1034           mv core/include include/core
1035
1036           mkdir -p include/impl/apple include/util/apple include/sync/impl/apple
1037           cp Realm/*.hpp include
1038           cp Realm/ObjectStore/src/*.hpp include
1039           cp Realm/ObjectStore/src/sync/*.hpp include/sync
1040           cp Realm/ObjectStore/src/sync/impl/*.hpp include/sync/impl
1041           cp Realm/ObjectStore/src/sync/impl/apple/*.hpp include/sync/impl/apple
1042           cp Realm/ObjectStore/src/impl/*.hpp include/impl
1043           cp Realm/ObjectStore/src/impl/apple/*.hpp include/impl/apple
1044           cp Realm/ObjectStore/src/util/*.hpp include/util
1045           cp Realm/ObjectStore/src/util/apple/*.hpp include/util/apple
1046
1047           touch Realm/RLMPlatform.h
1048           if [ -n "$COCOAPODS_VERSION" ]; then
1049             # This variable is set for the prepare_command available
1050             # from the 1.0 prereleases, which requires a different
1051             # header layout within the header_mappings_dir.
1052             cp Realm/*.h include
1053           else
1054             # For CocoaPods < 1.0, we need to scope the headers within
1055             # the header_mappings_dir by another subdirectory to avoid
1056             # Clang from complaining about non-modular headers.
1057             mkdir -p include/Realm
1058             cp Realm/*.h include/Realm
1059           fi
1060         else
1061           sh build.sh set-swift-version
1062         fi
1063         ;;
1064
1065     ######################################
1066     # Continuous Integration
1067     ######################################
1068
1069     "ci-pr")
1070         mkdir -p build/reports
1071         # FIXME: Re-enable once CI can properly unlock the keychain
1072         export REALM_DISABLE_METADATA_ENCRYPTION=1
1073
1074         # strip off the ios|tvos version specifier, e.g. the last part of: `ios-device-objc-ios8`
1075         if [[ "$target" =~ ^((ios|tvos)-device(-(objc|swift))?)(-(ios|tvos)[[:digit:]]+)?$ ]]; then
1076             export target=${BASH_REMATCH[1]}
1077         fi
1078
1079         if [ "$target" = "docs" ]; then
1080             sh build.sh set-swift-version
1081             sh build.sh verify-docs
1082         elif [ "$target" = "swiftlint" ]; then
1083             sh build.sh verify-swiftlint
1084         else
1085             export sha=$GITHUB_PR_SOURCE_BRANCH
1086             export CONFIGURATION=$configuration
1087             export REALM_EXTRA_BUILD_ARGUMENTS='GCC_GENERATE_DEBUGGING_SYMBOLS=NO REALM_PREFIX_HEADER=Realm/RLMPrefix.h'
1088             sh build.sh prelaunch-simulator
1089
1090             # Reset CoreSimulator.log
1091             mkdir -p ~/Library/Logs/CoreSimulator
1092             echo > ~/Library/Logs/CoreSimulator/CoreSimulator.log
1093
1094             if [ -d ~/Library/Developer/CoreSimulator/Devices/ ]; then
1095                 # Verify that no Realm files still exist
1096                 ! find ~/Library/Developer/CoreSimulator/Devices/ -name '*.realm' | grep -q .
1097             fi
1098
1099             failed=0
1100             sh build.sh verify-$target 2>&1 | tee build/build.log | xcpretty -r junit -o build/reports/junit.xml || failed=1
1101             if [ "$failed" = "1" ] && cat build/build.log | grep -E 'DTXProxyChannel|DTXChannel|out of date and needs to be rebuilt|operation never finished bootstrapping'; then
1102                 echo "Known Xcode error detected. Running job again."
1103                 if cat build/build.log | grep -E 'out of date and needs to be rebuilt'; then
1104                     rm -rf build/DerivedData
1105                 fi
1106                 failed=0
1107                 sh build.sh verify-$target | tee build/build.log | xcpretty -r junit -o build/reports/junit.xml || failed=1
1108             elif [ "$failed" = "1" ] && tail ~/Library/Logs/CoreSimulator/CoreSimulator.log | grep -E "Operation not supported|Failed to lookup com.apple.coreservices.lsuseractivity.simulatorsupport"; then
1109                 echo "Known Xcode error detected. Running job again."
1110                 failed=0
1111                 sh build.sh verify-$target | tee build/build.log | xcpretty -r junit -o build/reports/junit.xml || failed=1
1112             fi
1113             if [ "$failed" = "1" ]; then
1114                 echo "\n\n***\nbuild/build.log\n***\n\n" && cat build/build.log || true
1115                 echo "\n\n***\nCoreSimulator.log\n***\n\n" && cat ~/Library/Logs/CoreSimulator/CoreSimulator.log
1116                 exit 1
1117             fi
1118         fi
1119
1120         if [ "$target" = "osx" ] && [ "$configuration" = "Debug" ]; then
1121           gcovr -r . -f ".*Realm.*" -e ".*Tests.*" -e ".*core.*" --xml > build/reports/coverage-report.xml
1122           WS=$(pwd | sed "s/\//\\\\\//g")
1123           sed -i ".bak" "s/<source>\./<source>${WS}/" build/reports/coverage-report.xml
1124         fi
1125         ;;
1126
1127     ######################################
1128     # Release packaging
1129     ######################################
1130
1131     "package-examples")
1132         ./scripts/package_examples.rb
1133         zip --symlinks -r realm-examples.zip examples -x "examples/installation/*"
1134         ;;
1135
1136     "package-test-examples")
1137         if ! VERSION=$(echo realm-objc-*.zip | egrep -o '\d*\.\d*\.\d*-[a-z]*(\.\d*)?'); then
1138             VERSION=$(echo realm-objc-*.zip | egrep -o '\d*\.\d*\.\d*')
1139         fi
1140         OBJC="realm-objc-${VERSION}"
1141         SWIFT="realm-swift-${VERSION}"
1142         unzip ${OBJC}.zip
1143
1144         cp $0 ${OBJC}
1145         cp -r ${source_root}/scripts ${OBJC}
1146         cd ${OBJC}
1147         sh build.sh examples-ios
1148         sh build.sh examples-tvos
1149         sh build.sh examples-osx
1150         cd ..
1151         rm -rf ${OBJC}
1152
1153         unzip ${SWIFT}.zip
1154
1155         cp $0 ${SWIFT}
1156         cp -r ${source_root}/scripts ${SWIFT}
1157         cd ${SWIFT}
1158         sh build.sh examples-ios-swift
1159         sh build.sh examples-tvos-swift
1160         cd ..
1161         rm -rf ${SWIFT}
1162         ;;
1163
1164     "package-ios-static")
1165         sh build.sh prelaunch-simulator
1166         sh build.sh ios-static
1167
1168         cd build/ios-static
1169         zip --symlinks -r realm-framework-ios-static.zip Realm.framework
1170         ;;
1171
1172     "package-ios")
1173         sh build.sh prelaunch-simulator
1174         sh build.sh ios-dynamic
1175         cd build/ios
1176         zip --symlinks -r realm-framework-ios.zip Realm.framework
1177         ;;
1178
1179     "package-osx")
1180         sh build.sh osx
1181
1182         cd build/DerivedData/Realm/Build/Products/Release
1183         zip --symlinks -r realm-framework-osx.zip Realm.framework
1184         ;;
1185
1186     "package-ios-swift")
1187         for version in 8.3.3 9.0 9.1 9.2; do
1188             REALM_XCODE_VERSION=$version
1189             REALM_SWIFT_VERSION=
1190             set_xcode_and_swift_versions
1191             sh build.sh prelaunch-simulator
1192             sh build.sh ios-swift
1193         done
1194
1195         cd build/ios
1196         ln -s swift-4.0 swift-3.2
1197         ln -s swift-4.0.2 swift-3.2.2
1198         ln -s swift-4.0.2 swift-3.2.3
1199         ln -s swift-4.0.2 swift-4.0.3
1200         zip --symlinks -r realm-swift-framework-ios.zip swift-3.1 swift-3.2 swift-3.2.2 swift-3.2.3 swift-4.0 swift-4.0.2 swift-4.0.3
1201         ;;
1202
1203     "package-osx-swift")
1204         for version in 8.3.3 9.0 9.1 9.2; do
1205             REALM_XCODE_VERSION=$version
1206             REALM_SWIFT_VERSION=
1207             set_xcode_and_swift_versions
1208             sh build.sh prelaunch-simulator
1209             sh build.sh osx-swift
1210         done
1211
1212         cd build/osx
1213         ln -s swift-4.0 swift-3.2
1214         ln -s swift-4.0.2 swift-3.2.2
1215         ln -s swift-4.0.2 swift-3.2.3
1216         ln -s swift-4.0.2 swift-4.0.3
1217         zip --symlinks -r realm-swift-framework-osx.zip swift-3.1 swift-3.2 swift-3.2.2 swift-3.2.3 swift-4.0 swift-4.0.2 swift-4.0.3
1218         ;;
1219
1220     "package-watchos")
1221         sh build.sh prelaunch-simulator
1222         sh build.sh watchos
1223
1224         cd build/watchos
1225         zip --symlinks -r realm-framework-watchos.zip Realm.framework
1226         ;;
1227
1228     "package-watchos-swift")
1229         for version in 8.3.3 9.0 9.1 9.2; do
1230             REALM_XCODE_VERSION=$version
1231             REALM_SWIFT_VERSION=
1232             set_xcode_and_swift_versions
1233             sh build.sh prelaunch-simulator
1234             sh build.sh watchos-swift
1235         done
1236
1237         cd build/watchos
1238         ln -s swift-4.0 swift-3.2
1239         ln -s swift-4.0.2 swift-3.2.2
1240         ln -s swift-4.0.2 swift-3.2.3
1241         ln -s swift-4.0.2 swift-4.0.3
1242         zip --symlinks -r realm-swift-framework-watchos.zip swift-3.1 swift-3.2 swift-3.2.2 swift-3.2.3 swift-4.0 swift-4.0.2 swift-4.0.3
1243         ;;
1244
1245     "package-tvos")
1246         sh build.sh prelaunch-simulator
1247         sh build.sh tvos
1248
1249         cd build/tvos
1250         zip --symlinks -r realm-framework-tvos.zip Realm.framework
1251         ;;
1252
1253     "package-tvos-swift")
1254         for version in 8.3.3 9.0 9.1 9.2; do
1255             REALM_XCODE_VERSION=$version
1256             REALM_SWIFT_VERSION=
1257             set_xcode_and_swift_versions
1258             sh build.sh prelaunch-simulator
1259             sh build.sh tvos-swift
1260         done
1261
1262         cd build/tvos
1263         ln -s swift-4.0 swift-3.2
1264         ln -s swift-4.0.2 swift-3.2.2
1265         ln -s swift-4.0.2 swift-3.2.3
1266         ln -s swift-4.0.2 swift-4.0.3
1267         zip --symlinks -r realm-swift-framework-tvos.zip swift-3.1 swift-3.2 swift-3.2.2 swift-3.2.3 swift-4.0 swift-4.0.2 swift-4.0.3
1268         ;;
1269
1270     package-*-swift-3.2)
1271         PLATFORM=$(echo $COMMAND | cut -d - -f 2)
1272         mkdir -p build/$PLATFORM
1273         cd build/$PLATFORM
1274         ln -s swift-4.0 swift-3.2
1275         zip --symlinks -r realm-swift-framework-$PLATFORM-swift-3.2.zip swift-3.2
1276         ;;
1277
1278     package-*-swift-3.2.2)
1279         PLATFORM=$(echo $COMMAND | cut -d - -f 2)
1280         mkdir -p build/$PLATFORM
1281         cd build/$PLATFORM
1282         ln -s swift-4.0.2 swift-3.2.2
1283         zip --symlinks -r realm-swift-framework-$PLATFORM-swift-3.2.2.zip swift-3.2.2
1284         ;;
1285
1286     package-*-swift-3.2.3)
1287         PLATFORM=$(echo $COMMAND | cut -d - -f 2)
1288         mkdir -p build/$PLATFORM
1289         cd build/$PLATFORM
1290         ln -s swift-4.0.2 swift-3.2.3
1291         zip --symlinks -r realm-swift-framework-$PLATFORM-swift-3.2.3.zip swift-3.2.3
1292         ;;
1293
1294     package-*-swift-4.0.3)
1295         PLATFORM=$(echo $COMMAND | cut -d - -f 2)
1296         mkdir -p build/$PLATFORM
1297         cd build/$PLATFORM
1298         ln -s swift-4.0.2 swift-4.0.3
1299         zip --symlinks -r realm-swift-framework-$PLATFORM-swift-4.0.3.zip swift-4.0.3
1300         ;;
1301
1302     package-*-swift-*)
1303         PLATFORM=$(echo $COMMAND | cut -d - -f 2)
1304         REALM_SWIFT_VERSION=$(echo $COMMAND | cut -d - -f 4)
1305         REALM_XCODE_VERSION=
1306
1307         set_xcode_and_swift_versions
1308         sh build.sh prelaunch-simulator
1309         sh build.sh $PLATFORM-swift
1310
1311         cd build/$PLATFORM
1312         zip --symlinks -r realm-swift-framework-$PLATFORM-swift-$REALM_SWIFT_VERSION.zip swift-$REALM_SWIFT_VERSION
1313         ;;
1314
1315     "package-release")
1316         LANG="$2"
1317         TEMPDIR=$(mktemp -d $TMPDIR/realm-release-package-${LANG}.XXXX)
1318
1319         VERSION=$(sh build.sh get-version)
1320
1321         FOLDER=${TEMPDIR}/realm-${LANG}-${VERSION}
1322
1323         mkdir -p ${FOLDER}/osx ${FOLDER}/ios ${FOLDER}/watchos ${FOLDER}/tvos
1324
1325         if [[ "${LANG}" == "objc" ]]; then
1326             mkdir -p ${FOLDER}/ios/static
1327             mkdir -p ${FOLDER}/ios/dynamic
1328             mkdir -p ${FOLDER}/Swift
1329
1330             (
1331                 cd ${FOLDER}/osx
1332                 unzip ${WORKSPACE}/realm-framework-osx.zip
1333             )
1334
1335             (
1336                 cd ${FOLDER}/ios/static
1337                 unzip ${WORKSPACE}/realm-framework-ios-static.zip
1338             )
1339
1340             (
1341                 cd ${FOLDER}/ios/dynamic
1342                 unzip ${WORKSPACE}/realm-framework-ios.zip
1343             )
1344
1345             (
1346                 cd ${FOLDER}/watchos
1347                 unzip ${WORKSPACE}/realm-framework-watchos.zip
1348             )
1349
1350             (
1351                 cd ${FOLDER}/tvos
1352                 unzip ${WORKSPACE}/realm-framework-tvos.zip
1353             )
1354         else
1355             (
1356                 cd ${FOLDER}/osx
1357                 for f in ${WORKSPACE}/realm-swift-framework-osx-swift-*.zip; do
1358                     unzip "$f"
1359                 done
1360             )
1361
1362             (
1363                 cd ${FOLDER}/ios
1364                 for f in ${WORKSPACE}/realm-swift-framework-ios-swift-*.zip; do
1365                     unzip "$f"
1366                 done
1367             )
1368
1369             (
1370                 cd ${FOLDER}/watchos
1371                 for f in ${WORKSPACE}/realm-swift-framework-watchos-swift-*.zip; do
1372                     unzip "$f"
1373                 done
1374             )
1375
1376             (
1377                 cd ${FOLDER}/tvos
1378                 for f in ${WORKSPACE}/realm-swift-framework-tvos-swift-*.zip; do
1379                     unzip "$f"
1380                 done
1381             )
1382         fi
1383
1384         (
1385             cd ${WORKSPACE}
1386             cp -R plugin ${FOLDER}
1387             cp LICENSE ${FOLDER}/LICENSE.txt
1388             if [[ "${LANG}" == "objc" ]]; then
1389                 cp Realm/Swift/RLMSupport.swift ${FOLDER}/Swift/
1390             fi
1391         )
1392
1393         (
1394             cd ${FOLDER}
1395             unzip ${WORKSPACE}/realm-examples.zip
1396             cd examples
1397             if [[ "${LANG}" == "objc" ]]; then
1398                 rm -rf ios/swift-* tvos/swift-*
1399             else
1400                 rm -rf ios/objc ios/rubymotion osx tvos/objc
1401             fi
1402         )
1403
1404         cat > ${FOLDER}/docs.webloc <<EOF
1405 <?xml version="1.0" encoding="UTF-8"?>
1406 <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
1407 <plist version="1.0">
1408 <dict>
1409     <key>URL</key>
1410     <string>https://realm.io/docs/${LANG}/${VERSION}</string>
1411 </dict>
1412 </plist>
1413 EOF
1414
1415         (
1416           cd ${TEMPDIR}
1417           zip --symlinks -r realm-${LANG}-${VERSION}.zip realm-${LANG}-${VERSION}
1418           mv realm-${LANG}-${VERSION}.zip ${WORKSPACE}
1419         )
1420         ;;
1421
1422     "test-package-release")
1423         # Generate a release package locally for testing purposes
1424         # Real releases should always be done via Jenkins
1425         if [ -z "${WORKSPACE}" ]; then
1426             echo 'WORKSPACE must be set to a directory to assemble the release in'
1427             exit 1
1428         fi
1429         if [ -d "${WORKSPACE}" ]; then
1430             echo 'WORKSPACE directory should not already exist'
1431             exit 1
1432         fi
1433
1434         REALM_SOURCE="$(pwd)"
1435         mkdir -p "$WORKSPACE"
1436         WORKSPACE="$(cd "$WORKSPACE" && pwd)"
1437         export WORKSPACE
1438         cd $WORKSPACE
1439         git clone --recursive $REALM_SOURCE realm-cocoa
1440         cd realm-cocoa
1441
1442         echo 'Packaging iOS'
1443         sh build.sh package-ios-static
1444         cp build/ios-static/realm-framework-ios-static.zip ..
1445         sh build.sh package-ios
1446         cp build/ios/realm-framework-ios.zip ..
1447         sh build.sh package-ios-swift
1448         cp build/ios/realm-swift-framework-ios.zip ..
1449
1450         echo 'Packaging OS X'
1451         sh build.sh package-osx
1452         cp build/DerivedData/Realm/Build/Products/Release/realm-framework-osx.zip ..
1453         sh build.sh package-osx-swift
1454         cp build/osx/realm-swift-framework-osx.zip ..
1455
1456         echo 'Packaging watchOS'
1457         sh build.sh package-watchos
1458         cp build/watchos/realm-framework-watchos.zip ..
1459         sh build.sh package-watchos-swift
1460         cp build/watchos/realm-swift-framework-watchos.zip ..
1461
1462         echo 'Packaging tvOS'
1463         sh build.sh package-tvos
1464         cp build/tvos/realm-framework-tvos.zip ..
1465         sh build.sh package-tvos-swift
1466         cp build/tvos/realm-swift-framework-tvos.zip ..
1467
1468         echo 'Packaging examples'
1469         sh build.sh package-examples
1470         cp realm-examples.zip ..
1471
1472         echo 'Building final release packages'
1473         sh build.sh package-release objc
1474         sh build.sh package-release swift
1475
1476         echo 'Testing packaged examples'
1477         sh build.sh package-test-examples
1478         ;;
1479
1480     "github-release")
1481         if [ -z "${GITHUB_ACCESS_TOKEN}" ]; then
1482             echo 'GITHUB_ACCESS_TOKEN must be set to create GitHub releases'
1483             exit 1
1484         fi
1485         ./scripts/github_release.rb
1486         ;;
1487
1488     "add-empty-changelog")
1489         empty_section=$(cat <<EOS
1490 x.x.x Release notes (yyyy-MM-dd)
1491 =============================================================
1492
1493 ### Breaking Changes
1494
1495 * None.
1496
1497 ### Enhancements
1498
1499 * None.
1500
1501 ### Bugfixes
1502
1503 * None.
1504 EOS)
1505         changelog=$(cat CHANGELOG.md)
1506         echo "$empty_section" > CHANGELOG.md
1507         echo >> CHANGELOG.md
1508         echo "$changelog" >> CHANGELOG.md
1509         ;;
1510
1511     *)
1512         echo "Unknown command '$COMMAND'"
1513         usage
1514         exit 1
1515         ;;
1516 esac