From 280356aaff018a2b33defe80d0c4c73c81883c44 Mon Sep 17 00:00:00 2001
From: "dhollowa@chromium.org"
 <dhollowa@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>
Date: Sat, 13 Feb 2010 02:58:20 +0000
Subject: Adding summary string generation for the AutoFill feature.

Includes a small modification to the generated resources, needed additional whitespace
in credit card summary.  Added summary generation to autofill_profile.* and modified
summary generation in credit_card.* to match.  credit_card.* modifications were largely
to use string16 instead of std::wstring.

Factored out common unit testing utilities into autofill_common_unittest.*, and added
unit tests for summary string generation for credit_card.* and autofill_profile.*.

BUG=35551
TEST=unit_tests --gtest_filter=AutoFillProfileTest.*:CreditCardTest.*


Review URL: http://codereview.chromium.org/606031

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@39002 0039d316-1c4b-4281-b951-d872f2087c98
---
 chrome/app/generated_resources.grd                 |   8 +-
 .../browser/autofill/autofill_address_model_mac.mm | 103 ++++-------
 .../browser/autofill/autofill_common_unittest.cc   |  55 ++++++
 chrome/browser/autofill/autofill_common_unittest.h |  36 ++++
 .../autofill/autofill_credit_card_model_mac.mm     |  27 +--
 chrome/browser/autofill/autofill_profile.cc        |  45 +++++
 chrome/browser/autofill/autofill_profile.h         |  10 ++
 .../browser/autofill/autofill_profile_unittest.cc  | 191 +++++++++++++++++++++
 chrome/browser/autofill/credit_card.cc             |  25 ++-
 chrome/browser/autofill/credit_card.h              |   2 +-
 chrome/browser/autofill/credit_card_unittest.cc    | 113 ++++++++++++
 .../autofill/personal_data_manager_unittest.cc     |  62 ++-----
 chrome/chrome_tests.gypi                           |   4 +
 13 files changed, 536 insertions(+), 145 deletions(-)
 create mode 100644 chrome/browser/autofill/autofill_common_unittest.cc
 create mode 100644 chrome/browser/autofill/autofill_common_unittest.h
 create mode 100644 chrome/browser/autofill/autofill_profile_unittest.cc
 create mode 100644 chrome/browser/autofill/credit_card_unittest.cc

(limited to 'chrome')

diff --git a/chrome/app/generated_resources.grd b/chrome/app/generated_resources.grd
index 535dde8..050d147 100644
--- a/chrome/app/generated_resources.grd
+++ b/chrome/app/generated_resources.grd
@@ -4982,7 +4982,7 @@ Keep your key file in a safe place. You will need it to create new versions of y
       <message name="IDS_CREDIT_CARD_NUMBER_PREVIEW_FORMAT"
                desc="Credit card preview format">
         <ph name="OBFUSCATED_CC_NUMBER">$1<ex>************1234</ex>
-        </ph>, Exp:<ph name="CC_EXPIRATION_DATE">$2<ex>03/2020</ex>
+        </ph>, Exp: <ph name="CC_EXPIRATION_DATE">$2<ex>03/2020</ex>
         </ph>
       </message>
       <message name="IDS_AUTOFILL_DIALOG_LABEL" desc="The label of the Label entry.">
@@ -6855,12 +6855,12 @@ Keep your key file in a safe place. You will need it to create new versions of y
       </message>
       <message name="IDS_NETWORK_SELECTION_TITLE" desc="Welcome title shown on network selection screen">
         Welcome to <ph name="PRODUCT_NAME">$1<ex>Chrome OS</ex></ph>
-      </message>      
+      </message>
       <message name="IDS_NETWORK_SELECTION_SELECT" desc="Label for network selection dropdown">
         Please select a network:
-      </message>            
+      </message>
       <message name="IDS_LOGIN_TITLE">
-        Sign in with your Google account 
+        Sign in with your Google account
       </message>
       <message name="IDS_LOGIN_USERNAME">
         Username:
diff --git a/chrome/browser/autofill/autofill_address_model_mac.mm b/chrome/browser/autofill/autofill_address_model_mac.mm
index 265b055..2e70050 100644
--- a/chrome/browser/autofill/autofill_address_model_mac.mm
+++ b/chrome/browser/autofill/autofill_address_model_mac.mm
@@ -46,39 +46,39 @@
   if ((self = [super init])) {
     [self setLabel:SysUTF16ToNSString(profile.Label())];
     [self setFirstName:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(NAME_FIRST)))];
+        profile.GetFieldText(AutoFillType(NAME_FIRST)))];
     [self setMiddleName:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(NAME_MIDDLE)))];
+        profile.GetFieldText(AutoFillType(NAME_MIDDLE)))];
     [self setLastName:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(NAME_LAST)))];
+        profile.GetFieldText(AutoFillType(NAME_LAST)))];
     [self setEmail:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(EMAIL_ADDRESS)))];
+        profile.GetFieldText(AutoFillType(EMAIL_ADDRESS)))];
     [self setCompanyName:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(COMPANY_NAME)))];
+        profile.GetFieldText(AutoFillType(COMPANY_NAME)))];
     [self setAddressLine1:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(ADDRESS_HOME_LINE1)))];
+        profile.GetFieldText(AutoFillType(ADDRESS_HOME_LINE1)))];
     [self setAddressLine2:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(ADDRESS_HOME_LINE2)))];
+        profile.GetFieldText(AutoFillType(ADDRESS_HOME_LINE2)))];
     [self setCity:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(ADDRESS_HOME_CITY)))];
+        profile.GetFieldText(AutoFillType(ADDRESS_HOME_CITY)))];
     [self setState:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(ADDRESS_HOME_STATE)))];
+        profile.GetFieldText(AutoFillType(ADDRESS_HOME_STATE)))];
     [self setZip:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(ADDRESS_HOME_ZIP)))];
+        profile.GetFieldText(AutoFillType(ADDRESS_HOME_ZIP)))];
     [self setCountry:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(ADDRESS_HOME_COUNTRY)))];
+        profile.GetFieldText(AutoFillType(ADDRESS_HOME_COUNTRY)))];
     [self setPhoneCountryCode:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(PHONE_HOME_COUNTRY_CODE)))];
+        profile.GetFieldText(AutoFillType(PHONE_HOME_COUNTRY_CODE)))];
     [self setPhoneAreaCode:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(PHONE_HOME_CITY_CODE)))];
+        profile.GetFieldText(AutoFillType(PHONE_HOME_CITY_CODE)))];
     [self setPhoneNumber:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(PHONE_HOME_NUMBER)))];
+        profile.GetFieldText(AutoFillType(PHONE_HOME_NUMBER)))];
     [self setFaxCountryCode:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(PHONE_FAX_COUNTRY_CODE)))];
+        profile.GetFieldText(AutoFillType(PHONE_FAX_COUNTRY_CODE)))];
     [self setFaxAreaCode:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(PHONE_FAX_CITY_CODE)))];
+        profile.GetFieldText(AutoFillType(PHONE_FAX_CITY_CODE)))];
     [self setFaxNumber:SysUTF16ToNSString(
-          profile.GetFieldText(AutoFillType(PHONE_FAX_NUMBER)))];
+        profile.GetFieldText(AutoFillType(PHONE_FAX_NUMBER)))];
   }
   return self;
 }
@@ -106,76 +106,49 @@
 }
 
 - (NSString*)summary {
-  // Bindings may set these to nil.  We normalize here to @"".
-  if (firstName_ == nil)
-    firstName_ = @"";
-  if (lastName_ == nil)
-    lastName_ = @"";
-  if (addressLine1_ == nil)
-    addressLine1_ = @"";
-
-  BOOL haveFirstName = [firstName_ length] > 0;
-  BOOL haveLastName = [lastName_ length] > 0;
-  BOOL haveAddress = [addressLine1_ length] > 0;
-
-  NSString* nameSeparator = (haveFirstName && haveLastName) ?
-      l10n_util::GetNSString(IDS_AUTOFILL_DIALOG_ADDRESS_NAME_SEPARATOR) :
-      @"";
-  NSString* nameFormat =
-      l10n_util::GetNSStringF(IDS_AUTOFILL_DIALOG_ADDRESS_SUMMARY_NAME_FORMAT,
-                          base::SysNSStringToUTF16(firstName_),
-                          base::SysNSStringToUTF16(nameSeparator),
-                          base::SysNSStringToUTF16(lastName_));
-  NSString* summarySeparator = (haveFirstName || haveLastName) && haveAddress ?
-      l10n_util::GetNSString(IDS_AUTOFILL_DIALOG_ADDRESS_SUMMARY_SEPARATOR) :
-      @"";
-  NSString* summaryFormat =
-      l10n_util::GetNSStringF(IDS_AUTOFILL_DIALOG_ADDRESS_SUMMARY_FORMAT,
-                         base::SysNSStringToUTF16(nameFormat),
-                         base::SysNSStringToUTF16(summarySeparator),
-                         base::SysNSStringToUTF16(addressLine1_));
-
-  return summaryFormat;
+  // Create a temporary |profile| to generate summary string.
+  AutoFillProfile profile(string16(), 0);
+  [self copyModelToProfile:&profile];
+  return SysUTF16ToNSString(profile.PreviewSummary());
 }
 
 - (void)copyModelToProfile:(AutoFillProfile*)profile {
   DCHECK(profile);
   profile->set_label(base::SysNSStringToUTF16([self label]));
-
   profile->SetInfo(AutoFillType(NAME_FIRST),
-                   base::SysNSStringToUTF16([self firstName]));
+      base::SysNSStringToUTF16([self firstName]));
   profile->SetInfo(AutoFillType(NAME_MIDDLE),
-                   base::SysNSStringToUTF16([self middleName]));
+      base::SysNSStringToUTF16([self middleName]));
   profile->SetInfo(AutoFillType(NAME_LAST),
-                   base::SysNSStringToUTF16([self lastName]));
+      base::SysNSStringToUTF16([self lastName]));
   profile->SetInfo(AutoFillType(EMAIL_ADDRESS),
-                   base::SysNSStringToUTF16([self email]));
+      base::SysNSStringToUTF16([self email]));
   profile->SetInfo(AutoFillType(COMPANY_NAME),
-                   base::SysNSStringToUTF16([self companyName]));
+      base::SysNSStringToUTF16([self companyName]));
   profile->SetInfo(AutoFillType(ADDRESS_HOME_LINE1),
-                   base::SysNSStringToUTF16([self addressLine1]));
+      base::SysNSStringToUTF16([self addressLine1]));
   profile->SetInfo(AutoFillType(ADDRESS_HOME_LINE2),
-                   base::SysNSStringToUTF16([self addressLine2]));
+      base::SysNSStringToUTF16([self addressLine2]));
   profile->SetInfo(AutoFillType(ADDRESS_HOME_CITY),
-                   base::SysNSStringToUTF16([self city]));
+      base::SysNSStringToUTF16([self city]));
   profile->SetInfo(AutoFillType(ADDRESS_HOME_STATE),
-                   base::SysNSStringToUTF16([self state]));
+      base::SysNSStringToUTF16([self state]));
   profile->SetInfo(AutoFillType(ADDRESS_HOME_ZIP),
-                   base::SysNSStringToUTF16([self zip]));
+      base::SysNSStringToUTF16([self zip]));
   profile->SetInfo(AutoFillType(ADDRESS_HOME_COUNTRY),
-                   base::SysNSStringToUTF16([self country]));
+      base::SysNSStringToUTF16([self country]));
   profile->SetInfo(AutoFillType(PHONE_HOME_COUNTRY_CODE),
-                   base::SysNSStringToUTF16([self phoneCountryCode]));
+      base::SysNSStringToUTF16([self phoneCountryCode]));
   profile->SetInfo(AutoFillType(PHONE_HOME_CITY_CODE),
-                   base::SysNSStringToUTF16([self phoneAreaCode]));
+      base::SysNSStringToUTF16([self phoneAreaCode]));
   profile->SetInfo(AutoFillType(PHONE_HOME_NUMBER),
-                   base::SysNSStringToUTF16([self phoneNumber]));
+      base::SysNSStringToUTF16([self phoneNumber]));
   profile->SetInfo(AutoFillType(PHONE_FAX_COUNTRY_CODE),
-                   base::SysNSStringToUTF16([self faxCountryCode]));
+      base::SysNSStringToUTF16([self faxCountryCode]));
   profile->SetInfo(AutoFillType(PHONE_FAX_CITY_CODE),
-                   base::SysNSStringToUTF16([self faxAreaCode]));
+      base::SysNSStringToUTF16([self faxAreaCode]));
   profile->SetInfo(AutoFillType(PHONE_FAX_NUMBER),
-                   base::SysNSStringToUTF16([self faxNumber]));
+      base::SysNSStringToUTF16([self faxNumber]));
 }
 
 @end
diff --git a/chrome/browser/autofill/autofill_common_unittest.cc b/chrome/browser/autofill/autofill_common_unittest.cc
new file mode 100644
index 0000000..771d07a
--- /dev/null
+++ b/chrome/browser/autofill/autofill_common_unittest.cc
@@ -0,0 +1,55 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chrome/browser/autofill/autofill_common_unittest.h"
+#include "chrome/browser/autofill/autofill_profile.h"
+#include "chrome/browser/autofill/credit_card.h"
+
+namespace autofill_unittest {
+
+void SetProfileInfo(AutoFillProfile* profile,
+    const char* label, const char* first_name, const char* middle_name,
+    const char* last_name, const char* email, const char* company,
+    const char* address1, const char* address2, const char* city,
+    const char* state, const char* zipcode, const char* country,
+    const char* phone, const char* fax) {
+  profile->set_label(ASCIIToUTF16(label));
+  profile->SetInfo(AutoFillType(NAME_FIRST), ASCIIToUTF16(first_name));
+  profile->SetInfo(AutoFillType(NAME_MIDDLE), ASCIIToUTF16(middle_name));
+  profile->SetInfo(AutoFillType(NAME_LAST), ASCIIToUTF16(last_name));
+  profile->SetInfo(AutoFillType(EMAIL_ADDRESS), ASCIIToUTF16(email));
+  profile->SetInfo(AutoFillType(COMPANY_NAME), ASCIIToUTF16(company));
+  profile->SetInfo(AutoFillType(ADDRESS_HOME_LINE1), ASCIIToUTF16(address1));
+  profile->SetInfo(AutoFillType(ADDRESS_HOME_LINE2), ASCIIToUTF16(address2));
+  profile->SetInfo(AutoFillType(ADDRESS_HOME_CITY), ASCIIToUTF16(city));
+  profile->SetInfo(AutoFillType(ADDRESS_HOME_STATE), ASCIIToUTF16(state));
+  profile->SetInfo(AutoFillType(ADDRESS_HOME_ZIP), ASCIIToUTF16(zipcode));
+  profile->SetInfo(AutoFillType(ADDRESS_HOME_COUNTRY), ASCIIToUTF16(country));
+  profile->SetInfo(AutoFillType(PHONE_HOME_NUMBER), ASCIIToUTF16(phone));
+  profile->SetInfo(AutoFillType(PHONE_FAX_NUMBER), ASCIIToUTF16(fax));
+}
+
+void SetCreditCardInfo(CreditCard* credit_card,
+    const char* label, const char* name_on_card, const char* type,
+    const char* card_number, const char* expiration_month,
+    const char* expiration_year, const char* verification_code,
+    const char* billing_address, const char* shipping_address) {
+  credit_card->set_label(ASCIIToUTF16(label));
+  credit_card->SetInfo(AutoFillType(CREDIT_CARD_NAME),
+                   ASCIIToUTF16(name_on_card));
+  credit_card->SetInfo(AutoFillType(CREDIT_CARD_TYPE), ASCIIToUTF16(type));
+  credit_card->SetInfo(AutoFillType(CREDIT_CARD_NUMBER),
+                   ASCIIToUTF16(card_number));
+  credit_card->SetInfo(AutoFillType(CREDIT_CARD_EXP_MONTH),
+                   ASCIIToUTF16(expiration_month));
+  credit_card->SetInfo(AutoFillType(CREDIT_CARD_EXP_4_DIGIT_YEAR),
+                   ASCIIToUTF16(expiration_year));
+  credit_card->SetInfo(AutoFillType(CREDIT_CARD_VERIFICATION_CODE),
+                   ASCIIToUTF16(verification_code));
+  credit_card->set_billing_address(ASCIIToUTF16(billing_address));
+  credit_card->set_shipping_address(ASCIIToUTF16(shipping_address));
+}
+
+}  // namespace
+
diff --git a/chrome/browser/autofill/autofill_common_unittest.h b/chrome/browser/autofill/autofill_common_unittest.h
new file mode 100644
index 0000000..b4de512
--- /dev/null
+++ b/chrome/browser/autofill/autofill_common_unittest.h
@@ -0,0 +1,36 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef CHROME_BROWSER_AUTOFILL_AUTOFILL_COMMON_UNITTEST_H_
+#define CHROME_BROWSER_AUTOFILL_AUTOFILL_COMMON_UNITTEST_H_
+
+class AutoFillProfile;
+class CreditCard;
+
+// Common utilities shared amongst autofill unit tests.
+namespace autofill_unittest {
+
+// A unit testing utility that is common to a number of the autofill unit
+// tests.  |SetProfileInfo| provides a quick way to populate a profile with
+// c-strings.
+void SetProfileInfo(AutoFillProfile* profile,
+    const char* label, const char* first_name, const char* middle_name,
+    const char* last_name, const char* email, const char* company,
+    const char* address1, const char* address2, const char* city,
+    const char* state, const char* zipcode, const char* country,
+    const char* phone, const char* fax);
+
+// A unit testing utility that is common to a number of the autofill unit
+// tests.  |SetCreditCardInfo| provides a quick way to populate a credit card
+// with c-strings.
+void SetCreditCardInfo(CreditCard* credit_card,
+    const char* label, const char* name_on_card, const char* type,
+    const char* card_number, const char* expiration_month,
+    const char* expiration_year, const char* verification_code,
+    const char* billing_address, const char* shipping_address);
+
+}  // namespace
+
+#endif  // CHROME_BROWSER_AUTOFILL_AUTOFILL_COMMON_UNITTEST_H_
+
diff --git a/chrome/browser/autofill/autofill_credit_card_model_mac.mm b/chrome/browser/autofill/autofill_credit_card_model_mac.mm
index f59cff9..a2074b5 100644
--- a/chrome/browser/autofill/autofill_credit_card_model_mac.mm
+++ b/chrome/browser/autofill/autofill_credit_card_model_mac.mm
@@ -37,15 +37,15 @@
   if ((self = [super init])) {
     [self setLabel:SysUTF16ToNSString(creditCard.Label())];
     [self setNameOnCard:SysUTF16ToNSString(
-          creditCard.GetFieldText(AutoFillType(CREDIT_CARD_NAME)))];
+        creditCard.GetFieldText(AutoFillType(CREDIT_CARD_NAME)))];
     [self setCreditCardNumber:SysUTF16ToNSString(
-          creditCard.GetFieldText(AutoFillType(CREDIT_CARD_NUMBER)))];
+        creditCard.GetFieldText(AutoFillType(CREDIT_CARD_NUMBER)))];
     [self setExpirationMonth:SysUTF16ToNSString(
-          creditCard.GetFieldText(AutoFillType(CREDIT_CARD_EXP_MONTH)))];
+        creditCard.GetFieldText(AutoFillType(CREDIT_CARD_EXP_MONTH)))];
     [self setExpirationYear:SysUTF16ToNSString(
-          creditCard.GetFieldText(AutoFillType(CREDIT_CARD_EXP_4_DIGIT_YEAR)))];
+        creditCard.GetFieldText(AutoFillType(CREDIT_CARD_EXP_4_DIGIT_YEAR)))];
     [self setCvcCode:SysUTF16ToNSString(
-          creditCard.GetFieldText(AutoFillType(CREDIT_CARD_VERIFICATION_CODE)))];
+        creditCard.GetFieldText(AutoFillType(CREDIT_CARD_VERIFICATION_CODE)))];
   }
   return self;
 }
@@ -63,24 +63,25 @@
 }
 
 - (NSString*)summary {
-  // TODO(dhollowa): This has been pulled into cross platform code.
-  // Will hook up in separate CL.  See http://crbug.com/33029.
-  return @"";
+  // Create a temporary |creditCard| to generate summary string.
+  CreditCard creditCard(string16(), 0);
+  [self copyModelToCreditCard:&creditCard];
+  return SysUTF16ToNSString(creditCard.PreviewSummary());
 }
 
 - (void)copyModelToCreditCard:(CreditCard*)creditCard {
   DCHECK(creditCard);
   creditCard->set_label(base::SysNSStringToUTF16([self label]));
   creditCard->SetInfo(AutoFillType(CREDIT_CARD_NAME),
-        base::SysNSStringToUTF16([self nameOnCard]));
+      base::SysNSStringToUTF16([self nameOnCard]));
   creditCard->SetInfo(AutoFillType(CREDIT_CARD_NUMBER),
-        base::SysNSStringToUTF16([self creditCardNumber]));
+      base::SysNSStringToUTF16([self creditCardNumber]));
   creditCard->SetInfo(AutoFillType(CREDIT_CARD_EXP_MONTH),
-        base::SysNSStringToUTF16([self expirationMonth]));
+      base::SysNSStringToUTF16([self expirationMonth]));
   creditCard->SetInfo(AutoFillType(CREDIT_CARD_EXP_4_DIGIT_YEAR),
-        base::SysNSStringToUTF16([self expirationYear]));
+      base::SysNSStringToUTF16([self expirationYear]));
   creditCard->SetInfo(AutoFillType(CREDIT_CARD_VERIFICATION_CODE),
-        base::SysNSStringToUTF16([self cvcCode]));
+      base::SysNSStringToUTF16([self cvcCode]));
 }
 
 @end
diff --git a/chrome/browser/autofill/autofill_profile.cc b/chrome/browser/autofill/autofill_profile.cc
index fc3b30c..a8f0397 100644
--- a/chrome/browser/autofill/autofill_profile.cc
+++ b/chrome/browser/autofill/autofill_profile.cc
@@ -6,6 +6,7 @@
 
 #include <vector>
 
+#include "app/l10n_util.h"
 #include "base/stl_util-inl.h"
 #include "base/string_util.h"
 #include "chrome/browser/autofill/address.h"
@@ -15,6 +16,7 @@
 #include "chrome/browser/autofill/fax_number.h"
 #include "chrome/browser/autofill/home_address.h"
 #include "chrome/browser/autofill/home_phone_number.h"
+#include "grit/generated_resources.h"
 
 AutoFillProfile::AutoFillProfile(const string16& label, int unique_id)
     : label_(label),
@@ -109,6 +111,49 @@ FormGroup* AutoFillProfile::Clone() const {
   return profile;
 }
 
+string16 AutoFillProfile::PreviewSummary() const {
+  // Fetch the components of the summary string.  Any or all of these
+  // may be an empty string.
+  string16 first_name = GetFieldText(AutoFillType(NAME_FIRST));
+  string16 last_name = GetFieldText(AutoFillType(NAME_LAST));
+  string16 address = GetFieldText(AutoFillType(ADDRESS_HOME_LINE1));
+
+  // String separators depend (below) on the existence of the various fields.
+  bool have_first_name = first_name.length() > 0;
+  bool have_last_name = last_name.length() > 0;
+  bool have_address = address.length() > 0;
+
+  // Name separator defaults to "".  Space if we have first and last name.
+  string16 name_separator;
+  if (have_first_name && have_last_name) {
+    name_separator = l10n_util::GetStringUTF16(
+        IDS_AUTOFILL_DIALOG_ADDRESS_NAME_SEPARATOR);
+  }
+
+  // E.g. "John Smith", or "John", or "Smith", or "".
+  string16 name_format = l10n_util::GetStringFUTF16(
+      IDS_AUTOFILL_DIALOG_ADDRESS_SUMMARY_NAME_FORMAT,
+      first_name,
+      name_separator,
+      last_name);
+
+  // Summary separator defaults to "".  ", " if we have name and address.
+  string16 summary_separator;
+  if ((have_first_name || have_last_name) && have_address) {
+    summary_separator = l10n_util::GetStringUTF16(
+        IDS_AUTOFILL_DIALOG_ADDRESS_SUMMARY_SEPARATOR);
+  }
+
+  // E.g. "John Smith, 123 Main Street".
+  string16 summary_format = l10n_util::GetStringFUTF16(
+      IDS_AUTOFILL_DIALOG_ADDRESS_SUMMARY_FORMAT,
+      name_format,
+      summary_separator,
+      address);
+
+  return summary_format;
+}
+
 void AutoFillProfile::operator=(const AutoFillProfile& source) {
   label_ = source.label_;
   unique_id_ = source.unique_id_;
diff --git a/chrome/browser/autofill/autofill_profile.h b/chrome/browser/autofill/autofill_profile.h
index 65182ec..168c790 100644
--- a/chrome/browser/autofill/autofill_profile.h
+++ b/chrome/browser/autofill/autofill_profile.h
@@ -50,6 +50,16 @@ class AutoFillProfile : public FormGroup {
   void set_unique_id(int id) { unique_id_ = id; }
   int unique_id() const { return unique_id_; }
 
+  // Profile summary string for UI.
+  // Constructs a summary string based on NAME_FIRST, NAME_LAST, and
+  // ADDRESS_HOME_LINE1 fields of the profile.  The summary string is of the
+  // form:
+  //     L"<first_name> <last_name>, <address_line_1>"
+  // but may omit any or all of the fields if they are not present in the
+  // profile.
+  // The form of the string is governed by generated resources.
+  string16 PreviewSummary() const;
+
   // For use in STL containers.
   void operator=(const AutoFillProfile&);
 
diff --git a/chrome/browser/autofill/autofill_profile_unittest.cc b/chrome/browser/autofill/autofill_profile_unittest.cc
new file mode 100644
index 0000000..344cdfe
--- /dev/null
+++ b/chrome/browser/autofill/autofill_profile_unittest.cc
@@ -0,0 +1,191 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "base/basictypes.h"
+#include "chrome/browser/autofill/autofill_common_unittest.h"
+#include "chrome/browser/autofill/autofill_profile.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace {
+
+// Unit tests for autofill |AutoFillProfile| class.
+class AutoFillProfileTest : public testing::Test {
+ protected:
+  AutoFillProfileTest() {
+  }
+ private:
+  DISALLOW_COPY_AND_ASSIGN(AutoFillProfileTest);
+};
+
+// Tests different possibilities for summary string generation.
+// Based on existence of first name, last name, and address line 1.
+TEST_F(AutoFillProfileTest, PreviewSummaryString) {
+  // Case 0/null: ""
+  AutoFillProfile profile0(string16(), 0);
+  string16 summary0 = profile0.PreviewSummary();
+  EXPECT_EQ(summary0, string16(ASCIIToUTF16("")));
+
+  // Case 0/empty: ""
+  AutoFillProfile profile00(string16(), 0);
+  autofill_unittest::SetProfileInfo(
+      &profile00,
+      "Billing",
+      "",
+      "Mitchell",
+      "",
+      "johnwayne@me.xyz",
+      "Fox",
+      "",
+      "unit 5",
+      "Hollywood", "CA",
+      "91601",
+      "US",
+      "12345678910",
+      "01987654321");
+  string16 summary00 = profile00.PreviewSummary();
+  EXPECT_EQ(summary00, string16(ASCIIToUTF16("")));
+
+  // Case 1: "<address>"
+  AutoFillProfile profile1(string16(), 0);
+  autofill_unittest::SetProfileInfo(
+      &profile1,
+      "Billing",
+      "",
+      "Mitchell",
+      "",
+      "johnwayne@me.xyz",
+      "Fox",
+      "123 Zoo St.",
+      "unit 5",
+      "Hollywood", "CA",
+      "91601",
+      "US",
+      "12345678910",
+      "01987654321");
+  string16 summary1 = profile1.PreviewSummary();
+  EXPECT_EQ(summary1, string16(ASCIIToUTF16("123 Zoo St.")));
+
+  // Case 2: "<lastname>"
+  AutoFillProfile profile2(string16(), 0);
+  autofill_unittest::SetProfileInfo(
+      &profile2,
+     "Billing",
+     "",
+     "Mitchell",
+     "Morrison",
+     "johnwayne@me.xyz",
+     "Fox",
+     "",
+     "unit 5",
+     "Hollywood", "CA",
+     "91601",
+     "US",
+     "12345678910",
+     "01987654321");
+  string16 summary2 = profile2.PreviewSummary();
+  EXPECT_EQ(summary2, string16(ASCIIToUTF16("Morrison")));
+
+  // Case 3: "<lastname>, <address>"
+  AutoFillProfile profile3(string16(), 0);
+  autofill_unittest::SetProfileInfo(
+      &profile3,
+     "Billing",
+     "",
+     "Mitchell",
+     "Morrison",
+     "johnwayne@me.xyz",
+     "Fox",
+     "123 Zoo St.",
+     "unit 5",
+     "Hollywood", "CA",
+     "91601",
+     "US",
+     "12345678910",
+     "01987654321");
+  string16 summary3 = profile3.PreviewSummary();
+  EXPECT_EQ(summary3, string16(ASCIIToUTF16("Morrison, 123 Zoo St.")));
+
+  // Case 4: "<firstname>"
+  AutoFillProfile profile4(string16(), 0);
+  autofill_unittest::SetProfileInfo(
+      &profile4,
+      "Billing",
+      "Marion",
+      "Mitchell",
+      "",
+      "johnwayne@me.xyz",
+      "Fox",
+      "",
+      "unit 5",
+      "Hollywood", "CA",
+      "91601",
+      "US",
+      "12345678910",
+      "01987654321");
+  string16 summary4 = profile4.PreviewSummary();
+  EXPECT_EQ(summary4, string16(ASCIIToUTF16("Marion")));
+
+  // Case 5: "<firstname>, <address>"
+  AutoFillProfile profile5(string16(), 0);
+  autofill_unittest::SetProfileInfo(
+      &profile5,
+      "Billing",
+      "Marion",
+      "Mitchell",
+      "",
+      "johnwayne@me.xyz",
+      "Fox",
+      "123 Zoo St.",
+      "unit 5",
+      "Hollywood", "CA",
+      "91601",
+      "US",
+      "12345678910",
+      "01987654321");
+  string16 summary5 = profile5.PreviewSummary();
+  EXPECT_EQ(summary5, string16(ASCIIToUTF16("Marion, 123 Zoo St.")));
+
+  // Case 6: "<firstname> <lastname>"
+  AutoFillProfile profile6(string16(), 0);
+  autofill_unittest::SetProfileInfo(
+      &profile6,
+      "Billing",
+      "Marion",
+      "Mitchell",
+      "Morrison",
+      "johnwayne@me.xyz",
+      "Fox",
+      "",
+      "unit 5",
+      "Hollywood", "CA",
+      "91601",
+      "US",
+      "12345678910",
+      "01987654321");
+  string16 summary6 = profile6.PreviewSummary();
+  EXPECT_EQ(summary6, string16(ASCIIToUTF16("Marion Morrison")));
+
+  // Case 7: "<firstname> <lastname>, <address>"
+  AutoFillProfile profile7(string16(), 0);
+  autofill_unittest::SetProfileInfo(
+      &profile7,
+      "Billing",
+      "Marion",
+      "Mitchell",
+      "Morrison",
+      "johnwayne@me.xyz",
+      "Fox",
+      "123 Zoo St.",
+      "unit 5",
+      "Hollywood", "CA",
+      "91601",
+      "US",
+      "12345678910",
+      "01987654321");
+  string16 summary7 = profile7.PreviewSummary();
+  EXPECT_EQ(summary7, string16(ASCIIToUTF16("Marion Morrison, 123 Zoo St.")));
+}
+
+}  // namespace
+
diff --git a/chrome/browser/autofill/credit_card.cc b/chrome/browser/autofill/credit_card.cc
index e32ccf1..1d4ba55 100644
--- a/chrome/browser/autofill/credit_card.cc
+++ b/chrome/browser/autofill/credit_card.cc
@@ -262,27 +262,26 @@ void CreditCard::set_expiration_year(int expiration_year) {
   expiration_year_ = expiration_year;
 }
 
-std::wstring CreditCard::PreviewSummary() const {
-  // TODO(georgey): add unit-test
-  std::wstring preview;
+string16 CreditCard::PreviewSummary() const {
+  string16 preview;
   if (number().empty())
     return preview;  // No CC number, means empty preview.
-  std::wstring obfuscated_cc_number(L"************");
-  obfuscated_cc_number.append(UTF16ToWide(last_four_digits()));
+  string16 obfuscated_cc_number(ASCIIToUTF16("************"));
+  obfuscated_cc_number.append(last_four_digits());
   if (!expiration_month() || !expiration_year())
     return obfuscated_cc_number;  // no expiration date set
   // TODO(georgey): internationalize date
-  std::wstring formatted_date(UTF16ToWide(ExpirationMonthAsString()));
-  formatted_date.append(L"/");
-  formatted_date.append(UTF16ToWide(Expiration4DigitYearAsString()));
-
-  preview = l10n_util::GetStringF(IDS_CREDIT_CARD_NUMBER_PREVIEW_FORMAT,
-                                  obfuscated_cc_number,
-                                  formatted_date);
+  string16 formatted_date(ExpirationMonthAsString());
+  formatted_date.append(ASCIIToUTF16("/"));
+  formatted_date.append(Expiration4DigitYearAsString());
+
+  preview = l10n_util::GetStringFUTF16(
+      IDS_CREDIT_CARD_NUMBER_PREVIEW_FORMAT,
+      obfuscated_cc_number,
+      formatted_date);
   return preview;
 }
 
-
 void CreditCard::operator=(const CreditCard& source) {
   number_ = source.number_;
   name_on_card_ = source.name_on_card_;
diff --git a/chrome/browser/autofill/credit_card.h b/chrome/browser/autofill/credit_card.h
index 1c22d14..c1cd0cf 100644
--- a/chrome/browser/autofill/credit_card.h
+++ b/chrome/browser/autofill/credit_card.h
@@ -83,7 +83,7 @@ class CreditCard : public FormGroup {
   void set_expiration_year(int expiration_year);
 
   // Credit card preview summary, for example: ******1234, Exp: 01/2020
-  std::wstring PreviewSummary() const;
+  string16 PreviewSummary() const;
 
   // For use in STL containers.
   void operator=(const CreditCard&);
diff --git a/chrome/browser/autofill/credit_card_unittest.cc b/chrome/browser/autofill/credit_card_unittest.cc
new file mode 100644
index 0000000..7dab4ff
--- /dev/null
+++ b/chrome/browser/autofill/credit_card_unittest.cc
@@ -0,0 +1,113 @@
+// Copyright (c) 2010 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "base/basictypes.h"
+#include "chrome/browser/autofill/autofill_common_unittest.h"
+#include "chrome/browser/autofill/credit_card.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace {
+
+// Unit tests for autofill |CreditCard| class.
+class CreditCardTest : public testing::Test {
+ protected:
+  CreditCardTest() {
+  }
+
+ private:
+  DISALLOW_COPY_AND_ASSIGN(CreditCardTest);
+};
+
+// Tests credit card summary string generation.  This test simulates a variety
+// of different possible summary strings.  Variations occur based on the
+// existence of credit card number, month, and year fields.
+TEST_F(CreditCardTest, PreviewSummaryString) {
+  // Case 0: empty credit card.
+  CreditCard credit_card0(string16(), 0);
+  string16 summary0 = credit_card0.PreviewSummary();
+  EXPECT_EQ(summary0, string16(ASCIIToUTF16("")));
+
+  // Case 00: Empty credit card with empty strings.
+  CreditCard credit_card00(string16(), 0);
+  autofill_unittest::SetCreditCardInfo(
+      &credit_card00,
+      "Corporate",
+      "John Dillinger",
+      "Visa",
+      "",
+      "",
+      "",
+      "123",
+      "Chicago",
+      "Indianapolis");
+  string16 summary00 = credit_card00.PreviewSummary();
+  EXPECT_EQ(summary00, string16(ASCIIToUTF16("")));
+
+  // Case 1: No credit card number.
+  CreditCard credit_card1(string16(), 0);
+  autofill_unittest::SetCreditCardInfo(
+      &credit_card1,
+      "Corporate",
+      "John Dillinger",
+      "Visa",
+      "",
+      "01",
+      "2010",
+      "123",
+      "Chicago",
+      "Indianapolis");
+  string16 summary1 = credit_card1.PreviewSummary();
+  EXPECT_EQ(summary1, string16(ASCIIToUTF16("")));
+
+  // Case 2: No month.
+  CreditCard credit_card2(string16(), 0);
+  autofill_unittest::SetCreditCardInfo(
+      &credit_card2,
+      "Corporate",
+      "John Dillinger",
+      "Visa",
+      "123456789012",
+      "",
+      "2010",
+      "123",
+      "Chicago",
+      "Indianapolis");
+  string16 summary2 = credit_card2.PreviewSummary();
+  EXPECT_EQ(summary2, string16(ASCIIToUTF16("************9012")));
+
+  // Case 3: No year.
+  CreditCard credit_card3(string16(), 0);
+  autofill_unittest::SetCreditCardInfo(
+      &credit_card3,
+      "Corporate",
+      "John Dillinger",
+      "Visa",
+      "123456789012",
+      "01",
+      "",
+      "123",
+      "Chicago",
+      "Indianapolis");
+  string16 summary3 = credit_card3.PreviewSummary();
+  EXPECT_EQ(summary3, string16(ASCIIToUTF16("************9012")));
+
+  // Case 4: Have everything.
+  CreditCard credit_card4(string16(), 0);
+  autofill_unittest::SetCreditCardInfo(
+      &credit_card4,
+      "Corporate",
+      "John Dillinger",
+      "Visa",
+      "123456789012",
+      "01",
+      "2010",
+      "123",
+      "Chicago",
+      "Indianapolis");
+  string16 summary4 = credit_card4.PreviewSummary();
+  EXPECT_EQ(summary4, string16(ASCIIToUTF16("************9012, Exp: 01/2010")));
+}
+
+}  // namespace
+
diff --git a/chrome/browser/autofill/personal_data_manager_unittest.cc b/chrome/browser/autofill/personal_data_manager_unittest.cc
index db7e070..11940ef 100644
--- a/chrome/browser/autofill/personal_data_manager_unittest.cc
+++ b/chrome/browser/autofill/personal_data_manager_unittest.cc
@@ -5,6 +5,7 @@
 #include "base/basictypes.h"
 #include "base/message_loop.h"
 #include "base/scoped_ptr.h"
+#include "chrome/browser/autofill/autofill_common_unittest.h"
 #include "chrome/browser/autofill/autofill_profile.h"
 #include "chrome/browser/autofill/personal_data_manager.h"
 #include "chrome/browser/chrome_thread.h"
@@ -60,49 +61,6 @@ class PersonalDataManagerTest : public testing::Test {
     personal_data_->SetObserver(&personal_data_observer_);
   }
 
-  static void SetProfileInfo(AutoFillProfile* profile,
-      const char* label, const char* first_name, const char* middle_name,
-      const char* last_name, const char* email, const char* company,
-      const char* address1, const char* address2, const char* city,
-      const char* state, const char* zipcode, const char* country,
-      const char* phone, const char* fax) {
-    profile->set_label(ASCIIToUTF16(label));
-    profile->SetInfo(AutoFillType(NAME_FIRST), ASCIIToUTF16(first_name));
-    profile->SetInfo(AutoFillType(NAME_MIDDLE), ASCIIToUTF16(middle_name));
-    profile->SetInfo(AutoFillType(NAME_LAST), ASCIIToUTF16(last_name));
-    profile->SetInfo(AutoFillType(EMAIL_ADDRESS), ASCIIToUTF16(email));
-    profile->SetInfo(AutoFillType(COMPANY_NAME), ASCIIToUTF16(company));
-    profile->SetInfo(AutoFillType(ADDRESS_HOME_LINE1), ASCIIToUTF16(address1));
-    profile->SetInfo(AutoFillType(ADDRESS_HOME_LINE2), ASCIIToUTF16(address2));
-    profile->SetInfo(AutoFillType(ADDRESS_HOME_CITY), ASCIIToUTF16(city));
-    profile->SetInfo(AutoFillType(ADDRESS_HOME_STATE), ASCIIToUTF16(state));
-    profile->SetInfo(AutoFillType(ADDRESS_HOME_ZIP), ASCIIToUTF16(zipcode));
-    profile->SetInfo(AutoFillType(ADDRESS_HOME_COUNTRY), ASCIIToUTF16(country));
-    profile->SetInfo(AutoFillType(PHONE_HOME_NUMBER), ASCIIToUTF16(phone));
-    profile->SetInfo(AutoFillType(PHONE_FAX_NUMBER), ASCIIToUTF16(fax));
-  }
-
-  static void SetCreditCardInfo(CreditCard* credit_card,
-      const char* label, const char* name_on_card, const char* type,
-      const char* card_number, const char* expiration_month,
-      const char* expiration_year, const char* verification_code,
-      const char* billing_address, const char* shipping_address) {
-    credit_card->set_label(ASCIIToUTF16(label));
-    credit_card->SetInfo(AutoFillType(CREDIT_CARD_NAME),
-                     ASCIIToUTF16(name_on_card));
-    credit_card->SetInfo(AutoFillType(CREDIT_CARD_TYPE), ASCIIToUTF16(type));
-    credit_card->SetInfo(AutoFillType(CREDIT_CARD_NUMBER),
-                     ASCIIToUTF16(card_number));
-    credit_card->SetInfo(AutoFillType(CREDIT_CARD_EXP_MONTH),
-                     ASCIIToUTF16(expiration_month));
-    credit_card->SetInfo(AutoFillType(CREDIT_CARD_EXP_4_DIGIT_YEAR),
-                     ASCIIToUTF16(expiration_year));
-    credit_card->SetInfo(AutoFillType(CREDIT_CARD_VERIFICATION_CODE),
-                     ASCIIToUTF16(verification_code));
-    credit_card->set_billing_address(ASCIIToUTF16(billing_address));
-    credit_card->set_shipping_address(ASCIIToUTF16(shipping_address));
-  }
-
   MessageLoopForUI message_loop_;
   ChromeThread ui_thread_;
   ChromeThread db_thread_;
@@ -116,17 +74,20 @@ class PersonalDataManagerTest : public testing::Test {
 // TODO(jhawkins): Test SetProfiles w/out a WebDataService in the profile.
 TEST_F(PersonalDataManagerTest, SetProfiles) {
   AutoFillProfile profile0(string16(), 0);
-  SetProfileInfo(&profile0, "Billing", "Marion", "Mitchell", "Morrison",
+  autofill_unittest::SetProfileInfo(&profile0,
+      "Billing", "Marion", "Mitchell", "Morrison",
       "johnwayne@me.xyz", "Fox", "123 Zoo St.", "unit 5", "Hollywood", "CA",
       "91601", "US", "12345678910", "01987654321");
 
   AutoFillProfile profile1(string16(), 0);
-  SetProfileInfo(&profile1, "Home", "Josephine", "Alicia", "Saenz",
+  autofill_unittest::SetProfileInfo(&profile1,
+      "Home", "Josephine", "Alicia", "Saenz",
       "joewayne@me.xyz", "Fox", "903 Apple Ct.", NULL, "Orlando", "FL", "32801",
       "US", "19482937549", "13502849239");
 
   AutoFillProfile profile2(string16(), 0);
-  SetProfileInfo(&profile2, "Work", "Josephine", "Alicia", "Saenz",
+  autofill_unittest::SetProfileInfo(&profile2,
+      "Work", "Josephine", "Alicia", "Saenz",
       "joewayne@me.xyz", "Fox", "1212 Center.", "Bld. 5", "Orlando", "FL",
       "32801", "US", "19482937549", "13502849239");
 
@@ -199,15 +160,18 @@ TEST_F(PersonalDataManagerTest, SetProfiles) {
 // TODO(jhawkins): Test SetCreditCards w/out a WebDataService in the profile.
 TEST_F(PersonalDataManagerTest, SetCreditCards) {
   CreditCard creditcard0(string16(), 0);
-  SetCreditCardInfo(&creditcard0, "Corporate", "John Dillinger", "Visa",
+  autofill_unittest::SetCreditCardInfo(&creditcard0,
+      "Corporate", "John Dillinger", "Visa",
       "123456789012", "01", "2010", "123", "Chicago", "Indianapolis");
 
   CreditCard creditcard1(string16(), 0);
-  SetCreditCardInfo(&creditcard1, "Personal", "Bonnie Parker", "Mastercard",
+  autofill_unittest::SetCreditCardInfo(&creditcard1,
+      "Personal", "Bonnie Parker", "Mastercard",
       "098765432109", "12", "2012", "987", "Dallas", "");
 
   CreditCard creditcard2(string16(), 0);
-  SetCreditCardInfo(&creditcard2, "Savings", "Clyde Barrow", "American Express",
+  autofill_unittest::SetCreditCardInfo(&creditcard2,
+      "Savings", "Clyde Barrow", "American Express",
       "777666888555", "04", "2015", "445", "Home", "Farm");
 
   // This will verify that the web database has been loaded and the notification
diff --git a/chrome/chrome_tests.gypi b/chrome/chrome_tests.gypi
index 05ab6e0..afe2ba5 100755
--- a/chrome/chrome_tests.gypi
+++ b/chrome/chrome_tests.gypi
@@ -531,7 +531,11 @@
         'browser/autocomplete/history_url_provider_unittest.cc',
         'browser/autocomplete/keyword_provider_unittest.cc',
         'browser/autocomplete/search_provider_unittest.cc',
+        'browser/autofill/autofill_common_unittest.cc',
+        'browser/autofill/autofill_common_unittest.h',
         'browser/autofill/autofill_dialog_controller_mac_unittest.mm',
+        'browser/autofill/autofill_profile_unittest.cc',
+        'browser/autofill/credit_card_unittest.cc',
         'browser/autofill/personal_data_manager_unittest.cc',
         'browser/automation/automation_provider_unittest.cc',
         'browser/back_forward_menu_model_unittest.cc',
-- 
cgit v1.1