Створення фреймворків iOS / OSX: чи потрібно кодувати їх перед розповсюдженням серед інших розробників?


90

Я вчусь створювати фреймворки для iOS та OSX. Візьмемо для прикладу iOS, поки що для мене працюють наступні кроки:

  1. фреймворк xcodebuild за допомогою iphoneimulator -sdk та дії Build
  2. фреймворк xcodebuild за допомогою -sdk iphoneos та дії Build
  3. Використовуйте інструмент lipo, щоб створити універсальний двійковий файл, щоб отримати lipo -infoочікувані:

Архітектури в жировому файлі: Foo.framework / Foo: i386 x86_64 armv7 arm64

Питання такі:

  1. Я прочитав, що мій фреймворк може бути перепідписаний розробником, який його використовує: "Підписати код при копіюванні", але я не розумію, що є передумовами для нього, тобто чи слід додати крок кодового знаку для кодового дизайну цього універсального двійкового файлу з моєю ідентифікацією підпису поширювати його серед інших розробників?

  2. якщо попереднє позитивне - чи варто використовувати мою ідентифікацію "Розподіл iPhone: ..." або "Розробник iPhone: ..." (щоб мій фреймворк, який є частиною якогось проекту iOS, пройшов усі види перевірок, особливо перевірку App Store ) ?.

Передумовою моєї відповіді є "Помилка CodeSign: підпис коду необхідний для типу продукту 'Framework' в SDK 'iOS 8.3'", який я бачив на ряді сторонніх фреймворків і Carthage # 235 або "об'єкт коду не підписаний взагалі "(один приклад: проблема, про яку я повідомляв у Realm # 1998 .

Тому я хочу бути впевненим, що користувачі моїх фреймворків не будуть стикатися з проблемами кодового проектування, коли вони їх використовують.

PS Це питання стає ще цікавішим, коли застосовується не до одного розробника, а до організації, яка є фреймворковим постачальником.


Цей коментар пропонує використовувати "CODE_SIGN_IDENTITY = iPhone Developer", але незрозуміло, чому замість "iPhone Distribution" використовується "Developer".
Станіслав Панкевич

Пов’язана тема: Експорт програми із вбудованою структурою, але без чіткої відповіді.
Станіслав Панкевич

Я також обманув це питання на форумах розробників Apple: forums.developer.apple.com/thread/6400 .
Станіслав Панкевич

у мене виникає питання, коли ви поширюєте свій фреймворк, ви поширюєте налагоджувальну збірку або звільнюєте збірку? і якщо ви поширюєте його у версії build, як це зробити?
niczm25

@ niczm25, це один із способів того, як я це роблю: stanislaw.github.io/2015/11/23/… .
Станіслав Панкевич

Відповіді:


137

Я відкрив нагороду: "Шукаю відповідь із надійних та / або офіційних джерел". але не отримували таких відтоді.

Незважаючи на те, що відповідь, надана @jackslash, є правильною, вона розповідає лише частину історії, тому я хочу написати свою власну, так, як би хотілося, щоб я бачив її в той момент, коли я задавав це питання.

Актуальність цієї відповіді: липень 2015 р. Найімовірніше, що все зміниться.

Перш за все, давайте стверджуватимемо, що дії, необхідні для правильного підписання коду фреймворку, повинні бути розділені на кроки, які повинен зробити розробник фреймворку, і кроки, які повинен зробити споживач фреймворку.

TLDR;

Для фреймворку OSX: розробник може вільно розповсюджувати фреймворк OSX без кодового дизайну, оскільки споживач все одно перепрограмує його.

Для фреймворку iOS: розробник може вільно розповсюджувати фреймворк iOS без кодового підпису, оскільки споживач все одно перепроектує його, але розробник змушений Xcode кодувати їх фреймворк, коли вони будують для пристрою iOS.

Через радара: "Фреймворки iOS, що містять фрагменти симулятора, не можуть бути надіслані в App Store". Споживач фреймворку iOS змушений запускати спеціальний сценарій, такий як "copy_frameworks" або "strip_frameworks", який використовує lipo -removeдля видалення фрагментів симулятора з фреймворку iOS і повторного використання -дизайнери позбавлені фреймворку, тому що в цей момент його ідентифікатор коду, яким би він не був (чи не був), видаляється як побічний ефект lipo -removeманіпуляції.

Далі йде довша відповідь.


Ця відповідь не є "черпанням з достовірних та / або офіційних джерел", а скоріше базується на ряді емпіричних спостережень.

Емпіричне спостереження №1: Споживачеві це байдуже, оскільки він перепрограмує структуру, отриману від розробника

Бінарні фреймворкові розподіли добре відомих проектів з відкритим кодом на Github не кодуються . Команда codesign -d -vvvvдає: "об'єкт коду взагалі не підписаний" на всіх двійкових фреймворках iOS та OSX, які я використовував для дослідження. Кілька прикладів: ReactiveCocoa and Mantle , Realm , PromiseKit .

З цього спостереження стає зрозумілим, що автори цих фреймворків мають намір підписувати їх споживачем, від їх імені, тобто споживач повинен використовувати або прапорець "Знак коду при копіюванні" у фазі побудови "Вбудовувати фреймворки", наданий Xcode, або використовувати якусь спеціальну оболонку скрипт, який робить те ж саме вручну: фреймворк кодових знаків від імені Споживача.

Я не знайшов жодного прикладу протилежного: фреймворк з відкритим кодом, який буде розповсюджений із ідентифікацією коду в ньому, тому в решті відповіді я вважаю цей широко прийнятий підхід правильним: немає необхідності в розробнику фреймворку поширювати їх фреймворк іншим розробникам із кодовою ідентифікацією, оскільки споживач у будь-якому випадку перепрограмує його .

Емпіричне спостереження №2, яке стосується лише iOS і яке цілком стосується розробника

У той час як Споживач не піклується структура отримувати їх від забудовника codesigned чи ні, розробник все ще потребує CodeSign своїх рамок IOS , як частина процесу складання , коли вони будують його для IOS пристроїв , оскільки в іншому випадку Xcode не будує: CodeSign error: code signing is required for product type 'Framework' in SDK 'iOS 8.1'. Цитую Джастін Spahr-Саммерс :

Фреймворки OS X не потрібно кодувати під час збірки ... На жаль, Xcode вимагає, щоб фреймворки iOS кодувались під час збірки.

Це досить хороші відповіді на моє запитання №2: «Ідентифікатора розробника iPhone» достатньо, щоб привабити Xcode, щоб він міг створити фреймворк iOS для пристрою. Цей коментар до Carthage # 339 говорить про те саме.

Емпіричне спостереження №3: інструмент lipo

Специфічну поведінку льего інструменту: при нанесенні на рамкову двійковий, вона завжди рекурсивно видаляє будь CodeSign тотожності з нього : lipo -create/-remove codesigned framework ... -> not codesigned framework.

Це може бути відповіддю на те, чому всі приклади у спостереженні №1 взагалі не підписані кодом: їх ідентифікатор кодового дизайну здувається після застосування lipo, але оскільки згідно з спостереженням №1 споживачеві все одно, це нормально.

Це спостереження особливо актуально для наступного спостереження № 4 щодо AppStore.

Емпіричне спостереження №4: фреймворки iOS, що містять фрагменти симулятора, не можуть бути надіслані в App Store

Це широко обговорюється в: Realm # тисяча сто шістьдесят три і Карфагена # 188 і відкритий радар: rdar: // 19209161 .

Це повністю турбує Споживача: для універсальної фреймворки iOS, яку Споживач включає в свій додаток, під час створення додатка вони повинні запускати спеціальний скрипт (спеціальна фаза запуску сценарію), який видаляє фрагмент симулятора з двійкового файлу цього фреймворку, щоб програма могла пройти перевірку AppStore.

Хороший приклад для двійкових фреймворків, який я знайшов у Realm: strip-frameworks.sh .

Він використовує lipoдля видалення всіх фрагментів архітектур, крім, ${VALID_ARCHS}а потім перекодує його з ідентифікацією споживача - саме тут починається спостереження №3: фреймворк повинен бути перекодований через маніпуляції з ним.

У Carthage є сценарій CopyFrameworks.swift, який робить те саме для всіх фреймворків, включених споживачем: він видаляє фрагменти симулятора та перекодує фреймворк від імені споживача.

Також є хороша стаття: Видалення небажаних архітектур із динамічних бібліотек у Xcode .


Тепер огляд кроків, необхідних для створення iOS та OSX як з точки зору розробника, так і з точки зору споживача. Спочатку простіший:

OSX

Розробник:

  1. Створює фреймворк OSX
  2. Віддає споживачеві

Від розробника не потрібні дії з кодування.

Споживач:

  1. Отримує фреймворк OSX від розробника
  2. Копіює фреймворк у Frameworks / каталог і автоматично підписує його від свого імені споживача в рамках процесу "Підпис коду під час копіювання"

iOS

Розробник:

  1. Створює фреймворк iOS для пристрою. Кодове проектування вимагає Xcode, достатньо ідентичності "iPhone Developer".
  2. Створює фреймворк iOS для симулятора.
  3. Використовує lipo, який створює універсальний фреймворк iOS із попередніх двох. На цьому етапі ідентифікація кодового дизайну в 1 крок втрачається: універсальний фреймворковий двійковий файл "взагалі не підписаний", але це нормально, оскільки "Споживачеві все одно".
  4. Віддає споживачеві

Споживач:

  1. Отримує фреймворк iOS від розробника
  2. Копіює фреймворк у Frameworks / каталог (цей крок може бути зайвим, залежно від сценарію на кроці 3).
  3. Використовує спеціальний скрипт як частину процесу збірки: цей скрипт позбавляє симулятор фрагментів від фреймворку iOS, а потім перекодує його від свого імені споживача.

9
Це цінний запис. Гарний
jackslash

@Stanislaw дякує за інформацію та цінні дані. Оскільки я пишу фреймворк, який я розробив для розробників, я хочу, щоб вони могли взяти фреймворк як є і використовувати його без необхідності створювати спеціальний сценарій для завантаження в магазин додатків. Я думаю, GoogleMobileAd працює так. але ви кажете, що вони повинні запускати певний сценарій? Ви уявляєте, як GoogleMobileAds цього не вимагають? подяка
Michael A

@MichaelA, справді це цікаво. Я подивлюсь.
Станіслав Панкевич

Не могли б ви дати мені посилання на GoogleMobileAds, якими ви користуєтесь?
Станіслав Панкевич

1
Дякуємо, що заощадили мій час, який працював на мене. Xcode 7.3, Mac OS X 10.11.4.
eugen

21

З прочитання пов'язаного потоку в репозиторії Карфагена це здається відносно простим. Якщо ви поширюєте двійковий фреймворк, вам потрібно підписати його кодом, а якщо ви поширюєте джерело через картридж або стручки какао, ви цього не робите, оскільки ці інструменти дбають про це різними методами.

Причиною того, що вам потрібно підписати його під час розповсюдження двійкового фреймворку, є те, що Xcode не створює двійковий код фреймворка без підписання коду. Якщо ви намагаєтеся не підписувати код двійкового фреймворку, ви отримуєте цю помилку:

CodeSign error: code signing is required for product type 'Framework' in SDK 'iOS 8.1'

Немає значення, яким ідентифікатором ви кодуєте фреймворк (iPhone Developer або iPhone Distribution), оскільки, як ви зазначаєте, фреймворк буде перекодований із налаштуванням "знак коду на копії". Це означає, що ваша фреймворк буде переконструйована відповідним сертифікатом із профілю розробника споживача фреймворку, коли ваша фреймворк буде скопійована в їх додаток. Це означає, що з App Store не буде проблем, оскільки він побачить лише остаточний підпис коду від споживача фреймворку.

Врешті-решт, ви можете також підписати свій двійковий файл .framework, оскільки ви не хочете підтримувати екзотичний процес збірки, і оскільки Xcode виводить лише підписані фреймворки, ви не повинні занадто віддалятися від за замовчуванням. Це насправді не має значення, оскільки кінцевий споживач перепідпише його.


у вашій відповіді, у другому абзаці цього, ви говорите, що немає необхідності в кодовому дизайні, тому що він буде перекодований споживачем, і я також тепер впевнений, що це правда на 95%, але я не розумію чому одночасно в першому абзаці ви говорите: "Якщо ви поширюєте двійковий фреймворк, вам потрібно підписати його кодом" - яка різниця - якщо я поширюю двійковий фреймворк (тобто не його джерело через картридж або кокоподи), чому Мені потрібно було б кодувати його?
Станіслав Панкевич

Я вважаю, що я не повинен кодексувати свій фреймворк будь-яким видом розповсюдження, який я використовую (файл .framework у архівах, карфаген чи cocoapods). Приклади: усі наведені нижче двійкові фреймворкові розподіли не кодовані: Realm , ReactiveCocoa , OCMockito .
Станіслав Панкевич

Тож я трохи плутаюся з вашим "Якщо ви поширюєте двійковий фреймворк, вам потрібно його підписати", що (imho) суперечить решті вашої відповіді. Будь ласка, поясніть. Також зверніть увагу, що я відкрив цю нагороду як "Шукаю відповідь із надійних та / або офіційних джерел".
Станіслав Панкевич

1
Так, я також розглядав Realm та OCMockito. Realm має ідентифікацію розробника iPhone, і так, OCMockito - це статична бібліотека. Думаю, я розумію проблему - саме lipo видаляє кодове підписання з iphoneos, коли воно поєднує кодований iphoneos та некодектований iphonesimulator.
Станіслав Панкевич

1
у мене виникає питання, коли ви поширюєте свій фреймворк, ви поширюєте налагоджувальну збірку або звільнюєте збірку? і якщо ви поширюєте його у версії build, як це зробити?
niczm25

1

Відповідь Станіслава Панкевича вище є цілком слушною та правильною. Але зауважте, що станом на Xcode 9.4 IDE попросить вас відключити підпис коду для iOS Cocoa Touch Frameworks. Apple зараз каже, що не рекомендується підписувати код .framework.

Сподіваюся, це допоможе.


1
Чи є у вас джерело для Apple, що рекомендує не підписувати рамки?
Рік,
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.