Імпорт CommonCrypto в рамках Swift


184

Як ви імпортуєте CommonCryptoв рамку Swift для iOS?

Я розумію, як користуватися CommonCryptoпрограмою Swift: Ви додаєте #import <CommonCrypto/CommonCrypto.h>до мостового заголовка. Однак рамки Swift не підтримують з'єднання заголовків. Документація каже:

Ви можете імпортувати зовнішні фреймворки, які мають чисту базу даних коду Objective-C, чисту базу даних Swift або змішану мову. Процес імпорту зовнішнього фреймворку є однаковим, незалежно від того, чи є рамка написана однією мовою або містить файли з обох мов. Коли ви імпортуєте зовнішній фреймворк, переконайтесь, що для параметра "Зробити модуль" для структури, яку ви імпортуєте, встановлено Так.

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

import FrameworkName

На жаль, імпорт CommonCryptoне працює. Ні додавання #import <CommonCrypto/CommonCrypto.h>до заголовка парасольки.


CommonCrypto - це основа на C, а не рамка Objective-C.
rmaddy

1
@rmaddy Objective-C - це суперкомплект C. Ви хочете сказати, що ми не можемо використовувати CommonCrypto від Swift?
hpique

4
@rmaddy Мені просто вдалося змусити CommonCrypto працювати за допомогою модульних карт. Я відшліфую рішення та опублікую його пізніше сьогодні.
hpique

якщо вам здається зручним, а те, що ви шукаєте, вже реалізовано, ви можете спробувати CryptoSwift
Marcin

1
Apple просто відкриває джерело CommonCrypto. Можливо, ми можемо запустити це, якщо у нас є джерела.
очне яблуко

Відповіді:


137

Дещо трохи простішим і надійнішим є створення об'єднаної цілі під назвою "CommonCryptoModuleMap" з фазою Run Script для автоматичного генерування карти модуля з правильним трактом Xcode / SDK:

введіть тут опис зображення введіть тут опис зображення

Етап Run Script повинен містити цей баш:

# This if-statement means we'll only run the main script if the CommonCryptoModuleMap directory doesn't exist
# Because otherwise the rest of the script causes a full recompile for anything where CommonCrypto is a dependency
# Do a "Clean Build Folder" to remove this directory and trigger the rest of the script to run
if [ -d "${BUILT_PRODUCTS_DIR}/CommonCryptoModuleMap" ]; then
    echo "${BUILT_PRODUCTS_DIR}/CommonCryptoModuleMap directory already exists, so skipping the rest of the script."
    exit 0
fi

mkdir -p "${BUILT_PRODUCTS_DIR}/CommonCryptoModuleMap"
cat <<EOF > "${BUILT_PRODUCTS_DIR}/CommonCryptoModuleMap/module.modulemap"
module CommonCrypto [system] {
    header "${SDKROOT}/usr/include/CommonCrypto/CommonCrypto.h"
    export *
}
EOF

Використовуючи код оболонки і ${SDKROOT}означає, що вам не доведеться жорстко кодувати шлях Xcode.app, який може змінюватись від системи до системи, особливо якщо ви xcode-selectпереходите на бета-версію або будуєте на сервері CI, де встановлено кілька версій у нестандартних місцях. Вам також не потрібно сильно кодувати SDK, щоб це працювало для iOS, macOS тощо. Також вам не потрібно нічого сидіти у вихідному каталозі вашого проекту.

Створивши цю ціль, переконайтеся, що бібліотека / фреймворк залежать від неї за допомогою пункту Цільові залежності:

введіть тут опис зображення

Це забезпечить генерування карти модулів до того, як буде побудована ваша рамка.

Примітка macOS : Якщо ви також підтримуєте macOS, вам потрібно буде додати macosxдо Supported Platformsналаштування збірки нову створену вами сукупну ціль, інакше вона не помістить карту модуля у правильну Debugпохідну папку даних із рештою рамкові вироби.

введіть тут опис зображення

Далі додайте батьківський каталог карти модуля до ${BUILT_PRODUCTS_DIR}/CommonCryptoModuleMapпараметра збірки "Імпортувати шляхи" у розділі Swift ( SWIFT_INCLUDE_PATHS):

введіть тут опис зображення

Не забудьте додати $(inherited)рядок, якщо у вас визначені шляхи пошуку на рівні проекту чи xcconfig.

Це все, ви повинні тепер мати можливість import CommonCrypto

Оновлення для Xcode 10

Xcode 10 тепер поставляється з карткою модуля CommonCrypto, що робить це рішення непотрібним. Якщо ви хочете підтримати і Xcode 9, і 10, ви можете зробити перевірку на етапі Запуск сценарію, щоб побачити, чи існує карта модуля чи ні, наприклад

COMMON_CRYPTO_DIR="${SDKROOT}/usr/include/CommonCrypto"
if [ -f "${COMMON_CRYPTO_DIR}/module.modulemap" ]
then
   echo "CommonCrypto already exists, skipping"
else
    # generate the module map, using the original code above
fi

8
Ця відповідь має бути зверху. Простий і елегантний
Абдулла Саїд

1
Пізно до гри на цьому - але це має бути обрана відповідь. Іншим розробникам, які працюють над тим самим проектом, просто і простіше, щоб побачити вимогу.
fatuous.logic

1
Чудова відповідь. Дякую!
Klaus Busse

1
Якщо я це роблю у своїй .framework, чи повинен я робити те саме в проектах, де я включаю цю рамку?
Раві Кіран

2
@IanDundas Я оновив код вище з виправленням проблеми перекомпіляції, а також виправленням для використання цього на macOS
iwasrobbed

91

Ви дійсно можете побудувати рішення , яке «просто працює» (немає необхідності копіювати module.modulemap і SWIFT_INCLUDE_PATHSнастройку до вашого проекту, відповідно з вимогами інших рішеннями тут), але це зажадає від вас створити рамковий фіктивну / модуль , який » Буду імпортувати у вашу рамку належним чином. Ми також можемо забезпечити це працює незалежно від платформи ( iphoneos, iphonesimulatorабо macosx).

  1. Додайте нову рамкову ціль до свого проекту та назвіть його після системної бібліотеки, наприклад , "CommonCrypto". (Ви можете видалити заголовок парасольки, CommonCrypto.h .)

  2. Додайте новий файл параметрів конфігурації та назвіть його, наприклад , "CommonCrypto.xcconfig". (Не перевіряйте будь-яку з цілей на включення.) Населяйте її таким чином:

    MODULEMAP_FILE[sdk=iphoneos*]        = \
        $(SRCROOT)/CommonCrypto/iphoneos.modulemap
    MODULEMAP_FILE[sdk=iphonesimulator*] = \
        $(SRCROOT)/CommonCrypto/iphonesimulator.modulemap
    MODULEMAP_FILE[sdk=macosx*]          = \
        $(SRCROOT)/CommonCrypto/macosx.modulemap
  3. Створіть вищевказані три файли з картою модулів, на які посилається, та заповніть їх наступним чином:

    • iphoneos.modulemap

      module CommonCrypto [system] {
          header "/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk/usr/include/CommonCrypto/CommonCrypto.h"
          export *
      }
    • iphoneimulator.modulemap

      module CommonCrypto [system] {
          header "/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/usr/include/CommonCrypto/CommonCrypto.h"
          export *
      }
    • macosx.modulemap

      module CommonCrypto [system] {
          header "/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.11.sdk/usr/include/CommonCrypto/CommonCrypto.h"
          export *
      }

    (Замініть "Xcode.app" на "Xcode-beta.app", якщо ви використовуєте бета-версію. Замініть 10.11поточну версію SDK для ОС, якщо не використовується El Capitan.)

  4. На Info вкладці налаштувань проекту, в відповідно з конфігураціями , набір налагодження і реліз конфігурації CommonCrypto до CommonCrypto (посилається CommonCrypto.xcconfig ).

  5. На вкладці " Фази збірки" вашої рамкової цілі додайте рамку CommonCrypto до цільових залежностей . Крім того, додайте libcommonCrypto.dylib до фази збірки бінарних із бібліотеками .

  6. Виберіть CommonCrypto.framework у продуктах і переконайтесь, що його цільове членство для обгортки встановлено як необов’язкове .

Тепер ви маєте змогу будувати, працювати та працювати import CommonCrypto знаходитись у вашій обробці.

Для прикладу дивіться, як SQLite.swift використовує фіктивну sqlite3.framework .


4
Для мене працює без кроку (5). З його допомогою я отримую помилку побудови:ld: cannot link directly with /Applications/Xcode.app/Contents/Developer/Platforms/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator8.2.sdk/usr/lib/system/libcommonCrypto.dylib. Link against the umbrella framework 'System.framework' instead. for architecture x86_64
stannie

4
Відмінно! Використовували це для виготовлення github.com/soffes/Crypto, хоча я не повинен був посилатися System.framework. Варто зазначити, що вам потрібно створити окрему рамку для обгортки для Mac та iOS, якщо ваша рамка є кросплатформою.
Сем Соффс

32
Як чи де люди знаходять подібні речі?
hola

5
Лише в примітці чітко видно, що вам потрібно вибрати крок Objective-C як мову на кроці 1. Це легко не помітити. Також, можливо, тому, що у мене не було .dylib, мені потрібно було додати .framework на кроці 5.
Teo Sartori

7
це жахливо. У мене є зоопарк з Xcodes, кожен з яких по-різному розбитий, і абсолютні шляхи до заголовків у всьому місці викликають мотиви. У купертіно щось відбувається не так, або, принаймні, з тим, хто відповідає за цей безладний мап
Антон Тропашко

82

Я знайшов проект GitHub, який успішно використовує CommonCrypto в рамках Swift: SHA256-Swift . Також ця стаття про ту ж проблему з sqlite3 була корисною.

Виходячи з вищезазначеного, кроки:

1) Створіть CommonCryptoкаталог всередині каталогу проектів. Всередині створіть module.mapфайл. Карта модуля дозволить нам використовувати бібліотеку CommonCrypto як модуль у Swift. Його вміст:

module CommonCrypto [system] {
    header "/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator8.0.sdk/usr/include/CommonCrypto/CommonCrypto.h"
    link "CommonCrypto"
    export *
}

2) У Налаштуваннях збірки в межах Swift Compiler - Шляхи пошуку додайте CommonCryptoкаталог до Імпортувати шляхи ( SWIFT_INCLUDE_PATHS).

Налаштування побудови

3) Нарешті, імпортуйте CommonCrypto у файли Swift, як і будь-які інші модулі. Наприклад:

import CommonCrypto

extension String {

    func hnk_MD5String() -> String {
        if let data = self.dataUsingEncoding(NSUTF8StringEncoding)
        {
            let result = NSMutableData(length: Int(CC_MD5_DIGEST_LENGTH))
            let resultBytes = UnsafeMutablePointer<CUnsignedChar>(result.mutableBytes)
            CC_MD5(data.bytes, CC_LONG(data.length), resultBytes)
            let resultEnumerator = UnsafeBufferPointer<CUnsignedChar>(start: resultBytes, length: result.length)
            let MD5 = NSMutableString()
            for c in resultEnumerator {
                MD5.appendFormat("%02x", c)
            }
            return MD5
        }
        return ""
    }
}

Обмеження

Використання спеціальної рамки в іншому проекті не вдається під час компіляції з помилкою missing required module 'CommonCrypto'. Це пов’язано з тим, що модуль CommonCrypto, здається, не включений у спеціальний фреймворк. Вирішення завдання полягає в тому, щоб повторити етап 2 (налаштування Import Paths) в проекті, який використовує рамки.

Карта модуля не залежить від платформи (в даний час вказує на конкретну платформу, iOS 8 Simulator). Я не знаю, як зробити шлях заголовка щодо поточної платформи.

Оновлення для iOS 8 <= Ми повинні видалити рядок посилання "CommonCrypto" , щоб отримати успішну компіляцію.

ОНОВЛЕННЯ / редагування

Я постійно отримував таку помилку збірки:

ld: бібліотека не знайдена для -lCommonCrypto для архітектури x86_64 clang: error: команда linker не вдалася з кодом виходу 1 (використання -v для перегляду виклику)

Якщо я не видалив рядок link "CommonCrypto"із створеного module.mapфайлу. Після того, як я видалив цю лінію, вона склалася нормально.


30
Боже, Apple впевнена, що хоче ускладнити справи. Хіба це не вб'є Swifties, щоб ми просто імпортували файли / рамки без необхідності проходити все це BS?
zaph

4
Це викликає жахливість, оскільки $SDKROOTзмінна повинна дозволити вам платформу агностичних шляхів, але я не маю уявлення, як дістатися до цього в Swift.
danimal

2
Для мене це не спрацювало, поки я не видалив link "CommonCrypto"файл з module.map.
Тео Сарторі

1
Чи може хтось підтвердити це, працюючи на Xcode 7.3? Це рішення перестало працювати для мене після оновлення.
Микита Кукушкін

1
Виправлення: працює нормально, коли я створюю тренажер, але не вдається @ зв’язувати, коли я будую для пристрою iOS 9.3 "ld: бібліотеку не знайдено для -lCommonCrypto для архітектури arm64"
Микита Кукушкін

50

У цій відповіді йдеться про те, як змусити його працювати всередині рамки та з Cocoapods та Carthage

🐟 підхід до модульної карти

Я використовую modulemapв обгортці навколо CommonCrypto https://github.com/onmyway133/arcane , https://github.com/onmyway133/Reindeer

Для тих, хто отримує header not found, перегляньте https://github.com/onmyway133/Arcane/isissue/4 або запустітьxcode-select --install

  • Створіть папку, CCommonCryptoщо міститьmodule.modulemap

      module CCommonCrypto {
        header "/usr/include/CommonCrypto/CommonCrypto.h"
        export *
      }
  • Перейдіть до вбудованих налаштувань -> імпортувати шляхи

      ${SRCROOT}/Sources/CCommonCrypto

🌳 Какаоди з підходом до модульної карти

🐘 підхід публічного заголовка

  • Ji - це обгортка навколо libxml2, і він використовує публічний підхід до заголовка

  • Він має файл заголовка https://github.com/honghaoz/Ji/blob/master/Source/Ji.h із Target Membershipвстановленим наPublic

  • У ньому є список файлів заголовків для libxml2 https://github.com/honghaoz/Ji/tree/master/Source/Ji-libxml

  • У ньому є Налаштування збірки -> Шляхи пошуку заголовків

      $(SDKROOT)/usr/include/libxml2
  • У ньому є "Налаштування збірки" -> "Інші прапорці"

      -lxml2

🐏 Какаоди з публічним підходом до заголовка

🐝 Цікаві пов’язані повідомлення


1
Оце Так! На мій подив, шлях до заголовка від верхнього підходу (створення файлу module.modulemap) чудово працював, коли раніше файли modulemap викликали багато проблем. Я боровся з цим на деякий час , використовуючи файл module.modulemap абсолютний шлях до в /CommonCrypto/CommonCrypto.hмежах Applications/XCode.app/Contents/Developer/Platforms/iPhoneOS...., які вимагають ручної модифікації для людей , які перейменували XCode. Переключення цієї лінії на погляд, "/usr/include/CommonCrypto/CommonCrypto.h"здається, працює добре для команди з кількома версіями XCode. Дуже дякую!
Наталія

3
Створюючи стручок, я встановлюю SWIFT_INCLUDE_PATHS і зберігаю_пути. Коли я запускаю pod lib lint, але збірка не вдалася з помилкою: немає такого модуля 'CommonCrypto'. Як я можу з цим боротися.
Klein Mioke

1
Не пов'язано з проблемою, але я люблю використовувати смайли як кулі! 😊
Фоментія

2
@ onmyway133 Використання локальної стружки для розробки працює, якщо ви замінили $(PODS_ROOT)/CommonCryptoSwift/Sources/CCommonCryptoна $(PODS_TARGET_SRCROOT)/Sources/CCommonCrypto. PODS_TARGET_SRCROOTвстановлено правильно для місцевих стручків.
Орхан Аліханов

Чудова відповідь, врятував мені життя! Дякуємо мільйону
Хасан Шахбазі

45

Гарні новини! Swift 4.2 (Xcode 10) нарешті надає CommonCrypto!

Просто додайте import CommonCryptoу свій швидкий файл.


Відмінна новина! Чи можете ви додати посилання на документацію?
Kryštof Matěj

Я не маю посилання на документацію, я виявив це під час спроби скласти проект, де у мене було одне з обхідних шляхів тут з Xcode 10. Він скаржився, що може знайти два CommonCryptoмодулі, тим самим підозрюючи, що Apple зараз за умови, що я видалив своє вирішення та 'ось! Це було правдою. Я написав твіт про це, і інженер Apple відповів, що підтвердив, що це було призначено.
mxcl

1
App Store показує мені лише 9.4.7 як доступне оновлення, як ви отримали Xcode 10?
Хаммад Тарік

1
Це в бета-версії, як вам би сказав тривіальний пошук Google.
mxcl

1
@SomoyDasGupta так. Просто видаліть попередній імпорт та скомпілюйте його ще раз. Іншими словами, вам не потрібно робити кроки з відповіді MikeWeller
COLD ICE

7

ПОПЕРЕДЖЕННЯ: iTunesConnect може відхилити програми, які використовують цей метод.


Новий член в моїй команді випадково зламав рішення, отримане однією з найкращих відповідей, тому я вирішив об'єднати його в невеликому обгортковому проекті під назвою CommonCryptoModule . Ви можете встановити його вручну або через Cocoapods:

pod 'CommonCryptoModule', '~> 1.0.2'

Тоді все, що вам потрібно зробити, це імпортувати модуль, куди вам потрібно CommonCrypto, наприклад:

import CommonCryptoModule

Сподіваюся, що хтось інший вважає це корисним.


Попередження: Ваша заявка буде відхилена, якщо ви використовуєте цей метод!
Сегабонд

Так, нас також відхилили, дуже дивно, тому що ми завантажували без проблем кілька місяців за допомогою цього методу.
Микита Кукушкін

5

Я думаю, що я покращив чудову роботу Майка Веллера.

Додайте фазу Run Script перед Compile Sourcesфазою, що містить цей bash:

# This if-statement means we'll only run the main script if the
# CommonCrypto.framework directory doesn't exist because otherwise
# the rest of the script causes a full recompile for anything
# where CommonCrypto is a dependency
# Do a "Clean Build Folder" to remove this directory and trigger
# the rest of the script to run

FRAMEWORK_DIR="${BUILT_PRODUCTS_DIR}/CommonCrypto.framework"

if [ -d "${FRAMEWORK_DIR}" ]; then
echo "${FRAMEWORK_DIR} already exists, so skipping the rest of the script."
exit 0
fi

mkdir -p "${FRAMEWORK_DIR}/Modules"
cat <<EOF > "${FRAMEWORK_DIR}/Modules/module.modulemap"
module CommonCrypto [system] {
    header "${SDKROOT}/usr/include/CommonCrypto/CommonCrypto.h"
    export *
}
EOF

ln -sf "${SDKROOT}/usr/include/CommonCrypto" "${FRAMEWORK_DIR}/Headers"

Цей скрипт будує рамку з голими кістками за допомогою модуля.map у потрібному місці, а потім спирається на автоматичний пошук Xcode BUILT_PRODUCTS_DIR .

Я пов’язав оригінальну папку CommonCrypto include як папку заголовки рамки, тому результат повинен також функціонувати для проектів Objective C.


Дивіться відповідь dvdblk щодо покращення, яке стосується використання в CocoaPods.
jjrscott

5

Для всіх, хто використовує швидкий 4.2 з Xcode 10 :

Тепер модуль CommonCrypto надається системою, тому ви можете безпосередньо імпортувати його, як і будь-який інший системний каркас.

import CommonCrypto

Дублікат @ mxcl відповідають: stackoverflow.com/a/50690346/9988514
Райнер Шварц

4

@mogstad був досить люб'язний, щоб загорнути @stephencelis розчин у Cocoapod:

pod 'libCommonCrypto'

Інші наявні стручки для мене не працювали.


4

Рішення модульних карт можуть бути хорошими та надійними щодо змін SDK, але я вважаю їх незручними для використання на практиці та не настільки надійними, як хотілося б, коли передавали речі іншим. Щоб спробувати зробити це все дурнішим, я пішов іншим шляхом:

Просто скопіюйте заголовки.

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

Під "копіюванням заголовків" я маю на увазі "вирізати та вставити всі потрібні заголовки в один масивний заголовок у вашому проекті так, як це робив би препроцесор". Як приклад цього, який ви можете скопіювати або адаптувати, див. RNCryptor.h .

Зауважте, що всі ці файли ліцензовані на основі APSL 2.0, і цей підхід навмисно підтримує повідомлення про авторські права та ліцензії. Мій крок об'єднання ліцензується відповідно до MIT, і це стосується лише наступного повідомлення про ліцензію).

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


Я знайшов це, щоб компілювати надійно, і це просто. Чи потрібно додатку, що використовує рамки, посилатися на щось особливе, або CommonCrypto завжди доступний?
codingFriend1

1
Я думаю, що Security.frameworkце автоматично пов'язано (минуло небагато часу з початку нового проекту). Якщо ви отримуєте помилки, це рамки для зв'язку.
Роб Нап'єр

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

2

Я знаю, це старе питання. Але я знаходжу альтернативний спосіб використання бібліотеки в проекті Swift, який може бути корисним для тих, хто не хоче імпортувати рамки, введені в цих відповідях.

У проекті Swift створіть мостиковий заголовок Objective-C, створіть категорію NSData (або спеціальний клас, який буде використовувати бібліотеку) в Objective-C. Єдиним недоліком було б те, що вам потрібно записати весь код реалізації в Objective-C. Наприклад:

#import "NSData+NSDataEncryptionExtension.h"
#import <CommonCrypto/CommonCryptor.h>

@implementation NSData (NSDataEncryptionExtension)
- (NSData *)AES256EncryptWithKey:(NSString *)key {
    //do something
}

- (NSData *)AES256DecryptWithKey:(NSString *)key {
//do something
}

А потім додайте це у свій об'єктивний заголовок об'єктивного c

#import "NSData+NSDataEncryptionExtension.h"

А потім у класі Swift роблять подібне:

public extension String {
func encryp(withKey key:String) -> String? {
    if let data = self.data(using: .utf8), let encrypedData = NSData(data: data).aes256Encrypt(withKey: key) {
        return encrypedData.base64EncodedString()
    }
    return nil
}
func decryp(withKey key:String) -> String? {
    if let data = NSData(base64Encoded: self, options: []), let decrypedData = data.aes256Decrypt(withKey: key) {
        return decrypedData.UTF8String
    }
    return nil
}
}

Це працює як очікувалося.


Це працює дуже гладко і навіть дозволяє зберігати внутрішні внутрішні характеристики ( NSData+NSDataEncryptionExtension.hне обов'язково бути загальнодоступними).
Рафаель

Але з якою основою ОС я повинен пов'язувати цей предмет? На відміну від інших - мені доводиться працювати з CommonCrypto в проекті Obj-C, і це одне перерви на Xcode 9 з MacOS-10.13 SDK
Motti Shneor

@MottiShneor Посилання будь-якої ОС від 10.9 або вище. Я працюю над тим самим середовищем, і це прекрасно працює.
Теренс

2

До відповіді jjrscott я додав трохи магії cocoapods у випадку, якщо вам потрібно використовувати CommonCrypto у вашій бібліотеці cocoapods.


1) Додайте цей рядок до свого підспеку:

s.script_phase = { :name => 'CommonCrypto', :script => 'sh $PROJECT_DIR/../../install_common_crypto.sh', :execution_position => :before_compile }

2) Збережіть це в папці вашої бібліотеки або де завгодно (проте не забудьте відповідно змінити script_phase ...)

# This if-statement means we'll only run the main script if the
# CommonCrypto.framework directory doesn't exist because otherwise
# the rest of the script causes a full recompile for anything
# where CommonCrypto is a dependency
# Do a "Clean Build Folder" to remove this directory and trigger
# the rest of the script to run
FRAMEWORK_DIR="${BUILT_PRODUCTS_DIR}/CommonCrypto.framework"

if [ -d "${FRAMEWORK_DIR}" ]; then
echo "${FRAMEWORK_DIR} already exists, so skipping the rest of the script."
exit 0
fi

mkdir -p "${FRAMEWORK_DIR}/Modules"
echo "module CommonCrypto [system] {
    header "${SDKROOT}/usr/include/CommonCrypto/CommonCrypto.h"
    export *
}" >> "${FRAMEWORK_DIR}/Modules/module.modulemap"

ln -sf "${SDKROOT}/usr/include/CommonCrypto" "${FRAMEWORK_DIR}/Headers"

Працює як шарм :)


Чи можете ви надати демонстраційний чи зразковий рамковий проект для того ж самого разом із файлом специфікації pod?
Gowtham

0

Я не впевнений, чи щось змінилося з Xcode 9.2, але зараз це набагато простіше досягти. Єдине, що мені довелося зробити - це створити папку під назвою "CommonCrypto" у моєму каталозі базових проектів та створити всередині неї два файли, один під назвою "cc.h" наступним чином:

#include <CommonCrypto/CommonCrypto.h>
#include <CommonCrypto/CommonRandom.h>

І ще одна назва, що називається module.modulemap:

module CommonCrypto {
    export *
    header "cc.h"
}

(Я не знаю, чому ви не можете посилатися на файли заголовків із області SDKROOT безпосередньо у файлі mapmap, але я не зміг змусити його працювати)

Третє - знайти налаштування "Шляхи імпорту" та встановити значення $ (SRCROOT). Насправді ви можете встановити його в будь-яку папку, під якою ви хочете папку CommonCrypto, якщо ви не хочете її на рівні коренів.

Після цього ви зможете користуватися

import CommonCrypto

У будь-якому швидкому файлі та всіх типах / функціях / тощо. доступні.

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


0

Якщо у вас є наступний випуск:

ld: бібліотека не знайдена для -lapple_crypto clang: error: команда linker не вдалася з кодом виходу 1 (використання -v для перегляду виклику)

У Xcode 10 Swift 4.0. CommonCrypto є частиною основи.

Додайте

 import CommonCrypto

Видалити

  • Файл lib CommonCrpto з бінарного посилання з бібліотеками фаз збірки
  • import CommonCrypto з мостового заголовка

Це працювало для мене!


-1

Це сталося так само і зі мною після оновлення Xcode. Я спробував усе, що можу зробити, наприклад, перевстановити какаопи та очистити проект, але це не вийшло. Тепер це вирішено після перезавантаження системи.


-13

Це дуже просто. Додайте

#import <CommonCrypto/CommonCrypto.h>

до .h-файлу (мостовий файл заголовка вашого проекту). Зазвичай ви можете назвати його YourProjectName-Bridging-Header.h.

Потім перейдіть до свого проекту Настройки проекту та шукайте компілятор Swift - генерація коду. Під ним додайте назву мостового заголовка до запису "Об'єктивний заголовок мосту".

Ви закінчили. У вашому коді Swift не потрібно імпорту. Будь-які загальнодоступні заголовки Objective-C, перелічені в цьому мостовому файлі заголовка, будуть видимі Swift.


ваш метод повертає помилку: використання мостових заголовків із рамковими цілями не підтримується
gorgi93

5
@ gorgi93 Ви не можете використовувати мостиковий заголовок у рамковій цілі, як свідчить помилка. Єдиний варіант - на жаль, помістити його в основний файл заголовка фреймворку.
Чарльз А.

1
Якби ви насправді червоніли заголовок цієї теми, ви б побачили, що хлопець хоче імпортувати бібліотеку CommonCrypto в рамку Swift. Ви не можете використовувати з'єднувальні заголовки в рамках, і ви не можете імпортувати рамку CommonCrypto в заголовок парасольки.
miken.mkndev
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.