Path does not exist during CICD with code magic - ios

when i am running this command it gives this error
Command:
- name: Build ipa for distribution
script: |
xcode-project build-ipa \
--workspace "$CM_BUILD_DIR/ios/$XCODE_WORKSPACE" \
--scheme "$XCODE_SCHEME"
Error Snapshot
xcode-project: error: argument --export-options-plist: Path "/Users/builder/export_options.plist" does not exist
Build failed :|
Step 6 script `Build ipa for distribution` exited with status code 2

Need to add xcode-project use-profiles step before building the IPA. Error seems to be missing code signing step.
- name: Install CocoaPods dependencies
script: |
cd ios && pod install
- name: Set up provisioning profiles settings on Xcode project
script: xcode-project use-profiles
- name: Build ipa for distribution
script: |
xcode-project build-ipa \
--workspace "$CM_BUILD_DIR/ios/$XCODE_WORKSPACE" \
--scheme "$XCODE_SCHEME"
Reference:
https://docs.codemagic.io/yaml-code-signing/signing-ios/

Related

Error on codemagic publishing IPA to testflight

i having the follow error:
Command: app-store-connect publish --path /Users/builder/clone/build/ios/ipa/zimexahse.ipa --key-id '$APP_STORE_CONNECT_KEY_IDENTIFIER' --issuer-id '$APP_STORE_CONNECT_ISSUER_ID' --private-key #env:APP_STORE_CONNECT_PUBLISHER_PRIVATE_KEY
error: argument --private-key: Provided value in environment variable "APP_STORE_CONNECT_PUBLISHER_PRIVATE_KEY" is not valid. Provided value is not a valid PEM encoded private key
codemagic.yaml
workflows:
ios-workflow-id:
name: iOS Workflow
max_build_duration: 120
instance_type: mac_mini_m1
environment:
node: 14.17.6
npm: latest
ios_signing:
distribution_type: development # or: ad_hoc | development | enterprise
bundle_identifier: ...
groups:
- appstore_credentials
vars:
APP_ID: ...
BUNDLE_ID: "..."
XCODE_WORKSPACE: "....xcworkspace"
XCODE_SCHEME: "..."
scripts:
- name: install node dependencies
script: |
yarn install
# npm install --legacy-peer-deps
- name: Set Info.plist values
script: |
PLIST=$CM_BUILD_DIR/$XCODE_SCHEME/Info.plist
PLIST_BUDDY=/usr/libexec/PlistBuddy
$PLIST_BUDDY -c "Add :ITSAppUsesNonExemptEncryption bool false" $PLIST
- name: Install CocoaPods dependencies
script: |
cd ios && pod install
- name: Set up provisioning profiles settings on Xcode project
script: xcode-project use-profiles
- name: Increment build number
script: |
cd $CM_BUILD_DIR/ios
LATEST_BUILD_NUMBER=$(app-store-connect get-latest-app-store-build-number "$APP_ID")
agvtool new-version -all $(($LATEST_BUILD_NUMBER + 1))
- name: Build ipa for distribution
script: |
xcode-project build-ipa \
--workspace "$CM_BUILD_DIR/ios/$XCODE_WORKSPACE" \
--scheme "$XCODE_SCHEME" \
--archive-flags="-destination 'generic/platform=iOS'"
artifacts:
- build/ios/ipa/*.ipa
- /tmp/xcodebuild_logs/*.log
- $HOME/Library/Developer/Xcode/DerivedData/**/Build/**/*.app
- $HOME/Library/Developer/Xcode/DerivedData/**/Build/**/*.dSYM
publishing:
app_store_connect:
api_key: $APP_STORE_CONNECT_PRIVATE_KEY
key_id: $APP_STORE_CONNECT_KEY_IDENTIFIER
issuer_id: $APP_STORE_CONNECT_ISSUER_ID
submit_to_testflight: true
beta_groups:
- ...
submit_to_app_store: false
the api key was already configured in codemagic
make sure APP_STORE_CONNECT_PUBLISHER_PRIVATE_KEY variable includes -----BEGIN OPENSSH PRIVATE KEY----- and -----END OPENSSH PRIVATE KEY----- lines (depends on the key format it can be RSA instead of OPENSSH)

Turn Package.swift file into binary XCFramework

Someone in my company created a Swift package SDK and now I was tasked to publish it for the customer in a binary way so that the end customers that will use the SDK will not be able to see the source code of it. This is how the SDK is built:
the SDK in xcode (p.s. the build folder is empty)
From my reading on the subject I understand that I need to export the files into an XCFramework file. However, the vast majority of guides I've encountered explain how to make this progress from a framework, and not from a package like in my case..
The only guide I found that seems exactly like what I need is this one, however I get an error right on the first relevant terminal command of xcodebuild -scheme [my scheme name] -sdk iphoneos -configuration Release ARCHS="arm64" BUILD_DIR="./Build". This is the main error line I get: xcodebuild: error: Building a Swift package requires that a destination is provided using the "-destination" option. The "-showdestinations" option can be used to list the available destinations.. Why would I need to specify a destination? I want the SDK to work for all the devices (ios 13+). Non of the forums I searched in online helped me solve this.
I also read Apple's instructions here but got very confused about how the terminal command in step 2 is supposed to look like in my case. Are some of the fields mandatory and some are not?
Any help would be much appreciated!!
Assuming you are working with iOS only and you need an xcframework for both device and simulator architectures, in order to generate an XCFramework from a swift package you need to:
Mark your Package as .dynamic (i.e. .library(name: "Foo", type: .dynamic, targets: ["Foo"]))
Archive the project for both simulator and device. This will generate a .framework file for each architecture.
Copy Modules folders (if any) into the .xcarchive files
Copy the bundles (if any) into the .xcarchive files
Create the xcframework with the frameworks created in step 2
Here's a bash script, based on the one from this swift forums post, to create an XCFramework from a swift package (in my case, I have my package inside an xcworkspace. I didn't try it as a standalone package, not sure if that can be done):
Change the input parameters as needed :), but most importantly replace <Your project name> and <your workspace>.
#!/bin/bash
PROJECT_NAME="<Your project name>"
PROJECT_DIR="./Packages/${PROJECT_NAME}" # Relative path to the directory containing the `Package.swift` file
BUILD_FOLDER="./build"
OUTPUT_DIR="${PROJECT_DIR}/Output"
SIMULATOR_ARCHIVE="${OUTPUT_DIR}/${PROJECT_NAME}-iphonesimulator.xcarchive"
DEVICE_ARCHIVE="${OUTPUT_DIR}/${PROJECT_NAME}-iphoneos.xcarchive"
rm -rf "$OUTPUT_DIR"
mkdir -p "$OUTPUT_DIR"
# 2 iterations: 1 for device arch and another for simulator arch
for PLATFORM in "iOS" "iOS Simulator"; do
case $PLATFORM in
"iOS")
ARCHIVE=$DEVICE_ARCHIVE
SDK=iphoneos
RELEASE_FOLDER="Release-iphoneos"
;;
"iOS Simulator")
ARCHIVE=$SIMULATOR_ARCHIVE
SDK=iphonesimulator
RELEASE_FOLDER="Release-iphonesimulator"
;;
esac
# Step 2
xcodebuild archive \
-workspace <your workspace>.xcworkspace \
-scheme $PROJECT_NAME \
-destination="generic/platform=${PLATFORM}" \
-archivePath $ARCHIVE \
-sdk $SDK \
-derivedDataPath $BUILD_FOLDER \
SKIP_INSTALL=NO \
BUILD_LIBRARY_FOR_DISTRIBUTION=YES
FRAMEWORK_PATH="${ARCHIVE}/Products/Library/Frameworks/${PROJECT_NAME}.framework"
MODULES_PATH="$FRAMEWORK_PATH/Modules"
mkdir -p $MODULES_PATH
BUILD_PRODUCTS_PATH="${BUILD_FOLDER}/Build/Intermediates.noindex/ArchiveIntermediates/${PROJECT_NAME}/BuildProductsPath"
RELEASE_PATH="${BUILD_PRODUCTS_PATH}/${RELEASE_FOLDER}"
SWIFT_MODULE_PATH="${RELEASE_PATH}/${PROJECT_NAME}.swiftmodule"
RESOURCES_BUNDLE_PATH="${RELEASE_PATH}/${PROJECT_NAME}_${PROJECT_NAME}.bundle"
# Step 3
if [ -d $SWIFT_MODULE_PATH ]
then
cp -r $SWIFT_MODULE_PATH $MODULES_PATH
fi
# Step 4
if [ -e $RESOURCES_BUNDLE_PATH ]
then
cp -r $RESOURCES_BUNDLE_PATH $FRAMEWORK_PATH
fi
done
# Step 5
xcodebuild -create-xcframework \
-framework "${DEVICE_ARCHIVE}/Products/Library/Frameworks/${PROJECT_NAME}.framework" \
-framework "${SIMULATOR_ARCHIVE}/Products/Library/Frameworks/${PROJECT_NAME}.framework" \
-output "${OUTPUT_DIR}/${PROJECT_NAME}.xcframework"
When the script ends, you will see 3 files in the output folder:
Device xcarchive
Simulator xcarchive
XCFramework
You can remove the xcarchives, as you won't need them anymore (you can also update the script to do that for you).

Failing to execute tests in Bitrise for debug variant

Description
I'm using Bitrise to run Detox tests. The build command runs ok and is a success. But the test command always fails.
Running locally:
Command detox test -c ios.sim.debug without starting the packager: 'No bundle URL present' error
Command detox test -c ios.sim.debug with the packager: Opens the packager and everything runs OK.
Command detox test -c ios.sim.release without the packager: works fine.
Command detox test -c ios.sim.release with the packager: works fine.
Running in Bitrise:
Command detox test -c ios.sim.debug --cleanup without starting the packager: 'No bundle URL present' error
Command detox test -c ios.sim.debug --cleanup with the packager:
Verify tests are up
"before all" hook:
Error: Timeout of 120000ms exceeded. For async tests and hooks, ensure "done()" is called; if returning a Promise, ensure it resolves. (/Users/vagrant/git/e2e/tests.spec.js)
Command detox test -c ios.sim.release --cleanup without the packager: works fine.
Command detox test -c ios.sim.release --cleanup with the packager: works fine.
Disclaimer
With/Without the packager means the variable RCT_NO_LAUNCH_PACKAGER equals false/true, respectively.
The package.json file
"ios.sim.debug": {
"binaryPath": "ios/build/Build/Products/Debug-iphonesimulator/PROJECT_NAME.app",
"build": "export RCT_NO_LAUNCH_PACKAGER=true && xcodebuild -workspace ios/PROJECT_NAME.xcworkspace -scheme INTEGRATION_SCHEME -configuration Debug -sdk iphonesimulator -derivedDataPath ios/build",
"type": "ios.simulator",
"name": "iPhone 7"
},
"ios.sim.release": {
"binaryPath": "ios/build/Build/Products/Release-iphonesimulator/PROJECT_NAME.app",
"build": "export RCT_NO_LAUNCH_PACKAGER=true && xcodebuild -workspace ios/PROJECT_NAME.xcworkspace -scheme PRODUCTION_SCHEME -configuration Release -sdk iphonesimulator -derivedDataPath ios/build",
"type": "ios.simulator",
"name": "iPhone 7 Plus"
},
The bitrise.yml file
_init_install:
steps:
- activate-ssh-key#3.1.1:
run_if: '{{getenv "SSH_RSA_PRIVATE_KEY" | ne ""}}'
- git-clone#4.0.11: {}
- script#1.1.5:
inputs:
- content: |-
#!/usr/bin/env bash
# fail if any commands fails
set -e
# debug log
set -x
# write your script here
brew uninstall --ignore-dependencies node
brew install node#8
brew link --overwrite --force node#8
- yarn#0.0.7: {}
_detox_tests:
steps:
- npm#0.9.0:
title: Install Detox CLI
inputs:
- command: install -g detox-cli
- npm#0.9.0:
title: Install React-Native CLI
inputs:
- command: install -g react-native-cli
- script#1.1.5:
title: Install Detox Utils
inputs:
- content: |-
#!/bin/bash
brew tap facebook/fb
export CODE_SIGNING_REQUIRED=NO
brew install fbsimctl
brew tap wix/brew
brew install applesimutils --HEAD
- script#1.1.5:
title: Detox - Build Debug App
inputs:
- content: |-
#!/usr/bin/env bash
detox build -c ios.sim.debug
- script#1.1.5:
title: Detox - Run E2E Tests
inputs:
- content: |-
#!/usr/bin/env bash
detox test -c ios.sim.debug --cleanup
- deploy-to-bitrise-io#1.3.10: {}
test_ios:
before_run:
- _init_install
after_run:
- _detox_tests
steps:
- cocoapods-install#1.7.2:
inputs:
- podfile_path: ios/Podfile
- resource-archive#2.0.1:
inputs:
- extract_to_path: "$HOME/Documents/FacebookSDK/"
- archive_url:https://origincache.facebook.com/developers/resources/?id=facebook-ios-sdk-current.zip
- certificate-and-profile-installer#1.9.3: {}
```
Detox, Node, Device, Xcode and macOS Versions
Detox: v7.4.3
React Native: v0.51.0
Node: v9.4.0
Device: iPhone 7 (simulator)
Xcode: Version 9.3 (9E145)
macOS: 10.13.3 (17D102)
Device and verbose Detox logs
Error detox test -c ios.sim.debug --cleanup with the packager
pastebin
File detox.last_launch_app_log.err prints:
pastebin
TL;DR
I get an error when running Detox with Bitrise. The command detox test -c ios.sim.debug --cleanup should open a packager but looks like it's not doing it.
The version that is needed to test is the Debug one, no other options. Maybe I missed something about the installation, but all the files were checked with official docs and other examples and are the identical.
Related issues: 742, 749, 740

How to use cocoapods integrated project with OCLint?

I can build the project and generate OCLint report on a project without cocoapods but when integrated with cocoapods the build for project is successful but the build for OCLint results into errors for the file which are present into cocoapods and build fails.
So how to make build successful for cocoapods with OCLint?
Any help would be appreciated.
Below is the script I am using to generate html file for cocoapods integrated project with OCLint.
OCLINT_HOME is the path for oclint downloaded folder. I have renamed the folder to oclintrelease.
OCLINT_HOME=/Users/Dheeraj/Downloads/oclintrelease
export PATH=$OCLINT_HOME/bin:$PATH
hash oclint &> /dev/null
if [ $? -eq 1 ]; then
echo >&2 "oclint not found, analyzing stopped"
exit 1
fi
cd ${TARGET_TEMP_DIR}
if [ ! -f compile_commands.json ]; then
echo "[*] compile_commands.json not found, possibly clean was performed"
echo "Workspace Path : ${MY_WORKSPACE}"
echo "[*] starting xcodebuild to rebuild the project.."
# clean previous output
if [ -f xcodebuild.log ]; then
rm xcodebuild.log
echo "Oclint Clean performed"
fi
cd ${SRCROOT}
xcodebuild clean
#build xcodebuild.log
xcodebuild ONLY_ACTIVE_ARCH=NO -workspace ${PROJECT_NAME}.xcworkspace -scheme ${PROJECT_NAME} -configuration Debug clean build| tee ${TARGET_TEMP_DIR}/xcodebuild.log
#xcodebuild <options>| tee ${TARGET_TEMP_DIR}/xcodebuild.log
echo "[*] transforming xcodebuild.log into compile_commands.json..."
cd ${TARGET_TEMP_DIR}
#transform it into compile_commands.json
oclint-xcodebuild
fi
echo "[*] starting analyzing"
cd ${TARGET_TEMP_DIR}
oclint-json-compilation-database -e /Users/Dheeraj/Desktop/sampleCocoaPods/Pods/ -v oclint_args "-report-type html -o /Users/Dheeraj/NewHTMLREPORT.html" | sed 's/\(.*\.\m\{1,2\}:[0-9]*:[0-9]*:\)/\1 warning:/'
It will exclude all the Pods related files.
If you want to include Pods file as well then replace last line in script by :
oclint-json-compilation-database -v oclint_args "-report-type html -o /Users/Dheeraj/NewHTMLREPORT.html" | sed 's/\(.*\.\m\{1,2\}:[0-9]*:[0-9]*:\)/\1 warning:/'
Notes :
Please try first with a short sample Application including cocoapods and once you have generated report for sample application then integrate script into your real application as building with OCLint takes a lot of time to generate the report.
Always clean application and then build with OCLint.
Link for reference

Jenkins + iOS + TestFlight API

I installed a Jenkins and startet a Project with the Git Plugin, Xcode Plugin and the Testflight Plugin.
I can create automatic builds with the setup, but it is failing at the point on creating the .ipa files for Testflight.
The problem are at Debug and Release settings in different ways though…
If i try to create a .ipa via the Debug settings it will fail at the point that there is no build/Debug-iphoneos folder (i tried to turn of the clean option but it didn't helped). But the Xcode Build is not failing on the command line
When i try to switch to Release the linker is failing (ld).
Whithout the .ipa files i can't submit to Testflight and get a automated Test distributing.
Here is the script I'm using. (Obviously I removed the personal information, but you should be fine to understand it).
TARGET_NAME="-" # Target name
TARGET_SDK="iphoneos" # Target SDK: iphoneos
CONFIGURATION="Release" # Build Configuration
BUILD_DIR="build" # Directory where the build is generated
ARCHS="armv7" # Valid Architectures
APP_NAME="-" # Application name
## Provisioning configurations
BUILD_ARCHIVED_DIR="BuildArchived" # Directory with the history of builds
DEVELOPER_NAME="-" # Developer name
PROVISIONING_PROFILE=Prototype.mobileprovision # Provisioning profile file
PROVISIONING_DIR=~/Library/MobileDevice/Provisioning\ Profiles/ # Provisioning dir
## TestFlight App
TESTFLIGHT_API_TOKEN="-"
TESTFLIGHT_TEAM_TOKEN="-"
#Release Notes
BUILDSCRIPTS_DIR="build"
TESTFLIGHT_RELEASE_NOTES_FILE="ios_testflight-releasenotes"
#Distribution Lists
TESTFLIGHT_DISTRIBUTION_LISTS="Jenkins"
# Returns to the root directory of the build
cd ../ios
PROJECT_BUILDDIR="${BUILD_DIR}/${CONFIGURATION}-${TARGET_SDK}"
CURRENT_DIR=`pwd`
# fix for the newest sdk
# Only export the environment variable if the location exists,
# otherwise it breaks the signing process!
if [ -f "/Developer/Platforms/iPhoneOS.platform/Developer/usr/bin/codesign_allocate" ]
then
echo Export environment variable for codesign_allocate location
export CODESIGN_ALLOCATE=/Developer/Platforms/iPhoneOS.platform/Developer/usr/bin/codesign_allocate
fi
#changing the build version
INFO_PLIST_PATH="${CURRENT_DIR}/${TARGET_NAME}/${TARGET_NAME}-Info.plist"
/usr/libexec/PlistBuddy -c "Set :CFBundleVersion ${SVN_REVISION}" $INFO_PLIST_PATH
# compile project
echo Building Project
xcodebuild -target "${TARGET_NAME}" -sdk "${TARGET_SDK}" ARCHS=${ARCHS} -configuration "${CONFIGURATION}" clean build
#Check if build succeeded
#if [ $? != 0 ]
#then
# exit 1
#fi
# Create output dir ($x) if doesn't exist
mkdir -p $BUILD_ARCHIVED_DIR
# .ipa file generation
echo Generating .ipa file
/usr/bin/xcrun -sdk "${TARGET_SDK}" PackageApplication -v "${PROJECT_BUILDDIR}/${APP_NAME}.app" -o "${CURRENT_DIR}/${BUILD_ARCHIVED_DIR}/${APP_NAME}.ipa" --sign "${DEVELOPER_NAME}"
#zipping the .dSYM to send to Testflight
echo Generating zip file
/usr/bin/zip -r "${CURRENT_DIR}/${BUILD_ARCHIVED_DIR}/${APP_NAME}.app.dSYM.zip" "${CURRENT_DIR}/${PROJECT_BUILDDIR}/${APP_NAME}.app.dSYM"
echo Sending to TestFlight
curl http://testflightapp.com/api/builds.json -F file="#${CURRENT_DIR}/${BUILD_ARCHIVED_DIR}/${APP_NAME}.ipa" -F dsym="#${CURRENT_DIR}/${BUILD_ARCHIVED_DIR}/${APP_NAME}.app.dSYM.zip" -F api_token="${TESTFLIGHT_API_TOKEN}" -F team_token="${TESTFLIGHT_TEAM_TOKEN}" -F notes="This build was uploaded via the upload API" -F notify=False -F distribution_lists="${TESTFLIGHT_DISTRIBUTION_LISTS}"
echo Submission ended
I imagine the Scheme your build is targeting is incorrect.
Additionally, TestFlight has a plugin for Jenkins so you can script your build process and execute the upload to TestFlight using the their Jenkins Plugin. I have provided a build script example that works for me via manual command line and under Jenkins CI.
If you would like to see the full setup, you can find a iOS/Git/TestFlight tutorial here: Jenkins iOS – Git, xcodebuild, TestFlight
xcodebuild -alltargets clean
rm -rf "./JenkinsBuild/*"
xcodebuild -target HelloJenkins PROVISIONING_PROFILE="00000000-0000-0000-0000-000000000000" CONFIGURATION_BUILD_DIR=JenkinsBuild
rm -rf "./JenkinsArchive/*"
xcodebuild -scheme HelloJenkins archive PROVISIONING_PROFILE="00000000-0000-0000-0000-000000000000" CODE_SIGN_IDENTITY="iPhone Developer: Jonny Appleseed (XXXXXXXXXX)" -archivePath ./JenkinsArchive/HelloJenkins.xcarchive
rm -rf "./JenkinsIPAExport/*"
xcodebuild -exportArchive -exportFormat IPA -exportProvisioningProfile iOS\ Team\ Provisioning\ Profile:\ com.yourAPP.HelloJenkins -archivePath ./JenkinsArchive/HelloJenkins.xcarchive -exportPath ./JenkinsIPAExport/HelloJenkins.ipa

Resources