diff --git a/React/Base/RCTAssert.h b/React/Base/RCTAssert.h index 99b0af249960e9..903316660ef8b9 100644 --- a/React/Base/RCTAssert.h +++ b/React/Base/RCTAssert.h @@ -178,24 +178,24 @@ RCT_EXTERN NSString *RCTFormatStackTrace(NSArray *> // MARK: - New Architecture Validation typedef enum { - RCTNotAllowedValidationDisabled = 0, - RCTNotAllowedInAppWideFabric = 1, - RCTNotAllowedInBridgeless = 2, + RCTNotAllowedInBridgeless = 1, + RCTNotAllowedInAppWideFabric = 2, + RCTNotAllowedValidationDisabled = 3, } RCTNotAllowedValidation; /** * Ensure runtime assumptions holds for the new architecture by reporting when assumptions are violated. * Note: this is work in progress. * - * When type is RCTNotAllowedInAppWideFabric, validate Fabric assumptions in Bridge or Bridgeless mode. + * When level is RCTNotAllowedInAppWideFabric, validate Fabric assumptions. * i.e. Report legacy pre-Fabric call sites that should not be used while Fabric is enabled on all surfaces. * - * When type is RCTNotAllowedInBridgeless, validate Bridgeless assumptions, in Bridgeless mode only. + * When level is RCTNotAllowedInBridgeless, validate Fabric or Bridgeless assumptions. * i.e. Report Bridge call sites that should not be used while Bridgeless mode is enabled. * * Note: enabling this at runtime is not early enough to report issues within ObjC class +load execution. */ -__attribute__((used)) RCT_EXTERN void RCTNewArchitectureValidationSetEnabled(RCTNotAllowedValidation type); +__attribute__((used)) RCT_EXTERN void RCTNewArchitectureSetMinValidationLevel(RCTNotAllowedValidation level); // When new architecture validation reporting is enabled, trigger an assertion and crash. __attribute__((used)) RCT_EXTERN void @@ -208,3 +208,7 @@ RCTErrorNewArchitectureValidation(RCTNotAllowedValidation type, id context, NSSt // When ready, switch to stricter variant above. __attribute__((used)) RCT_EXTERN void RCTLogNewArchitectureValidation(RCTNotAllowedValidation type, id context, NSString *extra); +// A placeholder for callsites that frequently fail validation. +// When ready, switch to stricter variant above. +__attribute__((used)) RCT_EXTERN void +RCTNewArchitectureValidationPlaceholder(RCTNotAllowedValidation type, id context, NSString *extra); diff --git a/React/Base/RCTAssert.m b/React/Base/RCTAssert.m index 90d306e711d6e2..41bf66d46d261f 100644 --- a/React/Base/RCTAssert.m +++ b/React/Base/RCTAssert.m @@ -235,17 +235,17 @@ RCTFatalExceptionHandler RCTGetFatalExceptionHandler(void) // MARK: - New Architecture Validation - Enable Reporting #if RCT_ONLY_NEW_ARCHITECTURE -static RCTNotAllowedValidation validationReportingEnabled = RCTNotAllowedInBridgeless; +static RCTNotAllowedValidation minValidationLevel = RCTNotAllowedInBridgeless; #else -static RCTNotAllowedValidation validationReportingEnabled = RCTNotAllowedValidationDisabled; +static RCTNotAllowedValidation minValidationLevel = RCTNotAllowedValidationDisabled; #endif -__attribute__((used)) RCT_EXTERN void RCTNewArchitectureValidationSetEnabled(RCTNotAllowedValidation type) +__attribute__((used)) RCT_EXTERN void RCTNewArchitectureSetMinValidationLevel(RCTNotAllowedValidation level) { #if RCT_ONLY_NEW_ARCHITECTURE // Cannot disable the reporting in this mode. #else - validationReportingEnabled = type; + minValidationLevel = level; #endif } @@ -253,16 +253,7 @@ RCTFatalExceptionHandler RCTGetFatalExceptionHandler(void) static BOOL shouldEnforceValidation(RCTNotAllowedValidation type) { - switch (type) { - case RCTNotAllowedInAppWideFabric: - return validationReportingEnabled == RCTNotAllowedInBridgeless || - validationReportingEnabled == RCTNotAllowedInAppWideFabric; - case RCTNotAllowedInBridgeless: - return validationReportingEnabled == RCTNotAllowedInBridgeless; - case RCTNotAllowedValidationDisabled: - return NO; - } - return NO; + return type >= minValidationLevel; } static NSString *stringDescribingContext(id context) @@ -284,7 +275,7 @@ static BOOL shouldEnforceValidation(RCTNotAllowedValidation type) switch (type) { case RCTNotAllowedValidationDisabled: RCTAssert(0, @"RCTNotAllowedValidationDisabled not a validation type."); - break; + return nil; case RCTNotAllowedInAppWideFabric: notAllowedType = @"Fabric"; break; @@ -300,31 +291,55 @@ static BOOL shouldEnforceValidation(RCTNotAllowedValidation type) extra ?: @""]; } -// MARK: - New Architecture Validation - Public - -void RCTEnforceNewArchitectureValidation(RCTNotAllowedValidation type, id context, NSString *extra) +static void +newArchitectureValidationInternal(RCTLogLevel level, RCTNotAllowedValidation type, id context, NSString *extra) { if (!shouldEnforceValidation(type)) { return; } - RCTAssert(0, @"%@", validationMessage(type, context, extra)); + NSString *msg = validationMessage(type, context, extra); + if (msg) { + switch (level) { + case RCTLogLevelInfo: + RCTLogInfo(@"%@", msg); + break; + case RCTLogLevelError: + RCTLogError(@"%@", msg); + break; + case RCTLogLevelFatal: + RCTAssert(0, @"%@", msg); + break; + default: + RCTAssert(0, @"New architecture validation is only for info, error, and fatal levels."); + } + } } -void RCTErrorNewArchitectureValidation(RCTNotAllowedValidation type, id context, NSString *extra) +// MARK: - New Architecture Validation - Public + +void RCTEnforceNewArchitectureValidation(RCTNotAllowedValidation type, id context, NSString *extra) { - if (!shouldEnforceValidation(type)) { - return; - } + newArchitectureValidationInternal(RCTLogLevelFatal, type, context, extra); +} - RCTLogError(@"%@", validationMessage(type, context, extra)); +void RCTErrorNewArchitectureValidation(RCTNotAllowedValidation type, id context, NSString *extra) +{ +#if RCT_ONLY_NEW_ARCHITECTURE + newArchitectureValidationInternal(RCTLogLevelFatal, type, context, extra); +#else + newArchitectureValidationInternal(RCTLogLevelError, type, context, extra); +#endif } void RCTLogNewArchitectureValidation(RCTNotAllowedValidation type, id context, NSString *extra) { - if (!shouldEnforceValidation(type)) { - return; - } + newArchitectureValidationInternal(RCTLogLevelInfo, type, context, extra); +} - RCTLogInfo(@"%@", validationMessage(type, context, extra)); +void RCTNewArchitectureValidationPlaceholder(RCTNotAllowedValidation type, id context, NSString *extra) +{ +#if RCT_ONLY_NEW_ARCHITECTURE + newArchitectureValidationInternal(RCTLogLevelInfo, type, context, extra); +#endif }