#import "AssertTest.h"

@implementation AssertTest

- (void)testFail {
    BOOL didFail = NO;
    
    NS_DURING
        [self fail];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER

    [self assertTrue:didFail];
}

- (void)testFailException {
    AssertionFailedException *exception = nil;
    
    NS_DURING
        [self fail:@"Oops!"];
    NS_HANDLER
        exception = [[localException copy] autorelease];
    NS_ENDHANDLER
    
    [self assertNotNil:exception];
    [self assertTrue:[[exception name] isEqualToString:@"AssertionFailedException"]];
    [self assertTrue:[[exception reason] isEqualToString:@"Oops!"]];
}

- (void)testAssertEquals {
    id object = [[[NSObject alloc] init] autorelease];
    [self assert:object equals:object];
}

- (void)testAssertNilEqualsNil {
    [self assert:nil equals:nil];
}

- (void)testAssertNilDoesntEqualObject {
    id object = [[[NSObject alloc] init] autorelease];
    BOOL didFail = NO;

    NS_DURING
        [self assert:nil equals:object];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER

    [self assertTrue:didFail];
}

// FIXME: Is there a way you can pass an option to the compiler, or something
// like that, so that it will warn you if you pass a short as argument to a method
// which expects an int? If you know something about this, send us an email
// at objcunit@oops.se, please!

- (void)testAssertEqualsInt {
    [self assertInt:123 equals:123];
}

- (void)testAssertNotEqualInts {
    BOOL didFail = NO;

    NS_DURING
        [self assertInt:123 equals:321];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER

    [self assertTrue:didFail];
}

- (void)testAssertEqualsFloat {
    [self assertFloat:1.234 equals:1.234 precision:0.0];
}

- (void)testAssertEqualsFloatWithinDelta {
    [self assertFloat:1.1 equals:1.0 precision:0.11];
    [self assertFloat:1.0 equals:1.1 precision:0.11];
    [self assertFloat:0.011 equals:0.010 precision:0.0011];
    [self assertFloat:0.010 equals:0.011 precision:0.0011];
}

- (void)testAssertFloatEqualsNaNFails {
    BOOL didFail = NO;
    
    NS_DURING
        [self assertFloat:1.234 equals:NAN precision:0.0];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER
    
    [self assertTrue:didFail];
}

- (void)testAssertFloatNaNEqualsFails {
    BOOL didFail = NO;

    NS_DURING
        [self assertFloat:NAN equals:1.234 precision:0.0];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER

    [self assertTrue:didFail];
}

- (void)testAssertFloatNaNEqualsNaNFails {
    BOOL didFail = NO;

    NS_DURING
        [self assertFloat:NAN equals:NAN precision:0.0];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER

    [self assertTrue:didFail];
}

- (void)testAssertFloatPosInfinityNotEqualsNegInfinity {
    BOOL didFail = NO;
    
    NS_DURING
        [self assertFloat:INFINITY equals:-INFINITY precision:0.0];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER
    
    [self assertTrue:didFail];
}

- (void)testAssertFloatPosInfinityNotEquals {
    BOOL didFail = NO;
    
    NS_DURING
        [self assertFloat:INFINITY equals:1.234 precision:0.0];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER
    
    [self assertTrue:didFail];
}

- (void)testAssertFloatPosIntifinityEqualsInfinity {
    [self assertFloat:INFINITY equals:INFINITY precision:0.0];
}

- (void)testAssertFloatNegIntifinityEqualsInfinity {
    [self assertFloat:-INFINITY equals:-INFINITY precision:0.0];
}

- (void)testAssertNotNil {
    BOOL didFail = NO;
    
    [self assertNotNil:@"not nil"];

    NS_DURING
        [self assertNotNil:nil];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER
    
    [self assertTrue:didFail];
}

- (void)testAssertStringEquals {
    BOOL didFail = NO;
    
    [self assertString:@"Jeff Bridges" equals:@"Jeff Bridges"];
    
    NS_DURING
        [self assertString:@"Jeff" equals:@"Bridges"];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER
    
    [self assertTrue:didFail];
}

- (void)testAssertFalse {
    BOOL didFail = NO;
    
    [self assertFalse:NO];
    
    NS_DURING
        [self assertFalse:YES];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER
    
    [self assertTrue:didFail];
}

- (void)testAssertNil {
    BOOL didFail = NO;
    
    [self assertNil:nil];
    
    NS_DURING
        [self assertNil:self];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER
    
    [self assertTrue:didFail];
}

- (void)testAssertSame {
    BOOL didFail = NO;
    
    [self assert:self same:self];
    
    NS_DURING
        [self assert:self same:nil];
    NS_HANDLER
        didFail = YES;
    NS_ENDHANDLER
    
    [self assertTrue:didFail];
}

@end
