//
//  TestResultDataCollector.m
//  SKCore
//
//  Created by jungeol.park on 2014. 10. 1..
//  Copyright (c) 2014 ACCVUER. All rights reserved.
//

#import "TestResultDataCollector.h"
#import "../3rdParty/GoldRaccoon/Requests/GRUploadRequest.h"
#import "FTPLogger.h"

@implementation TestResultDataCollector

static TestResultDataCollector *instance = nil;
+(TestResultDataCollector *)sharedInstance
{
    if (!instance)
    {
        static dispatch_once_t onceToken;
        dispatch_once(&onceToken, ^{
            instance = [[TestResultDataCollector alloc] init];
        });
     
    }
    return instance;
}

- (id)init
{
    self = [super init];
    if (self)
    {
        [self initJapanOperator];
    }
    return self;
}

-(void)initResultData
{
    // common result init
    self.StartTime = @"";
    self.EndTime = @"";
    self.Latency = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    self.Packet_Loss = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    self.Max_DL_Throughput = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    self.Max_UL_Throughput = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    self.Avg_DL_Throughput = [[NSMutableArray alloc] init];
    self.Avg_UL_Throughput = [[NSMutableArray alloc] init];
    
    // GET result init
    self.GET_thread = @"";
    self.GET_result = [[NSMutableArray alloc] init];
    self.GET_warmup_Bytes = [[NSMutableArray alloc] init];
    self.GET_warmup_time = [[NSMutableArray alloc] init];
    self.GET_Byte_sec = [[NSMutableArray alloc] init];
    self.GET_Transfer_Time = [[NSMutableArray alloc] init];
    self.GET_Byte_Total = [[NSMutableArray alloc] init];
    
    // POST result init
    self.POST_thread = @"";
    self.POST_result = [[NSMutableArray alloc] init];
    self.POST_warmup_bytes = [[NSMutableArray alloc] init];
    self.POST_warmup_time = [[NSMutableArray alloc] init];
    self.POST_Byte_sec = [[NSMutableArray alloc] init];
    self.POST_Transfer_Time = [[NSMutableArray alloc] init];
    self.POST_Byte_Total = [[NSMutableArray alloc] init];
    
    // Latency result init
    self.RTT_Result = STR_FAIL;
    self.RTT_AVG = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    self.RTT_STDDEV = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    self.Received_packets = TEST_RESULT_UNKNOW_VALUE_int_TYPE;
    self.Lost_packet = TEST_RESULT_UNKNOW_VALUE_int_TYPE;
    self.RTT_MIN = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    self.RTT_MAX = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    
    self.requestsManager = nil;
}


-(void) doProcessFinalResultWithDBIndex:(NSNumber*)testId
{
    [FTPLogger writeLogToFile:@"\nTSV: TSV Process Started\n\n"];
    
    if (testId == nil)
    {
        [FTPLogger writeLogToFile:@"TSV: <ERROR>, testID is nil, can not update to local DB, TSV Process Stoped\n"];
        [self uploadFinishedWithError:YES];
        return;
    }
    
    //////////////////////////////////////////////
    // processing final test result
    //
    // 1. create result array
    // 2. write to DB
    // 3. write to file
    // 4. upload writed file to FTP
    //////////////////////////////////////////////
    
    // 1. create result array
    // closeset target
    NSString *target = [[SKAAppDelegate getAppDelegate] amdGetClosestTarget];
    NSString *target_ip = [SKIPHelper hostIPAddress:target]; 
    NSString *targetName = [[SKAAppDelegate getAppDelegate].testSchedule_new getClosestTargetName:target];
    
    // location
    double longitude = [[SKAAppDelegate getAppDelegate] amdGetLongitude];
    if(longitude == 0)
        longitude = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    
    double latitude = [[SKAAppDelegate getAppDelegate] amdGetLatitude];
    if(latitude == 0)
        latitude = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    
    double accuracy = [SKAAppDelegate getAppDelegate].accuracy;
    if(accuracy == 0)
        accuracy = TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    
    // network operator, code name
        
    NSString *operatorCode = [SKGlobalMethods getSimOperatorCodeMCCAndMNC];
    NSString *operatorName;
    if(operatorCode == nil || [operatorCode isEqualToString:@""])
    {
        operatorName = [SKGlobalMethods getCarrierName];
        operatorCode = @"";
    }
    else
    {
        if(m_japanOperatorDic == nil)
        {
            operatorName = [SKGlobalMethods getCarrierName]; 
        }
        else
        {
            NSString *temp = [m_japanOperatorDic valueForKey:operatorCode];
            
            if(temp == nil || [temp isEqualToString:@""])
                operatorName = [SKGlobalMethods getCarrierName]; 
            else
                operatorName = [NSString stringWithString:temp];
        }
    }
    
    NSMutableArray *resultArr = [[NSMutableArray alloc] initWithObjects:
                                    testId,
                                    self.StartTime,
                                    self.EndTime,
                                    targetName,
                                    target_ip,
                                    @"GET_POST_RTT", 
                                    [self doubleToString:[self calculateAvgDoubleType:self.Avg_DL_Throughput]],
                                    [self doubleToString:[self calculateAvgDoubleType:self.Avg_UL_Throughput]],
                                    [self doubleToString:self.Max_DL_Throughput],
                                    [self doubleToString:self.Max_UL_Throughput],
                                    [self doubleToString:self.Latency],
                                    [self doubleToString:self.Packet_Loss],
                                    [self getTestResult:self.GET_result],
                                    self.GET_thread,
                                    [self nsuintegerToString:[self calculateAvgNSUIntegerType:self.GET_warmup_Bytes]],
                                    [self doubleToString:[self calculateAvgDoubleType:self.GET_warmup_time]],
                                    [self intToString:[self calculateAvgIntType:self.GET_Byte_sec]],
                                    [self doubleToString:[self calculateAvgDoubleType:self.GET_Transfer_Time]],
                                    [self nsuintegerToString:[self calculateAvgNSUIntegerType:self.GET_Byte_Total]],
                                    [self getTestResult:self.POST_result],
                                    self.POST_thread,
                                    [self nsuintegerToString:[self calculateAvgNSUIntegerType:self.POST_warmup_bytes]],
                                    [self doubleToString:[self calculateAvgDoubleType:self.POST_warmup_time]],
                                    [self intToString:[self calculateAvgIntType:self.POST_Byte_sec]],
                                    [self doubleToString:[self calculateAvgDoubleType:self.POST_Transfer_Time]],
                                    [self nsuintegerToString:[self calculateAvgNSUIntegerType:self.POST_Byte_Total]],
                                    self.RTT_Result,
                                    [self doubleToString:self.RTT_AVG],
                                    [self doubleToString:self.RTT_MIN],
                                    [self doubleToString:self.RTT_MAX],
                                    [self doubleToString:self.RTT_STDDEV],
                                    [self intToString:self.Received_packets],
                                    [self intToString:self.Lost_packet],
                                    [SKGlobalMethods getDeviceModel],
                                    @"Apple",
                                    [[UIDevice currentDevice] systemName],
                                    [[UIDevice currentDevice] systemVersion],
                                    [SKGlobalMethods getNetWorkTechName],
                                    [SKGlobalMethods getDeviceModel],
                                    @"TRUE",
                                    [SKGlobalMethods getConnectionResultString:(ConnectionStatus)[[SKAAppDelegate getAppDelegate] amdGetConnectionStatus]],
                                    operatorName,
                                    operatorCode,
                                    operatorName,
                                    operatorCode,
                                    STR_NA,
                                    @"",
                                    @"",
                                    @"",
                                    @"",
                                    @"",
                                    @"",
                                    @"",
                                    [SKGlobalMethods getNetworkOrGps],
                                    [self doubleToString:longitude],
                                    [self doubleToString:latitude],
                                    [self doubleToString:accuracy],
                                    @"",
                                    @"",
                                    @"",
                                    @"",
                                    @"",
                                    @"",
                                    @"",
                                    nil];
    
    int historyTableCloumnCount =  [SKDatabase getHistoryTableColumnCount]; 
    
    if(historyTableCloumnCount < 0 || resultArr.count != historyTableCloumnCount)
    {
        [FTPLogger writeLogToFile:@"TSV: <ERROR>, historyTable cloumn count error, can not update to local DB. TSV Process Stoped\n"];
        [self uploadFinishedWithError:YES];
        return;
    }
    
    // 2. write to DB
    [SKDatabase storeHistory:testId withResultArr:resultArr];
    [FTPLogger writeLogToFile:@"TSV: update local DB done\n"];
    
    // 3. write to file
    NSString *tsvHeaderLineStr = @"StartTime\tEndTime\tTarget_Name\tTarget_IP\tRequested_Tests\tAvg_DL_Throughput\tAvg_UL_Throughput\tMax_DL_Throughput\tMax_UL_Throughput\tLatency\tPacket_Loss_Ratio\tGET_Result\tGET_Thread\tGET_Warmup_Bytes\tGET_Warmup_Time\tGET_Byte_Sec\tGET_Transfer_Time\tGET_Byte_Total\tPOST_Result\tPOST_Thread\tPOST_Warmup_Bytes\tPOST_Warmup_Time\tPOST_Byte_Sec\tPOST_Transfer_Time\tPOST_Byte_Total\tRTT_Result\tRTT_Avg\tRTT_MIN\tRTT_MAX\tRTT_STDDEV\tReceived_Packets\tLost_packet\tModel\tManufacturer\tOS_Type\tOS_Version\tNetwork_Type\tPhone_Type\tConnected\tActive_Network_Type\tNetwork_Operator_Name\tNetwork_Operator_Code\tSIM_Operator_Name\tSIM_Operator_Code\tRoaming\tTotal_TX_Bytes\tMobile_TX_Bytes\tAPP_TX_Bytes\tTotal_RX_Bytes\tMobile_RX_Bytes\tAPP_RX_Bytes\tDuration\tLocation_Type\tLongitude\tLatitude\tAccuracy\tLTE_RSSI\tLTE_CellID\tGSM_RSSI\tGSM_CellID\tCDMA_RSSI\tCDMA_BSID\tEVDO_RSSI\n";
    
    
    [resultArr removeObjectAtIndex:0];
    
    NSString *testResultStr = [resultArr componentsJoinedByString:@"\t"];
    NSString *tsvStr = [tsvHeaderLineStr stringByAppendingString:testResultStr];
    
    if ([self doSaveTsv:tsvStr])
    {
        [FTPLogger writeLogToFile:@"TSV: save TSV file done\n"];
    }
    else
    {
        [FTPLogger writeLogToFile:@"TSV: <ERROR>, save TSV file error. continue to upload other TSV file in local directory\n"];
        
    }
    
    // 4. upload writed file to FTP
    [self doUploadTsvToFtp];
    

//////////////////////////////////////////////////////////////
/////////////////   ・・・ｼ・ｼ・・・・  //////////////////////////////
//////////////////////////////////////////////////////////////
//    StartTime             = self.StartTime
//    EndTime               = self.EndTime
//    Target_Name           = targetName
//    Target_IP             = target_ip
//    Requested_Tests       = @"GET_POST_RTT" 
//    Avg_DL_Throughput     = [self doubleToString:[self calculateAvgDoubleType:self.Avg_DL_Throughput]]
//    Avg_UL_Throughput     = [self doubleToString:[self calculateAvgDoubleType:self.Avg_UL_Throughput]]
//    Max_DL_Throughput     = [self doubleToString:self.Max_DL_Throughput]
//    Max_UL_Throughput     = [self doubleToString:self.Max_UL_Throughput]
//    Latency               = [self doubleToString:self.Latency]
//    Packet_Loss_Ratio     = [self doubleToString:self.Packet_Loss]
//    GET_Result            = [self getTestResult:self.GET_result]
//    GET_Thread            = self.GET_thread
//    GET_Warmup_Bytes      = [self nsuintegerToString:[self calculateAvgNSUIntegerType:self.GET_warmup_Bytes]]
//    GET_Warmup_Time       = [self doubleToString:[self calculateAvgDoubleType:self.GET_warmup_time]]
//    GET_Byte_Sec          = [self intToString:[self calculateAvgIntType:self.GET_Byte_sec]]
//    GET_Transfer_Time     = [self doubleToString:[self calculateAvgDoubleType:self.GET_Transfer_Time]]
//    GET_Byte_Total        = [self nsuintegerToString:[self calculateAvgNSUIntegerType:self.GET_Byte_Total]]
//    POST_Result           = [self getTestResult:self.POST_result]
//    POST_Thread           = self.POST_thread
//    POST_Warmup_Bytes     = [self nsuintegerToString:[self calculateAvgNSUIntegerType:self.POST_warmup_bytes]]
//    POST_Warmup_Time      = [self doubleToString:[self calculateAvgDoubleType:self.POST_warmup_time]]
//    POST_Byte_Sec         = [self intToString:[self calculateAvgIntType:self.POST_Byte_sec]]
//    POST_Transfer_Time    = [self doubleToString:[self calculateAvgDoubleType:self.POST_Transfer_Time]]
//    POST_Byte_Total       = [self nsuintegerToString:[self calculateAvgNSUIntegerType:self.POST_Byte_Total]]
//    RTT_Result            = self.RTT_Result
//    RTT_Avg               = [self doubleToString:self.RTT_AVG]
//    RTT_MIN               = [self doubleToString:self.RTT_MIN]
//    RTT_MAX               = [self doubleToString:self.RTT_MAX]
//    RTT_STDDEV            = [self doubleToString:self.RTT_STDDEV]
//    Received_Packets      = [self intToString:self.Received_packets]
//    Lost_packet           = [self intToString:self.Lost_packet]
//    Model                 = [SKGlobalMethods getDeviceModel]
//    Manufacturer          = @"Apple"
//    OS_Type               = [[UIDevice currentDevice] systemName]
//    OS_Version            = [[UIDevice currentDevice] systemVersion]
//    Network_Type          = [SKGlobalMethods getNetWorkTechName]
//    Phone_Type            = [SKGlobalMethods getDeviceModel]
//    Connected             = @"TRUE"
//    Active_Network_Type   = [SKGlobalMethods getConnectionResultString:(ConnectionStatus)[[SKAAppDelegate getAppDelegate] amdGetConnectionStatus]]
//    Network_Operator_Name = [SKGlobalMethods getCarrierName]
//    Network_Operator_Code = [SKGlobalMethods getSimOperatorCodeMCCAndMNC]
//    SIM_Operator_Name     = [SKGlobalMethods getCarrierName]
//    SIM_Operator_Code     = [SKGlobalMethods getSimOperatorCodeMCCAndMNC]
//    Roaming               = STR_NA
//    Total_TX_Bytes        = @""
//    Mobile_TX_Bytes       = @""
//    APP_TX_Bytes          = @""
//    Total_RX_Bytes        = @""
//    Mobile_RX_Bytes       = @""
//    APP_RX_Bytes          = @""
//    Duration              = @""
//    Location_Type         = [SKGlobalMethods getNetworkOrGps]
//    Longitude             = [self doubleToString:longitude]
//    Latitude              = [self doubleToString:latitude]
//    Accuracy              = [self doubleToString:accuracy]
//    LTE_RSSI              = @""
//    LTE_CellID            = @""
//    GSM_RSSI              = @""
//    GSM_CellID            = @""
//    CDMA_RSSI             = @""
//    CDMA_BSID             = @""
//    EVDO_RSSI             = @""
    
}

#pragma mark - save tsv

- (NSString*)getNewTsvFilePath
{
    NSString *docPath = [SKAAppDelegate tsvDirectory];
    
    NSString *dateStr = [SKGlobalMethods yyyyMMdd_HHmmssStringFormDate:[SKCore getToday]];
    NSString *deviceModel = [SKGlobalMethods getDeviceModel];
    NSString *uuidForVendor = [[[UIDevice currentDevice] identifierForVendor] UUIDString];
    NSString *fileName = [NSString stringWithFormat:@"%@_%@_%@", dateStr, uuidForVendor, deviceModel];
    
    return [docPath stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.tsv", fileName]];
}

- (BOOL) doSaveTsv:(NSString*)tsvString
{
    NSString *path = [self getNewTsvFilePath];
    NSError *error = nil;
    if ([tsvString writeToFile:path atomically:YES encoding:NSUTF8StringEncoding error:&error])
    {
        return YES;
    }
    else
    {
        [FTPLogger writeLogToFile:[NSString stringWithFormat:@"TSV: <ERROR>, save TSV file error\n    error = %@\n", error]];
        return NO;
    }
}

#pragma mark - upload tsv to ftp
-(void)doUploadTsvToFtp
{
    NSString *tsvDirectory = [SKAAppDelegate tsvDirectory];
    NSError *error = nil;
    NSArray *tsvFiles = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:tsvDirectory error:&error];
    
    if (nil == error)
    {
        if (tsvFiles != nil && tsvFiles.count > 0)
        {
            NSString *uuidForVendor = [[[UIDevice currentDevice] identifierForVendor] UUIDString];
            NSString *remoteDirectoryName = [uuidForVendor stringByAppendingString:@"/"];
            
            [FTPLogger writeLogToFile:@"TSV: init FTP request manager, add directoryCreation to request queue\n"];
            [self _setupManager];
            [self.requestsManager addRequestForCreateDirectoryAtPath:remoteDirectoryName];
            
            for (NSString *fileName in tsvFiles )
            {
                NSString *pathToFile = [tsvDirectory stringByAppendingPathComponent:fileName];
                NSString *remotePath = [remoteDirectoryName stringByAppendingString:fileName];
                
                [FTPLogger writeLogToFile:[NSString stringWithFormat:@"TSV: add TSV fileUpload to request queue\n    File Name = %@\n", fileName]];
                [self.requestsManager addRequestForUploadFileAtLocalPath:pathToFile toRemotePath:remotePath];
            }
            
            [self.requestsManager startProcessingRequests];
        }
        else
        {
            [FTPLogger writeLogToFile:@"TSV: <ERROR>, no file on local TSV directory. TSV Process Stoped\n"];
            [self uploadFinishedWithError:YES];
        }
    }
    else
    {
        [FTPLogger writeLogToFile:@"TSV: <ERROR>, can not get tsv file list from local directory. TSV Process Stoped\n"];
        [self uploadFinishedWithError:YES];
    }
}

// Private Methods
- (void)_setupManager
{

    self.requestsManager = [[GRRequestsManager alloc] initWithHostname:FTP_ADDR_NORMAL_MODE_MANUAL
                                                                  user:FTP_USERNAME
                                                              password:FTP_PASSWORD];
    
    self.requestsManager.delegate = self;
}

-(void)uploadFinishedWithError:(BOOL)isError
{
    NSArray *resultArr = [[NSArray alloc] initWithObjects:@"TestResultDataCollector", [NSNumber numberWithBool:isError], nil];
    [[NSNotificationCenter defaultCenter] postNotificationName:FTPUploadCompliteNotification object:resultArr];
}

#pragma mark - GRRequestsManagerDelegate
                            
- (void)requestsManager:(id<GRRequestsManagerProtocol>)requestsManager didScheduleRequest:(id<GRRequestProtocol>)request
{
    // do nothing
}

- (void)requestsManager:(id<GRRequestsManagerProtocol>)requestsManager didCompleteCreateDirectoryRequest:(id<GRRequestProtocol>)request
{
    // do nothing
}

- (void)requestsManager:(id<GRRequestsManagerProtocol>)requestsManager didCompleteUploadRequest:(id<GRDataExchangeRequestProtocol>)request
{
    NSString *uploadCompletedFilePath = [request localFilePath];

    if(uploadCompletedFilePath == nil || uploadCompletedFilePath.length == 0)
        return;

#ifdef DEBUG
    NSLog(@"uploadFileSuccess fileName=%@", [uploadCompletedFilePath lastPathComponent]);
#endif
    
    [FTPLogger writeLogToFile:[NSString stringWithFormat:@"TSV: upload to FTP success.\n    File Name = %@\n", [uploadCompletedFilePath lastPathComponent]]];
    
    if([[NSFileManager defaultManager] fileExistsAtPath:uploadCompletedFilePath])
    {
        [[NSFileManager defaultManager] removeItemAtPath:uploadCompletedFilePath error:NULL];
    }
}

- (void)requestsManager:(id<GRRequestsManagerProtocol>)requestsManager didFailRequest:(id<GRRequestProtocol>)request withError:(NSError *)error
{
#ifdef DEBUG
    NSLog(@"TestResultDataCollector didFailRequest:withError: \n %@", error);
#endif
    
    switch (error.code) {
        case 0:
        case kGRFTPServerUserNotLoggedIn:
        case kGRFTPClientCantOpenStream:
            [FTPLogger writeLogToFile:[NSString stringWithFormat:@"TSV: <ERROR>, FTP ERROR. TSV Process Stoped.\n    error = %@\n", error]];
            [requestsManager stopAndCancelAllRequests];
            break;
        case kGRFTPClientCantOverwriteDirectory:
            [FTPLogger writeLogToFile:@"TSV: <WARNING>, can't overwrite directory on ftp server.\n"];
            break;
        default:
            [FTPLogger writeLogToFile:[NSString stringWithFormat:@"TSV: <WARNING>, FTP ERROR.\n    error = %@\n", error]];
            break;
    }
}

- (void)requestsManagerDidCompleteQueue:(id<GRRequestsManagerProtocol>)requestsManager
{
         
    [FTPLogger writeLogToFile:@"\nTSV: TSV Process Done\n\n"];
    [self uploadFinishedWithError:NO];
}

#pragma mark - getter / setter
-(void)setM_max_DL_Throughput:(double)Max_DL_Throughput
{
    if(_Max_DL_Throughput < Max_DL_Throughput)
        _Max_DL_Throughput = Max_DL_Throughput;
}

-(void)setM_max_UL_Throughput:(double)Max_UL_Throughput
{
    if(_Max_UL_Throughput < Max_UL_Throughput)
        _Max_UL_Throughput = Max_UL_Throughput;
}




#pragma mark - etc

-(double)calculateAvgDoubleType:(NSMutableArray *)a_inputArr
{
    NSMutableArray *inputArr = [a_inputArr mutableCopy];
    
    if(inputArr == nil || inputArr.count == 0)
        return TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE;
    
    NSNumber *fail = [NSNumber numberWithDouble:TEST_RESULT_FAILED_VALUE_DOUBLE_TYPE];
    [inputArr removeObject:fail];
    if (inputArr.count == 0)
    {
        return TEST_RESULT_FAILED_VALUE_DOUBLE_TYPE;
    }
    
    double total = 0;
    for (NSNumber *temp in inputArr)
    {
        total += [temp doubleValue];
    }
    
    return total / inputArr.count;
}

-(int)calculateAvgIntType:(NSMutableArray *)a_inputArr
{
    NSMutableArray *inputArr = [a_inputArr mutableCopy];
    
    if(inputArr == nil || inputArr.count == 0)
        return TEST_RESULT_UNKNOW_VALUE_int_TYPE;
    
    NSNumber *fail = [NSNumber numberWithInt:TEST_RESULT_FAILED_VALUE_int_TYPE];
    [inputArr removeObject:fail];
    if (inputArr.count == 0)
    {
        return TEST_RESULT_FAILED_VALUE_int_TYPE;
    }
    
    int total = 0;
    for (NSNumber *temp in inputArr) {
        total += [temp intValue];
    }
    
    return total / inputArr.count;
}

-(NSUInteger)calculateAvgNSUIntegerType:(NSMutableArray *)a_inputArr
{
    NSMutableArray *inputArr = [a_inputArr mutableCopy];
    
    if(inputArr == nil || inputArr.count == 0)
        return TEST_RESULT_UNKNOW_VALUE_NSUInteger_TYPE;
    
    NSNumber *fail = [NSNumber numberWithUnsignedInteger:TEST_RESULT_FAILED_VALUE_NSUInteger_TYPE];
    [inputArr removeObject:fail];
    if (inputArr.count == 0)
    {
        return TEST_RESULT_FAILED_VALUE_NSUInteger_TYPE;
    }
    
    NSUInteger total = 0;
    for (NSNumber *temp in inputArr) {
        total += [temp unsignedIntegerValue];
    }
    
    return total / inputArr.count;
}

-(NSString *)getTestResult:(NSMutableArray*)a_inputArr
{
    if (a_inputArr == nil || a_inputArr.count == 0)
        return STR_FAIL;
    
    NSString *s = STR_SUCCESS;
    
    if([a_inputArr containsObject:s])
        return STR_SUCCESS;
    else
        return STR_FAIL;
}

-(NSString *)doubleToString:(double)a_dbl
{
    if (a_dbl == TEST_RESULT_UNKNOW_VALUE_DOUBLE_TYPE)
        return STR_UNKNOWN;
    
    if (a_dbl == TEST_RESULT_FAILED_VALUE_DOUBLE_TYPE)
        return STR_FAIL;
    
    return [NSString stringWithFormat:@"%f", a_dbl];
}

-(NSString *)nsuintegerToString:(NSUInteger)a_uIntteger
{
    if (a_uIntteger == TEST_RESULT_UNKNOW_VALUE_NSUInteger_TYPE)
        return STR_UNKNOWN;
    if (a_uIntteger == TEST_RESULT_FAILED_VALUE_NSUInteger_TYPE)
        return STR_FAIL;
    
    return [NSString stringWithFormat:@"%ld", (long)a_uIntteger];
}

-(NSString *)intToString:(int)a_int
{
    if (a_int == TEST_RESULT_UNKNOW_VALUE_int_TYPE)
        return STR_UNKNOWN;
    if (a_int == TEST_RESULT_FAILED_VALUE_int_TYPE)
        return STR_FAIL;
    
    return [NSString stringWithFormat:@"%d", a_int];
}

-(void)initJapanOperator
{
    // http://en.wikipedia.org/wiki/Mobile_country_code#J
    
    m_japanOperatorDic = [[NSDictionary alloc] initWithObjectsAndKeys:
                          @"Y!Mobile", @"44000",
                          @"NTT DoCoMo", @"44001",
                          @"NTT DoCoMo", @"44002",
                          @"NTT DoCoMo", @"44003",
                          @"SoftBank", @"44004",
                          @"SoftBank", @"44006",
                          @"KDDI", @"44007",
                          @"KDDI", @"44008",
                          @"NTT DoCoMo", @"44009",
                          @"NTT DoCoMo", @"44010",
                          @"NTT DoCoMo", @"44011",
                          @"NTT DoCoMo", @"44012",
                          @"NTT DoCoMo", @"44013",
                          @"NTT DoCoMo", @"44014",
                          @"NTT DoCoMo", @"44015",
                          @"NTT DoCoMo", @"44016",
                          @"NTT DoCoMo", @"44017",
                          @"NTT DoCoMo", @"44018",
                          @"NTT DoCoMo", @"44019",
                          @"SoftBank", @"44020",
                          @"NTT DoCoMo", @"44021",
                          @"NTT DoCoMo", @"44022",
                          @"NTT DoCoMo", @"44023",
                          @"NTT DoCoMo", @"44024",
                          @"NTT DoCoMo", @"44025",
                          @"NTT DoCoMo", @"44026",
                          @"NTT DoCoMo", @"44027",
                          @"NTT DoCoMo", @"44028",
                          @"NTT DoCoMo", @"44029",
                          @"NTT DoCoMo", @"44030",
                          @"NTT DoCoMo", @"44031",
                          @"NTT DoCoMo", @"44032",
                          @"NTT DoCoMo", @"44033",
                          @"NTT DoCoMo", @"44034",
                          @"NTT DoCoMo", @"44035",
                          @"NTT DoCoMo", @"44036",
                          @"NTT DoCoMo", @"44037",
                          @"NTT DoCoMo", @"44038",
                          @"NTT DoCoMo", @"44039",
                          @"SoftBank", @"44040",
                          @"SoftBank", @"44041",
                          @"SoftBank", @"44042",
                          @"SoftBank", @"44043",
                          @"SoftBank", @"44044",
                          @"SoftBank", @"44045",
                          @"SoftBank", @"44046",
                          @"SoftBank", @"44047",
                          @"SoftBank", @"44048",
                          @"NTT DoCoMo", @"44049",
                          @"KDDI", @"44050",
                          @"KDDI", @"44051",
                          @"KDDI", @"44052",
                          @"KDDI", @"44053",
                          @"KDDI", @"44054",
                          @"KDDI", @"44055",
                          @"KDDI", @"44056",
                          @"NTT DoCoMo", @"44058",
                          @"NTT DoCoMo", @"44060",
                          @"NTT DoCoMo", @"44061",
                          @"NTT DoCoMo", @"44062",
                          @"NTT DoCoMo", @"44063",
                          @"NTT DoCoMo", @"44064",
                          @"NTT DoCoMo", @"44065",
                          @"NTT DoCoMo", @"44066",
                          @"NTT DoCoMo", @"44067",
                          @"NTT DoCoMo", @"44068",
                          @"NTT DoCoMo", @"44069",
                          @"au", @"44070",
                          @"KDDI", @"44071",
                          @"KDDI", @"44072",
                          @"KDDI", @"44073",
                          @"KDDI", @"44074",
                          @"KDDI", @"44075",
                          @"KDDI", @"44076",
                          @"KDDI", @"44077",
                          @"", @"44078",
                          @"KDDI", @"44079",
                          @"TU-KA", @"44080",
                          @"TU-KA", @"44081",
                          @"TU-KA", @"44082",
                          @"TU-KA", @"44083",
                          @"TU-KA", @"44084",
                          @"TU-KA", @"44085",
                          @"TU-KA", @"44086",
                          @"NTT DoCoMo", @"44087",
                          @"KDDI", @"44088",
                          @"KDDI", @"44089",
                          @"SoftBank", @"44090",
                          @"SoftBank", @"44092",
                          @"SoftBank", @"44093",
                          @"SoftBank", @"44094",
                          @"SoftBank", @"44095",
                          @"SoftBank", @"44096",
                          @"SoftBank", @"44097",
                          @"SoftBank", @"44098",
                          @"NTT DoCoMo", @"44099",
                          nil];
}
@end
