うちのいぬ Tech Blog

Tech Blog of Uchinoinu/My dog

How to handle Error "Untrusted Developer" at running app for debugging in iOS device

I'm writing about iOS/Flutter development tips.

The details are as follows

Topic

How to handle Error "Untrusted Developer" at running app for debugging in iOS device

Error detail

Untrusted Developer

Your device management settings do 
not allow using apps from developer
"Apple Development:
xxxxxxxxxxx(yyyyyyyyyyyy)" // <-- signing certificate
on this iPhone. You can allow using
these apps in Settings.

Error Meaning

You can configure your app about Team, Provisioning Profile, Signing Certificate from Signing & Capabilities tab in Xcode.

The error message tells you no permission was granted for launching the app of the setting in the device.

How to handle

In iOS14.6, Setting > General > Device Management, choose target developer app, and tap Trust button.

But this menu/page title and page structure may be different from each iOS version.

iOS端末でデバッグ時に、Untrusted Developerというエラー内容で、アプリを実機で立ち上げられなかった場合の対処法

アプリ開発の際に、iOS端末でデバッグをする際に以下のエラーになってアプリをインストールは出来ても立ち上げられないことがあります。

エラー内容

Untrusted Developer

Your device management settings do 
not allow using apps from developer
"Apple Development:
xxxxxxxxxxx(yyyyyyyyyyyy)" // <-- signing certificate
on this iPhone. You can allow using
these apps in Settings.

エラーの意味

xcodeSigning & Capabilities から、 Team Provisioning Profile Signing Certificate を設定できるかと思います。

その設定で実機でアプリを動かすための、実機側の許可が取れていない、というかと思います。

対応

iOS14.6では 設定の中の、一般、Device Management から該当のDeveloper Appを選択し、Trustというボタンをタップ` したら、修正できます。

ただ、iOSのバージョンによってこの設定画面がどういう名前のページあるかなどが変わってきます。

flutter runすると突然、Warning: CocoaPods not installed. Skipping pod install. というワーニングをはいた後に Error になり run が exit してしまう問題への対応

今回はflutter開発時のトラブルとその解決方法についてになります。

f:id:susanne:20210729114056j:plain

環境

  • Mac OS BigSur 11.4
  • VScode
  • flutter 2.2.0
  • fvm
  • 20200728現在

エラー内容

flutterで開発中 flutter run をすると、にこんなエラーが突然表示されることがありました。

Launching lib/main.dart on iPhone 12 in debug mode...
lib/main.dart:1
Warning: CocoaPods not installed. Skipping pod install.
  CocoaPods is used to retrieve the iOS and macOS platform side's plugin code that responds to your plugin usage on the Dart side.
  Without CocoaPods, plugins will not work on iOS or macOS.
  For more info, see https://flutter.dev/platform-plugins
To install see https://guides.cocoapods.org/using/getting-started.html#installation for instructions.

CocoaPods not installed or not in valid state.
Error launching application on iPhone 12.
Exited (sigterm)

調べてみると

ぐぐってみるとだいたいが、以下のような

  • cocoapodsを適切にインストールすること
    • sudo gem install cocoapods
  • cocoapodsをhomebrew経由でインストールすること
    • brew install cocoapods
    • brew reinstall cocoapods
    • brew unlink cocoapods && brew link cocoapods
  • flutter cleanをすること
  • PC再起動

といった解決策の記事が見つかりました。

しかし、今回はこのどれでも解決しませんでした。

開発時にエラーが起きたときにまずやること: 何をしたらエラーが発生するようになったか確認

検索しても答えが見つからなかったので、根本的に見直すことにしました。 つまり、実装中にエラーが発生するようになった場合にすること、 何をしたらそのエラーが発生するようになったのか、自分の行動を振り返ること 、です。 今回は、flutterもしくは開発環境のMacという閉じた環境の問題ということがわかっていたので、外的要因は無視して、自分の皇后を振り返ってみました。

そうすると、エラーが起きる前は色々ミーティングとかがあり合間合間での作業をしていましたが、Xcodeでcode signingの調整をしたことを思い出しました。

(↑このあたりを効率的に行うために私がやっている方法があるのですが、それはまたご紹介します)

なので、そのあたりを再度調整しました。

対応の手順

  • VScode
    • fvm flutter config をして 下部の Settings: 欄に ios-signing-cert がないことを確認
      • ある場合は、 fvm flutter config --clear-ios-signing-cert
  • Xcode
    • Signing & Capabilities の中を調整していきます

f:id:susanne:20210729105942p:plain

↑がうまく調整できたら、 flutter run が launch.json 経由で再度たたけるようになりました。

fvm自体をアップグレードする方法。fvmで管理しているflutterのバージョンが古いなと感じたら

flutterのバージョン管理にはfvmは便利なツールの一つでしょう。 fvmを使っていると時々fvmが管理しているflutterのバージョンが古いと感じるときがあります。 そういうときはfvm自体を pub global activate fvm でアップグレードするといいかもしれません。

内容

  • How to upgrade fvm
  • How to get latest flutter by fvm

どんなことが出来るようになるのか 

  • You can upgrade fvm at your command
  • You can use latest flutter using fvm

対象

  • MacOS user
  • Flutter app developer
  • fvm user

手順

まず現在のfvm releasesを確認します

$ fvm versions
...
Apr 15 212.2.0-10.1.pre
Apr 15 212.2.0-10.1.pre
Apr 16 212.0.5
Apr 27 212.3.0-0.1.pre
Apr 29 212.2.0-10.2.pre
Apr 30 212.0.6
May 10 212.2.0-10.3.pre
May 10 212.3.0-1.0.pre
May 18 212.2.0
May 18 212.3.0-12.1.pre
--------------------------------------
May 19 212.2.0             beta
--------------------------------------
--------------------------------------
May 27 212.2.1             stable
--------------------------------------
--------------------------------------
May 27 212.3.0-16.0.pre    dev
--------------------------------------

現在は Jul 16 21 なので、古い感じがします。 pub global activate fvm で fvmをアップグレードします。

fvmをアップグレード

$ pub global activate fvm

Package fvm is currently active at version 2.0.6.
Resolving dependencies... (1.7s)
+ args 2.1.1
+ charcode 1.3.1
+ cli_notify 0.0.3
+ cli_util 0.3.3
+ collection 1.15.0
+ console 4.1.0
+ date_format 2.0.2
+ fvm 2.2.2
+ io 1.0.3
+ meta 1.7.0
+ path 1.8.0
+ process_run 0.12.1+1
+ pub_semver 2.0.0
+ source_span 1.8.1
+ string_scanner 1.1.0
+ synchronized 3.0.0
+ term_glyph 1.2.0
+ tint 2.0.0
+ vector_math 2.1.0
+ yaml 3.1.0
Downloading fvm 2.2.2...
Downloading cli_notify 0.0.3...
Downloading process_run 0.12.1+1...
Downloading io 1.0.3...
Downloading cli_util 0.3.3...
Precompiling executables... (3.1s)
Precompiled fvm:main.
Installed executable fvm.
Activated fvm 2.2.2.

新しいfvmバージョンを確認します

$ fvm --version
2.2.2

再度 fvm releases を確認します

$ fvm releases
...
May 10 212.2.0-10.3.pre
May 10 212.3.0-1.0.pre
May 18 212.2.0
May 18 212.3.0-12.1.pre
May 19 212.2.0
May 27 212.2.1
May 27 212.3.0-16.0.pre
Jun 11 212.2.2
Jun 11 212.2.2
Jun 17 212.3.0-24.0.pre
--------------------------------------
Jun 25 212.3.0-24.1.pre    beta
--------------------------------------
--------------------------------------
Jul 1 212.2.3             stable
--------------------------------------
Jul 2 212.4.0-0.0.pre
--------------------------------------
Jul 13 212.4.0-4.0.pre     dev
--------------------------------------

よさそうですね。

新しいバージョンを使います

$ fvm use 2.2.3

Point

  • Remember pub global activate fvm

How to upgrade fvm itself. If you feel your fvm is old...

If you feel flutter version management tool fvm, you may sometimes verions listed at fvm versionsare old. If so, you can upgrade fvm itself by pub global activate fvm .

This article covers...

  • How to upgrade fvm
  • How to get latest flutter by fvm

By this article, you can ...

  • You can upgrade fvm at your command
  • You can use latest flutter using fvm

This article is for...

  • MacOS user
  • Flutter app developer
  • fvm user

Steps

check current fvm

$ fvm versions
...
Apr 15 212.2.0-10.1.pre
Apr 15 212.2.0-10.1.pre
Apr 16 212.0.5
Apr 27 212.3.0-0.1.pre
Apr 29 212.2.0-10.2.pre
Apr 30 212.0.6
May 10 212.2.0-10.3.pre
May 10 212.3.0-1.0.pre
May 18 212.2.0
May 18 212.3.0-12.1.pre
--------------------------------------
May 19 212.2.0             beta
--------------------------------------
--------------------------------------
May 27 212.2.1             stable
--------------------------------------
--------------------------------------
May 27 212.3.0-16.0.pre    dev
--------------------------------------

Something wrong. Too old. Then try fvm upgrade by pub global activate fvm

Upgrade fvm

$ pub global activate fvm

Package fvm is currently active at version 2.0.6.
Resolving dependencies... (1.7s)
+ args 2.1.1
+ charcode 1.3.1
+ cli_notify 0.0.3
+ cli_util 0.3.3
+ collection 1.15.0
+ console 4.1.0
+ date_format 2.0.2
+ fvm 2.2.2
+ io 1.0.3
+ meta 1.7.0
+ path 1.8.0
+ process_run 0.12.1+1
+ pub_semver 2.0.0
+ source_span 1.8.1
+ string_scanner 1.1.0
+ synchronized 3.0.0
+ term_glyph 1.2.0
+ tint 2.0.0
+ vector_math 2.1.0
+ yaml 3.1.0
Downloading fvm 2.2.2...
Downloading cli_notify 0.0.3...
Downloading process_run 0.12.1+1...
Downloading io 1.0.3...
Downloading cli_util 0.3.3...
Precompiling executables... (3.1s)
Precompiled fvm:main.
Installed executable fvm.
Activated fvm 2.2.2.

confirm new version

$ fvm --version
2.2.2

Retry to check fvm releases

$ fvm releases
...
May 10 212.2.0-10.3.pre
May 10 212.3.0-1.0.pre
May 18 212.2.0
May 18 212.3.0-12.1.pre
May 19 212.2.0
May 27 212.2.1
May 27 212.3.0-16.0.pre
Jun 11 212.2.2
Jun 11 212.2.2
Jun 17 212.3.0-24.0.pre
--------------------------------------
Jun 25 212.3.0-24.1.pre    beta
--------------------------------------
--------------------------------------
Jul 1 212.2.3             stable
--------------------------------------
Jul 2 212.4.0-0.0.pre
--------------------------------------
Jul 13 212.4.0-4.0.pre     dev
--------------------------------------

Got you versions!

use a new one!

$ fvm use 2.2.3

Point

  • Remember pub global activate fvm

How to use Exceptions

Error handling is a common and hard concern for developers.

There're some approaches to do it and Exception by try catch is one of them.

In this article, I'll introduce how to use Exceptions in terms of Effective Dart.

dart.dev

Exceptions

Exception object is included in dart:core library.

api.dart.dev

Dart has Error and Exception. The rough differences are below.

  • Error: Problem of program. You can fix it by modifying the program.
  • Exception: Not program problem. Changing the program does not always fix runtime errors.

throw Exception

Throw Exception object using throw .

throw Exception('Exception');

Catch exceotion

Catch Exception object by try...catch statement.

  try {
    throw Exception('occur exception');
  } on Exception catch (err, stacktrace) {
    print(err);
    print(stacktrace);
    rethrow;
  } finally {
    print('finish exception handlling');
  }

出力

exception: Exception: occur exception,
#0      hoge (hoge.dart:12:5)
#1      main (hoge.dart:7:3)
#2      new Future.<anonymous closure> (dart:async/future.dart:174:37)
#3      _rootRun (dart:async/zone.dart:1346:47)
#4      _CustomZone.run (dart:async/zone.dart:1258:19)
#5      _CustomZone.runGuarded (dart:async/zone.dart:1162:7)
#6      _CustomZone.bindCallbackGuarded.<anonymous closure> (dart:async/zone.dart:1202:23)
#7      _rootRun (dart:async/zone.dart:1354:13)
#8      _CustomZone.run (dart:async/zone.dart:1258:19)
#9      _CustomZone.bindCallback.<anonymous closure> (dart:async/zone.dart:1186:23)
#10     Timer._createTimer.<anonymous closure> (dart:async-patch/timer_patch.dart:18:15)
#11     _Timer._runTimers (dart:isolate-patch/timer_impl.dart:395:19)
#12     _Timer._handleMessage (dart:isolate-patch/timer_impl.dart:426:5)
#13     _RawReceivePortImpl._handleMessage (dart:isolate-patch/isolate_patch.dart:184:12)

finish exception handlling

Let's try

  • try these behaviors using dartpad

dartpad.dartlang.org

Attentions

Use on clause for catch

  • By being explicit and specific about what you are trying to catch, you can prevent unexpected behavior and errors.
try {
  doSomethingBad()
}
on Exception catch(e) {
  handleException(e);
}

Error can be analyzed and handled before execution, so it is not supplemented in the code.

  • As the headline suggests, Error can be supplemented and addressed before execution.
  • This means that there is almost no need to write code to explicitly supplement Error at runtime.

dart-lang.github.io

  • However, if there is a problem with the program that needs to be fixed, throwing an Error object is recommended by effective-dart

rethrow

dart-lang.github.io

Customise Exception class

  • When developing with the Flutter library, you may see exception classes called HogeHogeException, which may be an extension of the Exception class.
  • It may be a good idea to create such classes as needed in development.
class HogeHogeException implements Exception {
  const HogeHogeException(this.message);

  final String message;

  // By overriding toString(), when you use this class and `print(e)`, you can output the content characters instead of `Instance of 'HogeHogeException'`.
  @override
  String toString() => message;

  void sendDataToLogStorage(){
    // logic
  }
}

void main() {
  try {
    throw HogeHogeException('HogeHogeExceptionです');
  } on HogeHogeException catch (exception, stacktrace) {
    print(exception);
    print(stacktrace);
    exception.sendDataToLogStorage();
  } finally {
    print('Finally');
  }
}

例外処理(Exceptions)の使い方

プログラムを書く上でよくある話ですが、 エラーハンドリングをちゃんとしましょう という話になります。

エラーハンドリングというのはいろいろなやり方があると思いますが、そのうちの一つが try catch による例外処理になるかと思います。

ここれでは effective-dart を参考に、dartでの例外処理の使い方をご紹介します。

dart.dev

例外(Exceptions)

例外オブジェクト(Exception)は dart:core ライブラリに含まれています。

api.dart.dev

dartにはErrorとExceptionがあります。それぞれのだいたいの違いは以下の様になります。

  • Error: プログラムの問題。コード修正で対応できる。
  • Exception: プログラムの問題ではない。実行中に異常が起こった場合のため、コード修正で必ず対応可能とは限らない。

例外を投げます

throw 使用して例外オブジェクトを投げます。

throw Exception('例外です');

例外を補足する

try...catch ステートメントで例外オブジェクトをキャッチします。

  try {
    throw Exception('例外を起こしてみました');
  } on Exception catch (err, stacktrace) {
    print(err);
    print(stacktrace);
    rethrow;
  } finally {
    print('例外処理を終了します');
  }

出力

exception: Exception: 例外を起こしてみました,
#0      hoge (hoge.dart:12:5)
#1      main (hoge.dart:7:3)
#2      new Future.<anonymous closure> (dart:async/future.dart:174:37)
#3      _rootRun (dart:async/zone.dart:1346:47)
#4      _CustomZone.run (dart:async/zone.dart:1258:19)
#5      _CustomZone.runGuarded (dart:async/zone.dart:1162:7)
#6      _CustomZone.bindCallbackGuarded.<anonymous closure> (dart:async/zone.dart:1202:23)
#7      _rootRun (dart:async/zone.dart:1354:13)
#8      _CustomZone.run (dart:async/zone.dart:1258:19)
#9      _CustomZone.bindCallback.<anonymous closure> (dart:async/zone.dart:1186:23)
#10     Timer._createTimer.<anonymous closure> (dart:async-patch/timer_patch.dart:18:15)
#11     _Timer._runTimers (dart:isolate-patch/timer_impl.dart:395:19)
#12     _Timer._handleMessage (dart:isolate-patch/timer_impl.dart:426:5)
#13     _RawReceivePortImpl._handleMessage (dart:isolate-patch/isolate_patch.dart:184:12)

例外処理を終了します

試してみましょう

  • これらの挙動を試すには dartpadを使うのがとても便利です。

dartpad.dartlang.org

注意点

catchには on節を利用しましょう

  • 何をcatchしようとしているのか明示的・限定的にすることで、予期しない挙動・エラーを防ぐことができます
try {
  doSomethingBad()
}
on Exception catch(e) {
  handleException(e);
}

Errorは実行前に分析対応できるため、コードでは補足しない

  • 見出しの通りですが、Errorについては、実行前に補足・対応が可能です。
  • このため実行時にErrorを明示的に補足するコードを書く必要性はほぼないということです。

dart-lang.github.io

  • ただし、プログラムの問題で修正が必要な場合には、Errorオブジェクトをthrowすることが effective-dartでは推奨されています
    • throw Error('エラーなのでプログラムを修正してください'); しなさいということですね。

rethrow

dart-lang.github.io

Exceptionクラスをカスタマイズする

  • Flutterでライブラリを利用した開発をしていると、HogeHogeExceptionという例外クラスを目にすることがありますが、これらはExceptionクラスを拡張して実装しているクラスの場合もあると思います
  • 開発での必要に応じてこういったクラスはよきように作っていくと良いかもしれません。
class HogeHogeException implements Exception {
  const HogeHogeException(this.message);

  final String message;

  // toString()をoverrideすることで、このクラス利用時に `print(e)` した際に `Instance of 'HogeHogeException'` ではなく中身の文字を出力することができます。
  @override
  String toString() => message;

  void sendDataToLogStorage(){
    // logic
  }
}

void main() {
  try {
    throw HogeHogeException('HogeHogeExceptionです');
  } on HogeHogeException catch (exception, stacktrace) {
    print(exception);
    print(stacktrace);
    exception.sendDataToLogStorage();
  } finally {
    print('Finally');
  }
}