Skip to content

Commit

Permalink
moved the attribute validator to the BlockAttributeValidator class to…
Browse files Browse the repository at this point in the history
… try to address concerns.
  • Loading branch information
mbruin-NR committed Jan 23, 2025
1 parent 47ff808 commit c694a19
Show file tree
Hide file tree
Showing 6 changed files with 73 additions and 70 deletions.
2 changes: 2 additions & 0 deletions Agent/Analytics/BlockAttributeValidator.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,8 @@ NS_ASSUME_NONNULL_BEGIN
valueValidator:(ValueValidator)valueValidator
andEventTypeValidator:(EventTypeValidator)eventTypeValidator;

+ (BlockAttributeValidator *) attributeValidator;

@end

NS_ASSUME_NONNULL_END
63 changes: 63 additions & 0 deletions Agent/Analytics/BlockAttributeValidator.m
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@
//

#import "BlockAttributeValidator.h"
#import "Constants.h"
#import "NRMAAnalytics.h"
#import "NRLogger.h"

@implementation BlockAttributeValidator

Expand Down Expand Up @@ -35,4 +38,64 @@ - (BOOL)valueValidator:(id)value {
return self.valueValidator(value);
}

static BlockAttributeValidator *_attributeValidator;
+ (BlockAttributeValidator *) attributeValidator
{
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
_attributeValidator = [[BlockAttributeValidator alloc] initWithNameValidator:^BOOL(NSString *name) {
if ([name length] == 0) {
NRLOG_AGENT_ERROR(@"invalid attribute: name length = 0");
return false;
}
if ([name hasPrefix:@" "]) {
NRLOG_AGENT_ERROR(@"invalid attribute: name prefix = \" \"");
return false;
}
// check if attribute name is reserved or attribute name matches reserved prefix.
for (NSString* key in [NRMAAnalytics reservedKeywords]) {
if ([key isEqualToString:name]) {
NRLOG_AGENT_ERROR(@"invalid attribute: name prefix disallowed");
return false;
}
}
for (NSString* key in [NRMAAnalytics reservedPrefixes]) {
if ([name hasPrefix:key]) {
NRLOG_AGENT_ERROR(@"invalid attribute: name prefix disallowed");
return false;
}
}

// check if attribute name exceeds max length.
if ([name length] > kNRMA_Attrib_Max_Name_Length) {
NRLOG_AGENT_ERROR(@"invalid attribute: name length exceeds limit");
return false;
}
return true;

} valueValidator:^BOOL(id value) {
if ([value isKindOfClass:[NSString class]]) {
if ([(NSString*)value length] == 0) {
NRLOG_AGENT_ERROR(@"invalid attribute: value length = 0");
return false;
}
else if ([(NSString*)value length] >= kNRMA_Attrib_Max_Value_Size_Bytes) {
NRLOG_AGENT_ERROR(@"invalid attribute: value exceeded maximum byte size exceeded");
return false;
}
}
if (value == nil || [value isKindOfClass:[NSNull class]]) {
NRLOG_AGENT_ERROR(@"invalid attribute: value cannot be nil");
return false;
}

return true;
} andEventTypeValidator:^BOOL(NSString *eventType) {
return YES;
}];
});

return _attributeValidator;
}

@end
2 changes: 1 addition & 1 deletion Agent/Analytics/NRMAAnalytics.mm
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,7 @@ - (id) initWithSessionStartTimeMS:(long long) sessionStartTime {
PersistentEventStore *eventStore = [[PersistentEventStore alloc] initWithFilename:filename andMinimumDelay:.025];

_eventManager = [[NRMAEventManager alloc] initWithPersistentStore:eventStore];
_attributeValidator = [NewRelicInternalUtils attributeValidator];
_attributeValidator = [BlockAttributeValidator attributeValidator];
_sessionAttributeManager = [[NRMASAM alloc] initWithAttributeValidator:_attributeValidator];

NSString* attributes = [self sessionAttributeJSONString];
Expand Down
13 changes: 7 additions & 6 deletions Agent/HandledException/NRMAHandledExceptions.mm
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
#import "NRMABool.h"
#import "NRMASupportMetricHelper.h"
#import "Constants.h"
#import "BlockAttributeValidator.h"

@interface NRMAAnalytics(Protected)
// Because the NRMAAnalytics class interfaces with non Objective-C++ files, we cannot expose the API on the header. Therefore, we must use this reference.
Expand Down Expand Up @@ -198,7 +199,7 @@ - (void) recordError:(NSError * _Nonnull)error
resultMap,
[self createThreadVector:callstack length:frames]
);
NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[NewRelicInternalUtils attributeValidator]] autorelease];
NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[BlockAttributeValidator attributeValidator]] autorelease];

if (attributes != nil) {
[contextAdapter addAttributesNewValidation:attributes];
Expand All @@ -218,7 +219,7 @@ - (void) recordError:(NSError * _Nonnull)error
[self createThreadVector:callstack length:frames]
);

NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[NewRelicInternalUtils attributeValidator]] autorelease];
NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[BlockAttributeValidator attributeValidator]] autorelease];

if (attributes != nil) {
[contextAdapter addAttributes:attributes];
Expand Down Expand Up @@ -268,7 +269,7 @@ - (void) recordHandledException:(NSException*)exception

[self checkOffline:report];

NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[NewRelicInternalUtils attributeValidator]] autorelease];
NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[BlockAttributeValidator attributeValidator]] autorelease];

if (attributes != nil) {
[contextAdapter addAttributesNewValidation:attributes];
Expand All @@ -287,7 +288,7 @@ - (void) recordHandledException:(NSException*)exception

[self checkOffline:report];

NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[NewRelicInternalUtils attributeValidator]] autorelease];
NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[BlockAttributeValidator attributeValidator]] autorelease];

if (attributes != nil) {
[contextAdapter addAttributes:attributes];
Expand Down Expand Up @@ -371,7 +372,7 @@ - (void) recordHandledExceptionWithStackTrace:(NSDictionary*)exceptionDictionary
report->setAttributeNoValidation("timeSinceLoad", [[[NSDate new] autorelease] timeIntervalSinceDate:self.sessionStartDate]);
[self checkOffline:report];

NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[NewRelicInternalUtils attributeValidator]] autorelease];
NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[BlockAttributeValidator attributeValidator]] autorelease];

if (exceptionDictionary != nil) {
[contextAdapter addAttributesNewValidation:exceptionDictionary];
Expand All @@ -388,7 +389,7 @@ - (void) recordHandledExceptionWithStackTrace:(NSDictionary*)exceptionDictionary
report->setAttribute("timeSinceLoad", [[[NSDate new] autorelease] timeIntervalSinceDate:self.sessionStartDate]);
[self checkOffline:report];

NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[NewRelicInternalUtils attributeValidator]] autorelease];
NRMAExceptionReportAdaptor* contextAdapter = [[[NRMAExceptionReportAdaptor alloc] initWithReport:report attributeValidator:[BlockAttributeValidator attributeValidator]] autorelease];

if (exceptionDictionary != nil) {
[contextAdapter addAttributes:exceptionDictionary];
Expand Down
3 changes: 0 additions & 3 deletions Agent/Utilities/NewRelicInternalUtils.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@
#import "NRMAReachability.h"
#import "NRConstants.h"
#import "NRMANetworkMonitor.h"
#import "BlockAttributeValidator.h"

#if __LP64__
#define NRMA_NSI "ld"
Expand Down Expand Up @@ -105,7 +104,5 @@ NSTimeInterval NRMAMillisecondTimestamp(void);

+ (NRMAReachability*) reachability;

+ (id<AttributeValidatorProtocol>) attributeValidator;

@end

60 changes: 0 additions & 60 deletions Agent/Utilities/NewRelicInternalUtils.m
Original file line number Diff line number Diff line change
Expand Up @@ -689,64 +689,4 @@ + (BOOL) isSimulator {
return simulator != nil;
}

static id<AttributeValidatorProtocol> _attributeValidator;
+ (id<AttributeValidatorProtocol>) attributeValidator
{
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
_attributeValidator = [[BlockAttributeValidator alloc] initWithNameValidator:^BOOL(NSString *name) {
if ([name length] == 0) {
NRLOG_AGENT_ERROR(@"invalid attribute: name length = 0");
return false;
}
if ([name hasPrefix:@" "]) {
NRLOG_AGENT_ERROR(@"invalid attribute: name prefix = \" \"");
return false;
}
// check if attribute name is reserved or attribute name matches reserved prefix.
for (NSString* key in [NRMAAnalytics reservedKeywords]) {
if ([key isEqualToString:name]) {
NRLOG_AGENT_ERROR(@"invalid attribute: name prefix disallowed");
return false;
}
}
for (NSString* key in [NRMAAnalytics reservedPrefixes]) {
if ([name hasPrefix:key]) {
NRLOG_AGENT_ERROR(@"invalid attribute: name prefix disallowed");
return false;
}
}

// check if attribute name exceeds max length.
if ([name length] > kNRMA_Attrib_Max_Name_Length) {
NRLOG_AGENT_ERROR(@"invalid attribute: name length exceeds limit");
return false;
}
return true;

} valueValidator:^BOOL(id value) {
if ([value isKindOfClass:[NSString class]]) {
if ([(NSString*)value length] == 0) {
NRLOG_AGENT_ERROR(@"invalid attribute: value length = 0");
return false;
}
else if ([(NSString*)value length] >= kNRMA_Attrib_Max_Value_Size_Bytes) {
NRLOG_AGENT_ERROR(@"invalid attribute: value exceeded maximum byte size exceeded");
return false;
}
}
if (value == nil || [value isKindOfClass:[NSNull class]]) {
NRLOG_AGENT_ERROR(@"invalid attribute: value cannot be nil");
return false;
}

return true;
} andEventTypeValidator:^BOOL(NSString *eventType) {
return YES;
}];
});

return _attributeValidator;
}

@end

0 comments on commit c694a19

Please sign in to comment.