diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml new file mode 100644 index 0000000..93b1790 --- /dev/null +++ b/.github/workflows/main.yml @@ -0,0 +1,24 @@ +name: ObjectiveRocks CI + +on: [push] + +jobs: + macOS: + name: Test macOS + runs-on: macOS-latest + steps: + - uses: actions/checkout@v1 + with: + submodules: recursive + - name: macOS + run: xcodebuild -workspace "ObjectiveRocks.xcworkspace" -scheme "ObjectiveRocks" -destination "platform=macOS" clean test + pod_lint: + name: Pod Lint + runs-on: macOS-latest + needs: [macOS] + steps: + - uses: actions/checkout@v1 + with: + submodules: recursive + - name: Pod Lint + run: pod lib lint --skip-import-validation --allow-warnings diff --git a/CHANGELOG.md b/CHANGELOG.md index 89b0992..c767bed 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,25 @@ # Change Log +## [0.11.0](https://github.com/iabudiab/ObjectiveRocks/releases/tag/0.11.0) + +Released on 2020.01.08 + +- Improve `ColumnFamilyOptions` by @jurmous in PR #19 + - Add `compactionStyle` setting + - Change `maxBytesForLevelMultiplier` to a double to match internal type + - Add missing `level0FileNumCompactionTrigger` implementation +- Expand `WriteOptions` with `noSlowdown` and `lowPriority` options by @jurmous in PR #21 +- Expand `RocksDBIterator` with `seekForPrev` and `status` methods by @jurmous in PR #22 +- Expand `CompactRangeOptions` by @jurmous in PR #25 + - `allowWriteStall`, `maxSubcompactions`, `targetPathId`, `exclusiveManualCompaction` +- Removed redundant mem-copy in Iterator and improved release semantics in `enumerate` methods by @myeyesareblind in PRs #27 & #28 +- Fix `bottommostLevelCompaction` switch statement by @jurmous in PR #20 + + +### Updated + +- Project settings to Xcode11 + ## [0.10.0](https://github.com/iabudiab/ObjectiveRocks/releases/tag/0.10.0) diff --git a/Code/RocksDB.mm b/Code/RocksDB.mm index 2d9425e..fe8ad29 100644 --- a/Code/RocksDB.mm +++ b/Code/RocksDB.mm @@ -180,7 +180,7 @@ - (void)close - (BOOL)isClosed { @synchronized(self) { - return _db == nullptr; + return _db == nullptr; } } diff --git a/Code/RocksDBColumnFamilyOptions.h b/Code/RocksDBColumnFamilyOptions.h index 0879bc5..ecfe6a3 100644 --- a/Code/RocksDBColumnFamilyOptions.h +++ b/Code/RocksDBColumnFamilyOptions.h @@ -16,6 +16,15 @@ NS_ASSUME_NONNULL_BEGIN +/** The DB compression type. */ +typedef NS_ENUM(char, RocksDBCompactionStyle) +{ + RocksDBCompressionStyleLevel = 0x0, + RocksDBCompressionStyleUniversal = 0x1, + RocksDBCompressionStyleFifo = 0x2, + RocksDBCompressionStyleNone = 0x3 +}; + /** The DB compression type. */ typedef NS_ENUM(char, RocksDBCompressionType) { @@ -70,6 +79,11 @@ typedef NS_ENUM(char, RocksDBCompressionType) */ @property (nonatomic, assign) RocksDBCompressionType compressionType; +/** @brief Set compaction style for DB. + Default: RocksDBCompactionStyleLevel + */ +@property (nonatomic, assign) RocksDBCompactionStyle compactionStyle; + /** @brief If non-nil, the specified function to determine the prefixes for keys will be used. These prefixes will be placed in the filter. @@ -106,7 +120,7 @@ typedef NS_ENUM(char, RocksDBCompressionType) @property (nonatomic, assign) uint64_t maxBytesForLevelBase; /** @brief Default: 10 */ -@property (nonatomic, assign) int maxBytesForLevelMultiplier; +@property (nonatomic, assign) double maxBytesForLevelMultiplier; /** @brief Puts are delayed 0-1 ms when any level has a compaction score that exceeds this limit. diff --git a/Code/RocksDBColumnFamilyOptions.mm b/Code/RocksDBColumnFamilyOptions.mm index b033f7b..34027ef 100644 --- a/Code/RocksDBColumnFamilyOptions.mm +++ b/Code/RocksDBColumnFamilyOptions.mm @@ -135,6 +135,16 @@ - (void)setCompressionType:(RocksDBCompressionType)compressionType _options.compression = (rocksdb::CompressionType)compressionType; } +- (void)setCompactionStyle:(RocksDBCompactionStyle)compactionStyle +{ + _options.compaction_style = (rocksdb::CompactionStyle)compactionStyle; +} + +- (RocksDBCompactionStyle)compactionStyle +{ + return (RocksDBCompactionStyle)_options.compaction_style; +} + - (void)setPrefixExtractor:(RocksDBPrefixExtractor *)prefixExtractor { _prefixExtractorWrapper = prefixExtractor; @@ -161,6 +171,11 @@ - (void)setLevel0FileNumCompactionTrigger:(int)level0FileNumCompactionTrigger _options.level0_file_num_compaction_trigger = level0FileNumCompactionTrigger; } +- (int)level0FileNumCompactionTrigger +{ + return _options.level0_file_num_compaction_trigger; +} + - (void)setLevel0SlowdownWritesTrigger:(int)level0SlowdownWritesTrigger { _options.level0_slowdown_writes_trigger = level0SlowdownWritesTrigger; @@ -211,12 +226,12 @@ - (uint64_t)maxBytesForLevelBase return _options.max_bytes_for_level_base; } -- (void)setMaxBytesForLevelMultiplier:(int)maxBytesForLevelMultiplier +- (void)setMaxBytesForLevelMultiplier:(double)maxBytesForLevelMultiplier { _options.max_bytes_for_level_multiplier = maxBytesForLevelMultiplier; } -- (int)maxBytesForLevelMultiplier +- (double)maxBytesForLevelMultiplier { return _options.max_bytes_for_level_multiplier; } diff --git a/Code/RocksDBCompactRangeOptions.h b/Code/RocksDBCompactRangeOptions.h index ea6537d..6b89029 100644 --- a/Code/RocksDBCompactRangeOptions.h +++ b/Code/RocksDBCompactRangeOptions.h @@ -26,6 +26,12 @@ typedef NS_ENUM(NSUInteger, RocksDBBottommostLevelCompaction) */ @interface RocksDBCompactRangeOptions : NSObject +/** + If true the compaction is exclusive, if false other compactions may run concurrently at the same time. + Default: true +*/ +@property (nonatomic, assign) BOOL exclusiveManualCompaction; + /** If true, compacted files will be moved to the minimum level capable of holding the data or given level (specified non-negative targetLevel). @@ -38,11 +44,30 @@ typedef NS_ENUM(NSUInteger, RocksDBBottommostLevelCompaction) */ @property (nonatomic, assign) int targetLevel; +/** + target_path_id for compaction output. Compaction outputs will be placed in options.dbPaths[target_path_id]. + Default: 0 +*/ +@property (nonatomic, assign) uint32_t targetPathId; + /** By default level based compaction will only compact the bottommost level if there is a compaction filter. */ @property (nonatomic, assign) RocksDBBottommostLevelCompaction bottommostLevelCompaction; +/** + If true, compaction will execute immediately even if doing so would cause the DB to + enter write stall mode. Otherwise, it'll sleep until load is low enough. + Default: false +*/ +@property (nonatomic, assign) BOOL allowWriteStall; + +/** + If > 0, it will replace the option in the DBOptions for this compaction + Default: 0 +*/ +@property (nonatomic, assign) uint32_t maxSubcompactions; + @end NS_ASSUME_NONNULL_END diff --git a/Code/RocksDBCompactRangeOptions.mm b/Code/RocksDBCompactRangeOptions.mm index 72cd60c..df767d2 100644 --- a/Code/RocksDBCompactRangeOptions.mm +++ b/Code/RocksDBCompactRangeOptions.mm @@ -31,6 +31,16 @@ - (instancetype)init #pragma mark - Options +- (BOOL)exclusiveManualCompaction +{ + return _options.exclusive_manual_compaction; +} + +- (void)setExclusiveManualCompaction:(BOOL)exclusiveManualCompaction +{ + _options.exclusive_manual_compaction = exclusiveManualCompaction; +} + - (BOOL)changeLevel { return _options.change_level; @@ -51,6 +61,16 @@ - (void)setTargetLevel:(int)targetLevel _options.target_level = targetLevel; } +- (uint32_t)targetPathId +{ + return _options.target_path_id; +} + +- (void)setTargetPathId:(uint32_t)targetPathId +{ + _options.target_path_id = targetPathId; +} + - (RocksDBBottommostLevelCompaction)bottommostLevelCompaction { switch (_options.bottommost_level_compaction) { @@ -62,7 +82,7 @@ - (RocksDBBottommostLevelCompaction)bottommostLevelCompaction return RocksDBBottommostLevelCompactionForce; case rocksdb::BottommostLevelCompaction::kForceOptimized: return RocksDBBottommostLevelCompactionForceOptimized; - } + } } - (void)setBottommostLevelCompaction:(RocksDBBottommostLevelCompaction)bottommostLevelCompaction @@ -70,13 +90,37 @@ - (void)setBottommostLevelCompaction:(RocksDBBottommostLevelCompaction)bottommos switch (bottommostLevelCompaction) { case RocksDBBottommostLevelCompactionSkip: _options.bottommost_level_compaction = rocksdb::BottommostLevelCompaction::kSkip; + break; case RocksDBBottommostLevelCompactionIfHaveCompactionFilter: _options.bottommost_level_compaction = rocksdb::BottommostLevelCompaction::kIfHaveCompactionFilter; + break; case RocksDBBottommostLevelCompactionForce: _options.bottommost_level_compaction = rocksdb::BottommostLevelCompaction::kForce; + break; case RocksDBBottommostLevelCompactionForceOptimized: _options.bottommost_level_compaction = rocksdb::BottommostLevelCompaction::kForceOptimized; - } + break; + } +} + +- (BOOL)allowWriteStall +{ + return _options.allow_write_stall; +} + +- (void)setAllowWriteStall:(BOOL)allowWriteStall +{ + _options.allow_write_stall = allowWriteStall; +} + +- (uint32_t)maxSubcompactions +{ + return _options.max_subcompactions; +} + +- (void)setMaxSubcompactions:(uint32_t)maxSubcompactions +{ + _options.max_subcompactions = maxSubcompactions; } @end diff --git a/Code/RocksDBError.mm b/Code/RocksDBError.mm index bf277cc..24f6831 100644 --- a/Code/RocksDBError.mm +++ b/Code/RocksDBError.mm @@ -20,10 +20,10 @@ + (NSError *)errorWithRocksStatus:(rocksdb::Status)status NSString *reason = [NSString stringWithUTF8String:status.ToString().c_str()]; NSDictionary *userInfo = @{ - NSLocalizedDescriptionKey : @"Operation couldn't be completed", - NSLocalizedFailureReasonErrorKey : reason, - RocksDBSubcodeKey: @(status.subcode()) - }; + NSLocalizedDescriptionKey : @"Operation couldn't be completed", + NSLocalizedFailureReasonErrorKey : reason, + RocksDBSubcodeKey: @(status.subcode()) + }; return [NSError errorWithDomain:RocksDBErrorDomain code:status.code() userInfo:userInfo]; } diff --git a/Code/RocksDBIterator.h b/Code/RocksDBIterator.h index a2617ef..8fd1d8b 100644 --- a/Code/RocksDBIterator.h +++ b/Code/RocksDBIterator.h @@ -43,10 +43,19 @@ NS_ASSUME_NONNULL_BEGIN The iterator `isValid` after this call if the source contains an entry that comes at or past the given key. - @param aKey The key to position the tartaritartor at. + @param aKey The key to position the iterator at. */ - (void)seekToKey:(NSData *)aKey; +/** + Positions the iterator at the last key in the source at or before the given key. + The iterator `isValid` after this call if the source contains an entry that comes at + or past the given key. + + @param aKey The key to position the iterator at. + */ +- (void)seekForPrev:(NSData *)aKey; + /** Moves to the next entry in the source. After this call, `isValid` is true if the iterator was not positioned at the last entry in the source. @@ -75,6 +84,15 @@ NS_ASSUME_NONNULL_BEGIN */ - (NSData *)value; +/** + If an error has occurred, throw it. Else just continue + If non-blocking IO is requested and this operation cannot be + satisfied without doing some IO, then this throws Error with Status::Incomplete. + + @param error RocksDBError if error happens in underlying native library. + */ +- (void)status:(NSError * __autoreleasing *)error; + /** Executes a given block for each key in the iterator. diff --git a/Code/RocksDBIterator.mm b/Code/RocksDBIterator.mm index d1e48d8..9c0b384 100644 --- a/Code/RocksDBIterator.mm +++ b/Code/RocksDBIterator.mm @@ -8,6 +8,7 @@ #import "RocksDBIterator.h" #import "RocksDBSlice.h" +#import "RocksDBError.h" #import @@ -71,6 +72,13 @@ - (void)seekToKey:(NSData *)aKey } } +- (void)seekForPrev:(NSData *)aKey +{ + if (aKey != nil) { + _iterator->SeekForPrev(SliceFromData(aKey)); + } +} + - (void)next { _iterator->Next(); @@ -84,17 +92,33 @@ - (void)previous - (NSData *)key { rocksdb::Slice keySlice = _iterator->key(); - NSData *key = DataFromSlice(keySlice); + NSData *key = [NSData dataWithBytesNoCopy:(void*)keySlice.data() + length:keySlice.size() + freeWhenDone:NO]; return key; } - (NSData *)value { rocksdb::Slice valueSlice = _iterator->value(); - NSData *value = DataFromSlice(valueSlice); + NSData *value = [NSData dataWithBytesNoCopy:(void*)valueSlice.data() + length:valueSlice.size() + freeWhenDone:NO]; return value; } +- (void)status:(NSError * __autoreleasing *)error +{ + rocksdb::Status status = _iterator->status(); + + if (!status.ok()) { + NSError *temp = [RocksDBError errorWithRocksStatus:status]; + if (error && *error == nil) { + *error = temp; + } + } +} + #pragma mark - Enumerate Keys - (void)enumerateKeysUsingBlock:(void (^)(NSData *key, BOOL *stop))block @@ -138,33 +162,35 @@ - (void)enumerateKeysAndValuesInRange:(RocksDBKeyRange *)range reverse:(BOOL)reverse usingBlock:(void (^)(NSData *key, NSData *value, BOOL *stop))block { - BOOL stop = NO; + @autoreleasepool { + BOOL stop = NO; - if (range.start != nil) { - [self seekToKey:range.start]; - } else { - reverse ? _iterator->SeekToLast(): _iterator->SeekToFirst(); - } + if (range.start != nil) { + [self seekToKey:range.start]; + } else { + reverse ? _iterator->SeekToLast(): _iterator->SeekToFirst(); + } - rocksdb::Slice limitSlice; - if (range.end != nil) { - limitSlice = SliceFromData(range.end); - } + rocksdb::Slice limitSlice; + if (range.end != nil) { + limitSlice = SliceFromData(range.end); + } - BOOL (^ checkLimit)(BOOL, rocksdb::Slice) = ^ BOOL (BOOL reverse, rocksdb::Slice key) { - if (limitSlice.size() == 0) return YES; + BOOL (^ checkLimit)(BOOL, rocksdb::Slice) = ^ BOOL (BOOL reverse, rocksdb::Slice key) { + if (limitSlice.size() == 0) return YES; - if (reverse && key.ToString() <= limitSlice.ToString()) return NO; - if (!reverse && key.ToString() >= limitSlice.ToString()) return NO; + if (reverse && key.ToString() <= limitSlice.ToString()) return NO; + if (!reverse && key.ToString() >= limitSlice.ToString()) return NO; - return YES; - }; + return YES; + }; - while (_iterator->Valid() && checkLimit(reverse, _iterator->key())) { - if (block) block(self.key, self.value, &stop); - if (stop == YES) break; + while (_iterator->Valid() && checkLimit(reverse, _iterator->key())) { + if (block) block(self.key, self.value, &stop); + if (stop == YES) break; - reverse ? _iterator->Prev(): _iterator->Next(); + reverse ? _iterator->Prev(): _iterator->Next(); + } } } @@ -180,13 +206,15 @@ - (void)enumerateKeysWithPrefix:(NSData *)prefix usingBlock:(void (^)(NSData *ke - (void)enumerateKeysAndValuesWithPrefix:(NSData *)prefix usingBlock:(void (^)(NSData *key, NSData *value, BOOL *stop))block { - BOOL stop = NO; - rocksdb::Slice prefixSlice = SliceFromData(prefix); + @autoreleasepool { + BOOL stop = NO; + rocksdb::Slice prefixSlice = SliceFromData(prefix); - for (_iterator->Seek(prefixSlice); _iterator->Valid(); _iterator->Next()) { - if (_iterator->key().starts_with(prefixSlice) == false) continue; - if (block) block(self.key, self.value, &stop); - if (stop == YES) break; + for (_iterator->Seek(prefixSlice); _iterator->Valid(); _iterator->Next()) { + if (_iterator->key().starts_with(prefixSlice) == false) continue; + if (block) block(self.key, self.value, &stop); + if (stop == YES) break; + } } } diff --git a/Code/RocksDBOptions.h b/Code/RocksDBOptions.h index ffaed78..3e24a80 100644 --- a/Code/RocksDBOptions.h +++ b/Code/RocksDBOptions.h @@ -165,6 +165,11 @@ NS_ASSUME_NONNULL_BEGIN */ @property (nonatomic, assign) RocksDBCompressionType compressionType; +/** @brief Set compaction style for DB. + Default: RocksDBCompactionStyleLevel + */ +@property (nonatomic, assign) RocksDBCompactionStyle compactionStyle; + /** @brief If non-nil, the specified function to determine the prefixes for keys will be used. These prefixes will be placed in the filter. @@ -205,7 +210,7 @@ NS_ASSUME_NONNULL_BEGIN @property (nonatomic, assign) uint64_t maxBytesForLevelBase; /** @brief Default: 10 */ -@property (nonatomic, assign) int maxBytesForLevelMultiplier; +@property (nonatomic, assign) double maxBytesForLevelMultiplier; /** @brief Maximum number of bytes in all compacted files. */ @property (nonatomic, assign) int expandedCompactionFactor; diff --git a/Code/RocksDBWriteOptions.h b/Code/RocksDBWriteOptions.h index 2b4c34b..35a4ed3 100644 --- a/Code/RocksDBWriteOptions.h +++ b/Code/RocksDBWriteOptions.h @@ -30,6 +30,21 @@ NS_ASSUME_NONNULL_BEGIN */ @property (nonatomic, assign) BOOL ignoreMissingColumnFamilies; +/** @brief If true and we need to wait or sleep for the write request, fails immediately + with [Status.Code.Incomplete]. + Default: false +*/ +@property (nonatomic, assign) BOOL noSlowdown; + +/** @brief If true, this write request is of lower priority if compaction is + behind. In this case that, [.noSlowdown] == true, the request + will be cancelled immediately with [Status.Code.Incomplete] returned. + Otherwise, it will be slowed down. The slowdown value is determined by + RocksDB to guarantee it introduces minimum impacts to high priority writes. + Default: false +*/ +@property (nonatomic, assign) BOOL lowPriority; + @end NS_ASSUME_NONNULL_END diff --git a/Code/RocksDBWriteOptions.mm b/Code/RocksDBWriteOptions.mm index 3ea3616..db59f69 100644 --- a/Code/RocksDBWriteOptions.mm +++ b/Code/RocksDBWriteOptions.mm @@ -61,6 +61,26 @@ - (void)setIgnoreMissingColumnFamilies:(BOOL)ignoreMissingColumnFamilies _options.ignore_missing_column_families = ignoreMissingColumnFamilies; } +- (BOOL)noSlowdown +{ + return _options.no_slowdown; +} + +- (void)setNoSlowdown:(BOOL)noSlowdown +{ + _options.no_slowdown = noSlowdown; +} + +- (BOOL)lowPriority +{ + return _options.low_pri; +} + +- (void)setLowPriority:(BOOL)lowPriority +{ + _options.low_pri = lowPriority; +} + #pragma mark - NSCopying - (id)copyWithZone:(NSZone *)zone diff --git a/Framework/Info.plist b/Framework/Info.plist index 47d391f..496a32c 100644 --- a/Framework/Info.plist +++ b/Framework/Info.plist @@ -15,7 +15,7 @@ CFBundlePackageType FMWK CFBundleShortVersionString - 0.10.0 + $(MARKETING_VERSION) CFBundleSignature ???? CFBundleVersion diff --git a/ObjectiveRocks.podspec b/ObjectiveRocks.podspec index 2f82e55..105f204 100644 --- a/ObjectiveRocks.podspec +++ b/ObjectiveRocks.podspec @@ -1,6 +1,6 @@ Pod::Spec.new do |s| s.name = 'ObjectiveRocks' - s.version = '0.10.0' + s.version = '0.11.0' s.summary = 'Objective-C wrapper of RocksDB - A Persistent Key-Value Store for Flash and RAM Storage.' s.license = 'MIT' s.homepage = 'https://github.com/iabudiab/ObjectiveRocks' diff --git a/ObjectiveRocks.xcodeproj/project.pbxproj b/ObjectiveRocks.xcodeproj/project.pbxproj index 57869a0..b9856c4 100644 --- a/ObjectiveRocks.xcodeproj/project.pbxproj +++ b/ObjectiveRocks.xcodeproj/project.pbxproj @@ -2830,6 +2830,7 @@ 6299F80A1A17B28200123F56 /* Products */, ); sourceTree = ""; + usesTabs = 1; }; 6299F80A1A17B28200123F56 /* Products */ = { isa = PBXGroup; @@ -3723,7 +3724,7 @@ attributes = { LastSwiftMigration = 0700; LastSwiftUpdateCheck = 0700; - LastUpgradeCheck = 0930; + LastUpgradeCheck = 1130; ORGANIZATIONNAME = BrainCookie; TargetAttributes = { 624203BF1BED64410043DD6F = { @@ -3734,7 +3735,7 @@ }; 6299F8131A17B28200123F56 = { CreatedOnToolsVersion = 6.1; - LastSwiftMigration = 0920; + LastSwiftMigration = 1130; }; 62A8B0441A58C40A0069B4C8 = { LastSwiftMigration = 0920; @@ -3743,11 +3744,11 @@ }; buildConfigurationList = 6299F8041A17B28200123F56 /* Build configuration list for PBXProject "ObjectiveRocks" */; compatibilityVersion = "Xcode 3.2"; - developmentRegion = English; + developmentRegion = en; hasScannedForEncodings = 0; knownRegions = ( - English, en, + Base, ); mainGroup = 6299F8001A17B28200123F56; productRefGroup = 6299F80A1A17B28200123F56 /* Products */; @@ -4438,6 +4439,7 @@ "$(PROJECT_DIR)/rocksdb", ); MACOSX_DEPLOYMENT_TARGET = 10.10; + MARKETING_VERSION = 0.11.0; PRODUCT_BUNDLE_IDENTIFIER = de.iabudiab.ObjectiveRocks; PRODUCT_NAME = ObjectiveRocks; SDKROOT = macosx; @@ -4481,6 +4483,7 @@ "$(PROJECT_DIR)/rocksdb", ); MACOSX_DEPLOYMENT_TARGET = 10.10; + MARKETING_VERSION = 0.11.0; PRODUCT_BUNDLE_IDENTIFIER = de.iabudiab.ObjectiveRocks; PRODUCT_NAME = ObjectiveRocks; SDKROOT = macosx; @@ -4581,6 +4584,7 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; CLANG_CXX_LIBRARY = "libc++"; CLANG_ENABLE_MODULES = YES; @@ -4633,6 +4637,7 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; CLANG_CXX_LIBRARY = "libc++"; CLANG_ENABLE_MODULES = YES; @@ -4699,7 +4704,7 @@ SWIFT_OBJC_BRIDGING_HEADER = "Tests/ObjectiveRocksTests-Bridging-Header.h"; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; SWIFT_SWIFT3_OBJC_INFERENCE = Default; - SWIFT_VERSION = 4.0; + SWIFT_VERSION = 5.0; }; name = Debug; }; @@ -4722,7 +4727,7 @@ SDKROOT = macosx; SWIFT_OBJC_BRIDGING_HEADER = "Tests/ObjectiveRocksTests-Bridging-Header.h"; SWIFT_SWIFT3_OBJC_INFERENCE = Default; - SWIFT_VERSION = 4.0; + SWIFT_VERSION = 5.0; }; name = Release; }; diff --git a/ObjectiveRocks.xcodeproj/xcshareddata/xcschemes/ObjectiveRocks-iOS.xcscheme b/ObjectiveRocks.xcodeproj/xcshareddata/xcschemes/ObjectiveRocks-iOS.xcscheme index d0a3c3f..269c2c6 100644 --- a/ObjectiveRocks.xcodeproj/xcshareddata/xcschemes/ObjectiveRocks-iOS.xcscheme +++ b/ObjectiveRocks.xcodeproj/xcshareddata/xcschemes/ObjectiveRocks-iOS.xcscheme @@ -1,6 +1,6 @@ + shouldUseLaunchSchemeArgsEnv = "YES" + codeCoverageEnabled = "YES"> + + + + @@ -54,17 +63,6 @@ - - - - - - - - + + + + @@ -39,17 +48,6 @@ - - - - - - - - + + + + @@ -39,17 +48,6 @@ - - - - - - - -