Xcode / iOS: Bagaimana menentukan apakah kode berjalan di DEBUG / RELEASE build?

241

Saya membuat aplikasi yang memproses data kartu kredit sensitif.

Jika kode saya berjalan dalam mode debug saya ingin mencatat data ini ke konsol dan membuat beberapa dump file.

Namun pada versi appstore final (yaitu ketika sedang berjalan dalam mode rilis) sangat penting semua ini dinonaktifkan (bahaya keamanan)!

Saya akan mencoba menjawab pertanyaan saya sebaik mungkin; jadi pertanyaannya menjadi 'Apakah solusi ini tepat atau cara terbaik untuk melakukannya?'

// add `IS_DEBUG=1` to your debug build preprocessor settings  

#if( IS_DEBUG )  
#define MYLog(args...) NSLog(args)  
#else  
#define MYLog(args...)  
#endif  
P i
sumber

Jawaban:

248

Periksa pengaturan pembangunan proyek Anda di bawah 'Apple LLVM - Preprocessing', 'Preprocessor Macros' untuk debug untuk memastikan bahwa DEBUGsedang diatur - lakukan ini dengan memilih proyek dan mengklik pada tab pengaturan build. Cari DEBUGdan cari untuk melihat apakah memang DEBUGsedang diatur.

Perhatikan juga. Anda mungkin melihat DEBUG diubah ke nama variabel lain seperti DEBUG_MODE.

Bangun Pengaturan tab dari pengaturan proyek saya

kemudian kode kondisional untuk DEBUG dalam file sumber Anda

#ifdef DEBUG

// Something to log your sensitive data here

#else

// 

#endif
Damo
sumber
Terima kasih atas jawaban Anda, jika saya mencoba membuat seperti ini:, #ifdef DEBUG NSLog@("Something");#else//#endifini tidak berhasil. Bagaimana saya bisa menginisialisasi tombol atau mencatat sesuatu ke konsol, bisakah Anda mengedit pertanyaan Anda?
Malloc
Bagaimana dengan di Swift?
technophyle
dapatkah saya mengubah makro ini secara terprogram saat dijalankan? Saya ingin mengaktifkan tombol yang beralih ke API produksi. Pada tombol itu, saya ingin mengubah DEBUG menjadi 0 dan menampilkan pesan bahwa pengguna perlu memulai ulang aplikasi. Jadi lain kali akan menggunakan API produksi.
Hiren Prajapati
130

Untuk solusi di Swift silakan merujuk utas ini di SO.

Pada dasarnya solusi di Swift akan terlihat seperti ini:

#if DEBUG
    println("I'm running in DEBUG mode")
#else
    println("I'm running in a non-DEBUG mode")
#endif

Selain itu Anda perlu mengatur DEBUGsimbol di Swift Compiler - Custom Flagsbagian untuk Other Swift Flagskunci melalui -D DEBUGentri. Lihat tangkapan layar berikut untuk contoh:

masukkan deskripsi gambar di sini

Astaga
sumber
1
Di mana saya menemukan Swift Compiler - Custom Flags?
confile
2
@ confile: Saya telah melampirkan tangkapan layar yang seharusnya menjelaskan di mana menemukannya. Semoga ini bisa membantu!
Jeehut
1
Ingat ini harus didefinisikan untuk kerangka kerja spesifik / ekstensi yang menggunakannya! Jadi jika Anda memiliki ekstensi keyboard / hari ini tentukan di sana. Jika Anda memiliki beberapa jenis kerangka kerja yang sama. Ini mungkin hanya diperlukan jika target utama adalah tujuan ...
Warpzit
terima kasih, sepertinya Other Swift Flagskunci tidak akan muncul kecuali Anda memilih Alldan di combinedatas
Oscar Zhang
Terima kasih! Ini yang saya lewatkan. Saya mengaturnya untuk Dentang tetapi tidak Swift.
bugloaf
90

Apple sudah menyertakan DEBUGflag dalam debug build, jadi Anda tidak perlu menentukan sendiri.

Anda mungkin juga ingin mempertimbangkan hanya mendefinisikan ulang NSLogke operasi nol ketika tidak dalam DEBUGmode, sehingga kode Anda akan lebih portabel dan Anda hanya dapat menggunakan biasaNSLog pernyataan :

//put this in prefix.pch

#ifndef DEBUG
#undef NSLog
#define NSLog(args, ...)
#endif
Nick Lockwood
sumber
33

Sebagian besar jawaban mengatakan bahwa cara mengatur #ifdef DEBUG dan tidak ada yang mengatakan bagaimana cara menentukan debug / rilis build.

Pendapat saya:

  1. Edit skema -> run -> build configuration: pilih debug / release. Ini dapat mengontrol simulator dan status kode pengujian iPhone Anda.

  2. Edit skema -> arsip -> konfigurasi bangunan: pilih debug / lepaskan. Itu dapat mengontrol aplikasi paket tes dan status kode aplikasi App Store. masukkan deskripsi gambar di sini

Qun Li
sumber
Jawaban yang diberikan !!! ini membantu saya mengidentifikasi masalah saya. Dalam kasus saya, saya tetap menggunakan Archivemode Debugdan mengirimkan aplikasi ke app store. Saat memeriksa hasil setelah pengunduhan aplikasi dari iTunes, itu tidak berfungsi. Jadi pastikan itu DEBUG/RELEASEhanya berfungsi saat dipilih masing-masing mode di Build/Run/Archive.
Bhavin_m
13

Swift dan Xcode 10+

#if DEBUGakan melewati pengembangan, perangkat, atau simulator ad-hoc APAPUN. Ini hanya salah untuk App Store dan build TestFlight.

Contoh:

#if DEBUG
   print("Not App Store build")
#else
   print("App Store build")
#endif
Kirill Kudaev
sumber
8

Jawaban zitao xiong cukup dekat dengan apa yang saya gunakan; Saya juga memasukkan nama file (dengan menghapus jalur FILE ).

#ifdef DEBUG
    #define NSLogDebug(format, ...) \
    NSLog(@"<%s:%d> %s, " format, \
    strrchr("/" __FILE__, '/') + 1, __LINE__, __PRETTY_FUNCTION__, ## __VA_ARGS__)
#else
    #define NSLogDebug(format, ...)
#endif
geowar
sumber
7

Di xcode 7, ada bidang di bawah Apple LLVM 7.0 - preprocessing , yang disebut " Preprocessors Macros Not Used In Precompile ... "? Saya meletakkan DEBUG di depan Debug dan berfungsi untuk saya dengan menggunakan kode di bawah ini:

#ifdef DEBUG
    NSString* const kURL = @"http://debug.com";
#else
    NSString* const kURL = @"http://release.com";
#endif
Fa.Shapouri
sumber
4

Hanya satu ide lagi untuk dideteksi:

DebugMode.h

#import <Foundation/Foundation.h>

@interface DebugMode: NSObject
    +(BOOL) isDebug;
@end

DebugMode.m

#import "DebugMode.h"

@implementation DebugMode
+(BOOL) isDebug {
#ifdef DEBUG
    return true;
#else
    return false;
#endif
}
@end

tambahkan ke file header jembatan:

#include "DebugMode.h"

pemakaian:

DebugMode.isDebug()

Tidak perlu menulis sesuatu di dalam properti proyek dengan cepat.

Vyacheslav
sumber
1

Tidak yakin jika saya menjawab pertanyaan Anda, mungkin Anda dapat mencoba kode ini:

#ifdef DEBUG
#define DLOG(xx, ...)  NSLog( \
    @"%s(%d): " \
    xx, __PRETTY_FUNCTION__, __LINE__, ##__VA_ARGS__ \  
    )
#else
#define DLOG(xx, ...)  ((void)0)
#endif 
Zitao Xiong
sumber
Bisakah Anda menguraikan apa yang dilakukan definisi itu? Terlihat rapi, tapi saya tidak mengerti. X Biasanya menunjukkan makro milik Apple, sedangkan PRETTY_FUNCTION menunjukkan sesuatu yang dibuat pengguna, sehingga hasilnya membingungkan
P i
2
xx adalah format string, Anda dapat menggunakan apa pun yang Anda inginkan, jika identik dengan string sebelumnya. Anda dapat menggunakan FUNCTION , tetapi PRETTY_FUNCTION mencetak nama metode Objective-C. tautan ini menjelaskannya dengan sangat baik.
Zitao Xiong