예제 #1
0
        /// <summary>
        /// Replace the current character with a random replacement
        /// </summary>
        /// <param name="c"></param>
        /// <returns></returns>
        public static Char RandomCharacterReplacement(Char character, Random random)
        {
            Char newChar;

            do
            {
                newChar = DataGenHelpers.GetRandomAlphaNumericCharacter(random);
            } while (newChar == character); // try again if we end up with the same character

            return(newChar);
        }
예제 #2
0
        /// <summary>
        /// Insert a random character in the passed in source
        /// </summary>
        /// <param name="soure"></param>
        /// <returns></returns>
        public String InsertRandomCharacter(String source)
        {
            // Ramdonly pick a spot to insert at.  Weigh the positional end point a bit heavier than the overall
            // length of the source string so we get some more chances that characters get appended
            // to the end of the string.
            Int32 pos = this.random.Next(0, source.Length + 1);

            // Pick a random character to insert
            Char c = DataGenHelpers.GetRandomAlphaNumericCharacter(random);

            StringBuilder sb = new StringBuilder(source);

            if (pos >= source.Length)
            {
                sb.Append(c);
            }
            else
            {
                sb.Insert(pos, c);
            }

            return(sb.ToString());
        }
예제 #3
0
        /// <summary>
        ///  Walks through the ConsumerTrust records and fuzzes them according to the configurable settings
        /// </summary>
        private void FuzzConsumerTrust(RandomNumberGenerator random)
        {
            Int32 fuzzCount        = 0;
            Int32 nicknameAttempts = 0;

            // do until we have reached the number of records that are supposed to be fuzzed
            while (fuzzCount < Properties.Settings.Default.TrustSideFuzzCount)
            {
                // Get a random Credit Card out of the TrustSideCreditCard table
                DataSetDebtDataGenerator.TrustCreditCardRow trustCreditCardRow =
                    this.dataSetDebtDataGen.TrustCreditCard[random.Next(this.dataSetDebtDataGen.TrustCreditCard.Count)];

                // Ensure that the credit card is a matching one. The reason we fuzz only match candidates is so we can compare
                // the ACTUAL results of the server's actual matching algorithm to our EXPECTED value of matches.
                if (!this.dataSetDebtDataGen.RealCreditCard[trustCreditCardRow.RealCreditCardId].IsMatched)
                {
                    continue;
                }

                // Ensure that the Credit Card we retrieved (OR its Consumer) has not already been fuzzed by either the
                // Common Fuzz heuristics or here in this method.  IF FuzzedFields is any value other than "none" the
                // record has been fuzzed.
                if (trustCreditCardRow.FuzzedFields != Convert.ToInt32(CreditCardFuzzedFields.None) ||
                    trustCreditCardRow.TrustSideConsumerRow.FuzzedFields != Convert.ToInt32(ConsumerFuzzedFields.None))
                {
                    continue;
                }

                // *** If we get to this point, we have a candiate for fuzzing ***

                // Get the Credit Card's corresponding consumer
                DataSetDebtDataGenerator.TrustSideConsumerRow trustConsumer = trustCreditCardRow.TrustSideConsumerRow;

                // fulfill the 'constant' requirements first
                if (!TrustNickNamePercentageIsMet(fuzzCount))
                {
                    // We're not always guaranteed that a particular consumer is going to have a shortened first name
                    // or nickname.  Therefore we use this clause to force a known percentage to be fulfilled by picking
                    // through and finding the consumer records that actually do have them.

                    string nickname;

                    if (TryGetRealConsumerNickName(trustConsumer.RealConsumerId, out nickname))
                    {
                        trustConsumer.FirstName    = nickname;
                        trustConsumer.FuzzedFields = Convert.ToInt32(ConsumerFuzzedFields.FirstName);
                        trustConsumer.FuzzMethod   = Convert.ToInt32(FuzzMethod.NicknameSubstitution);
                    }
                    else
                    {
                        // This consumer did not have a nickname so go get another one and try again

                        // We may not have enough first names to satisfy the nickname criteria. A 'reasonable enough' number
                        // of attempts is three times the size of the TrustSideConsumerTable.
                        // Note:  [skt] I've run across some seeds that cause this exception to be thrown.  This is relatively
                        //        rare.  The easiest thing to do is just pick another random seed and gen the data again.
                        if (++nicknameAttempts > this.dataSetDebtDataGen.TrustSideConsumer.Count * 3)
                        {
                            throw new SystemException(
                                      String.Format(
                                          " Data Generation Failed. Exceeded the number of valid attempts ({0}) to reach nickname percentage.",
                                          this.dataSetDebtDataGen.TrustSideConsumer.Count * 3));
                        }

                        continue;
                    }
                }
                else // fulfill the remaining fuzzCount with different variations of fuzzed data
                {
                    // roll the dice to see what gets fuzzzed
                    switch (random.Next(1, 7))
                    {
                    // one third of the time we will fuzz the SSN
                    case 1:
                    case 2:
                    {
                        // 30 percent of the time we fuzz the SSN, it will be character subtraction
                        if (random.Next(100).IsWithinRange(0, 29))
                        {
                            // flip a coin to determine whether or not we omit a middle character or one on the end
                            if (random.Next(100).IsWithinRange(0, 49))
                            {
                                // omit a character in the middle
                                FuzzSocialSecurityNumber(trustConsumer, FuzzMethod.MissingRandomMiddleCharacter, random);
                                trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.MissingRandomMiddleCharacter);
                            }
                            else
                            {
                                // omit an endpoint character: Flip a coin to determine which end
                                if (random.Next(100).IsWithinRange(0, 49))
                                {
                                    // first char
                                    FuzzSocialSecurityNumber(trustConsumer, FuzzMethod.MissingFirstCharacter, random);
                                    trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.MissingFirstCharacter);
                                }
                                else
                                {
                                    // last char
                                    FuzzSocialSecurityNumber(trustConsumer, FuzzMethod.MissingLastCharacter, random);
                                    trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.MissingLastCharacter);
                                }
                            }
                        }
                        // 70 percent of the time we will fat finger this field
                        else
                        {
                            // determine the fat-finger-technique
                            if (random.Next(100).IsWithinRange(0, 74))
                            {
                                // 'accidentally' swapping characters 75% of the time
                                FuzzSocialSecurityNumber(trustConsumer, FuzzMethod.AdjacentCharactersSwapped, random);
                                trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.AdjacentCharactersSwapped);
                            }
                            else
                            {
                                // adding an extra 'random' character 25% of the time
                                FuzzSocialSecurityNumber(trustConsumer, FuzzMethod.RandomCharacterAdded, random);
                                trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.RandomCharacterAdded);
                            }
                        }

                        // mark that the SSN was fuzzed
                        trustConsumer.FuzzedFields = Convert.ToInt32(ConsumerFuzzedFields.SocialSecurityNumber);
                        break;
                    }

                    // one third of the time we will fuzz the matched consumer's CCN
                    case 3:
                    case 4:
                    {
                        // 25 percent of the time we fuzz the CCN, it will be character subtraction
                        if (random.Next(100).IsWithinRange(0, 24))
                        {
                            // flip a coin to determine whether or not we omit a middle character or one on the end
                            if (random.Next(100).IsWithinRange(0, 49))
                            {
                                // omit a character in the middle
                                FuzzCreditCardNumber(trustCreditCardRow, FuzzMethod.MissingRandomMiddleCharacter, random);
                                trustCreditCardRow.FuzzMethod = Convert.ToInt32(FuzzMethod.MissingRandomMiddleCharacter);
                            }
                            else
                            {
                                // omit an endpoint character: Flip a coin to determine which end
                                if (random.Next(100).IsWithinRange(0, 49))
                                {
                                    // first char
                                    FuzzCreditCardNumber(trustCreditCardRow, FuzzMethod.MissingFirstCharacter, random);
                                    trustCreditCardRow.FuzzMethod = Convert.ToInt32(FuzzMethod.MissingFirstCharacter);
                                }
                                else
                                {
                                    // last char
                                    FuzzCreditCardNumber(trustCreditCardRow, FuzzMethod.MissingLastCharacter, random);
                                    trustCreditCardRow.FuzzMethod = Convert.ToInt32(FuzzMethod.MissingLastCharacter);
                                }
                            }
                        }

                        // 75 percent of the time we will fat finger this field:
                        else
                        {
                            // determine the fat-finger-technique
                            if (random.Next(100).IsWithinRange(0, 74))
                            {
                                // 'accidentally' swapping characters 75% of the time
                                FuzzCreditCardNumber(trustCreditCardRow, FuzzMethod.AdjacentCharactersSwapped, random);
                                trustCreditCardRow.FuzzMethod = Convert.ToInt32(FuzzMethod.AdjacentCharactersSwapped);
                            }
                            else
                            {
                                // adding an extra 'random' character 25% of the time
                                FuzzCreditCardNumber(trustCreditCardRow, FuzzMethod.RandomCharacterAdded, random);
                                trustCreditCardRow.FuzzMethod = Convert.ToInt32(FuzzMethod.RandomCharacterAdded);
                            }
                        }

                        // mark the credit card to say that its CCN has been fuzzed
                        trustCreditCardRow.FuzzedFields = Convert.ToInt32(CreditCardFuzzedFields.CreditCardNumber);

                        break;
                    }

                    // one sixth of the time we will fuzz both
                    case 5:
                    {
                        // fat fingering - accidentally swapping characters
                        FuzzSocialSecurityNumber(trustConsumer, FuzzMethod.AdjacentCharactersSwapped, random);
                        FuzzCreditCardNumber(trustCreditCardRow, FuzzMethod.AdjacentCharactersSwapped, random);

                        // mark that both SSN and CCN were fuzzed
                        trustConsumer.FuzzedFields = Convert.ToInt32(ConsumerFuzzedFields.SocialSecurityNumber);
                        trustConsumer.FuzzMethod   = Convert.ToInt32(FuzzMethod.AdjacentCharactersSwapped);

                        trustCreditCardRow.FuzzedFields = Convert.ToInt32(CreditCardFuzzedFields.CreditCardNumber);
                        trustCreditCardRow.FuzzMethod   = Convert.ToInt32(FuzzMethod.AdjacentCharactersSwapped);

                        break;
                    }

                    // One-sixth of the time we will muck with the consumer's name.
                    case 6:
                    {
                        // If both FN/LN fields are empty...
                        if (trustConsumer.FirstName == null && trustConsumer.LastName == null)
                        {
                            // add a couple random characters into the LN field
                            trustConsumer.LastName  = Convert.ToString(DataGenHelpers.GetRandomAlphaNumericCharacter(random));
                            trustConsumer.LastName += Convert.ToString(DataGenHelpers.GetRandomAlphaNumericCharacter(random));

                            // mark that the last name has been fuzzed with a whole new name
                            trustConsumer.FuzzedFields = Convert.ToInt32(ConsumerFuzzedFields.LastName);
                            trustConsumer.FuzzMethod   = Convert.ToInt32(FuzzMethod.CompletelyNewValue);
                        }

                        // Flip a 3-sided coin (http://www.statisticool.com/3sided.htm) to determine how we muck with the name
                        switch (random.Next(1, 4))
                        {
                        case 1:             // First Name Muck
                        {
                            if (trustConsumer.FirstName == null)
                            {
                                // If the field is empty, add a random character
                                trustConsumer.FirstName =
                                    Convert.ToString(DataGenHelpers.GetRandomAlphaNumericCharacter(random));
                                trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.CompletelyNewValue);
                            }
                            else if (trustConsumer.FirstName.Length == 1)
                            {
                                // FN is already one char in length, so swap it with another (i.e, a screwed-up first initial)
                                trustConsumer.FirstName =
                                    Convert.ToString(DataGenHelpers.RandomCharacterReplacement(trustConsumer.FirstName[0], random));
                                trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.CompletelyNewValue);
                            }
                            else
                            {
                                // first name is > 1 characters, strip it down to just one
                                trustConsumer.FirstName  = trustConsumer.FirstName.Substring(0, 1);
                                trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.StrippedDownToFirstCharacterOnly);
                            }
                            // mark that the firstname has been fuzzed
                            trustConsumer.FuzzedFields = Convert.ToInt32(ConsumerFuzzedFields.FirstName);
                            break;
                        }

                        case 2:             // Last Name Muck
                        {
                            // Replace the last name altogether (someone got married/divorced/etc...)

                            String newLastName = this.lastNameList[random.Next(0, this.lastNameList.Count - 1)];
                            while (newLastName == trustConsumer.LastName)
                            {
                                // if we happen to get the same name, try again
                                newLastName = this.lastNameList[random.Next(0, this.lastNameList.Count - 1)];
                            }

                            // Flip a coin to see if we hyphenate or replace it altogether
                            //   [skt] can refine this by gender if the need arises (put a gender column in the consumer tables)
                            if (random.Next(100).IsWithinRange(0, 49))
                            {
                                // hyphenate
                                trustConsumer.LastName = String.Format("{0}-{1}", trustConsumer.LastName,
                                                                       newLastName[0] + newLastName.Substring(1, newLastName.Length - 1).ToLower());
                                trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.CompletelyNewValueHyphenated);
                            }
                            else
                            {
                                // new name, no hyphenation
                                trustConsumer.LastName   = newLastName.ToLower();
                                trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.CompletelyNewValue);
                            }

                            // mark that the last name has been fuzzed with a whole new name
                            trustConsumer.FuzzedFields = Convert.ToInt32(ConsumerFuzzedFields.LastName);
                            break;
                        }

                        case 3:             // swap FN and LN
                        {
                            string tmp = trustConsumer.FirstName;
                            trustConsumer.FirstName = trustConsumer.LastName;
                            trustConsumer.LastName  = tmp;

                            // mark that both FN and LN were fuzzed
                            trustConsumer.FuzzedFields = Convert.ToInt32(ConsumerFuzzedFields.FirstName) |
                                                         Convert.ToInt32(ConsumerFuzzedFields.LastName);

                            trustConsumer.FuzzMethod = Convert.ToInt32(FuzzMethod.Swapped);

                            break;
                        }
                        }

                        break;
                    }
                    }
                }

                // increment the count of how many records we fuzzed
                ++fuzzCount;
            }
        }
예제 #4
0
        /// <summary>
        /// Fuzz the passed in SSN string
        /// </summary>
        /// <param name="socialSecurityNumber"></param>
        /// <returns></returns>
        private string FuzzSocialSecurityNumber(String socialSecurityNumber, FuzzMethod fuzzMethod, Random random)
        {
            string fuzzedSsn = null;

            // if all the characters in the string are the same, this is essentially a no-op
            if (socialSecurityNumber.HasAllTheSameCharacters())
            {
                return(socialSecurityNumber);
            }

            // instance of the random class used for mixing up the list.
            if (random == null)
            {
                random = new Random(DateTime.Now.Millisecond);
            }

            // remove the dashes in the ssn
            char[] rawSsn = DataGenHelpers.GetRawSsn(socialSecurityNumber).ToCharArray();

            // Initialize string fuzzer
            StringFuzzer fuzzer = new StringFuzzer(random);

            // Fuzz Accordingly:
            switch (fuzzMethod)
            {
            case (FuzzMethod.AdjacentCharactersSwapped):
            {
                // Starting from a random position in a string, swap two unique and adjacent characters in that string.
                // If the string happens to have all the same characters, there is not much we can do
                fuzzer    = new StringFuzzer(random);
                fuzzedSsn = fuzzer.SwapTwoUniqueAdjacentCharacters(rawSsn);
                fuzzedSsn = DataGenHelpers.BuildFormattedSsn(fuzzedSsn);
                break;
            }

            case (FuzzMethod.MissingRandomMiddleCharacter):
            {
                // simply remove a character from a random position within the SSN. The two end characters are preserved
                Char firstChar = rawSsn.First();
                Char lastChar  = rawSsn.Last();

                // delete a random character between the begining and end characters of the string
                String midSsn = fuzzer.DeleteRandomCharacter(new String(rawSsn, 1, rawSsn.Length - 2));

                // put the pieces back together again
                fuzzedSsn = String.Format("{0}{1}{2}", firstChar, midSsn, lastChar);
                fuzzedSsn = DataGenHelpers.BuildFormattedSsn(fuzzedSsn);
                break;
            }

            case (FuzzMethod.MissingFirstCharacter):
            {
                fuzzedSsn = socialSecurityNumber.Remove(0, 1);
                break;
            }

            case (FuzzMethod.MissingLastCharacter):
            {
                fuzzedSsn = socialSecurityNumber.Remove(socialSecurityNumber.Length - 1, 1);
                break;
            }

            case (FuzzMethod.RandomCharacterAdded):
            {
                fuzzedSsn = fuzzer.InsertRandomCharacter(socialSecurityNumber);
                break;
            }
            }

            return(fuzzedSsn);
        }