// Copyright 2013 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 "components/autofill/core/browser/autofill_data_model.h"

#include "base/basictypes.h"
#include "base/logging.h"
#include "base/strings/string_number_conversions.h"
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "components/autofill/core/browser/autofill_country.h"
#include "components/autofill/core/browser/autofill_field.h"
#include "components/autofill/core/browser/autofill_type.h"
#include "components/autofill/core/browser/state_names.h"
#include "components/autofill/core/browser/validation.h"
#include "components/autofill/core/common/form_field_data.h"
#include "grit/component_strings.h"
#include "ui/base/l10n/l10n_util.h"
#include "url/gurl.h"

namespace autofill {
namespace {

const char* const kMonthsAbbreviated[] = {
  NULL,  // Padding so index 1 = month 1 = January.
  "Jan", "Feb", "Mar", "Apr", "May", "Jun",
  "Jul", "Aug", "Sep", "Oct", "Nov", "Dec",
};

const char* const kMonthsFull[] = {
  NULL,  // Padding so index 1 = month 1 = January.
  "January", "February", "March", "April", "May", "June",
  "July", "August", "September", "October", "November", "December",
};

const char* const kMonthsNumeric[] = {
  NULL,  // Padding so index 1 = month 1 = January.
  "1", "2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12",
};

// Returns true if the value was successfully set, meaning |value| was found in
// the list of select options in |field|.
bool SetSelectControlValue(const base::string16& value,
                           FormFieldData* field) {
  base::string16 value_lowercase = StringToLowerASCII(value);

  DCHECK_EQ(field->option_values.size(), field->option_contents.size());
  for (size_t i = 0; i < field->option_values.size(); ++i) {
    if (value_lowercase == StringToLowerASCII(field->option_values[i]) ||
        value_lowercase == StringToLowerASCII(field->option_contents[i])) {
      field->value = field->option_values[i];
      return true;
    }
  }

  return false;
}

bool FillStateSelectControl(const base::string16& value,
                            FormFieldData* field) {
  base::string16 full, abbreviation;
  state_names::GetNameAndAbbreviation(value, &full, &abbreviation);

  // Try the abbreviation first.
  if (!abbreviation.empty() && SetSelectControlValue(abbreviation, field))
    return true;

  return !full.empty() && SetSelectControlValue(full, field);
}

bool FillExpirationMonthSelectControl(const base::string16& value,
                                      FormFieldData* field) {
  int index = 0;
  if (!base::StringToInt(value, &index) ||
      index <= 0 ||
      static_cast<size_t>(index) >= arraysize(kMonthsFull))
    return false;

  bool filled =
      SetSelectControlValue(ASCIIToUTF16(kMonthsAbbreviated[index]), field) ||
      SetSelectControlValue(ASCIIToUTF16(kMonthsFull[index]), field) ||
      SetSelectControlValue(ASCIIToUTF16(kMonthsNumeric[index]), field);
  return filled;
}

// Try to fill a credit card type |value| (Visa, MasterCard, etc.) into the
// given |field|.
bool FillCreditCardTypeSelectControl(const base::string16& value,
                                     FormFieldData* field) {
  // Try stripping off spaces.
  base::string16 value_stripped;
  RemoveChars(StringToLowerASCII(value), kWhitespaceUTF16, &value_stripped);

  for (size_t i = 0; i < field->option_values.size(); ++i) {
    base::string16 option_value_lowercase;
    RemoveChars(StringToLowerASCII(field->option_values[i]), kWhitespaceUTF16,
                &option_value_lowercase);
    base::string16 option_contents_lowercase;
    RemoveChars(StringToLowerASCII(field->option_contents[i]), kWhitespaceUTF16,
                &option_contents_lowercase);

    // Perform a case-insensitive comparison; but fill the form with the
    // original text, not the lowercased version.
    if (value_stripped == option_value_lowercase ||
        value_stripped == option_contents_lowercase) {
      field->value = field->option_values[i];
      return true;
    }
  }

  // For American Express, also try filling as "AmEx".
  if (value == l10n_util::GetStringUTF16(IDS_AUTOFILL_CC_AMEX))
    return FillCreditCardTypeSelectControl(ASCIIToUTF16("AmEx"), field);

  return false;
}

}  // namespace

AutofillDataModel::AutofillDataModel(const std::string& guid,
                                     const std::string& origin)
    : guid_(guid),
      origin_(origin) {}
AutofillDataModel::~AutofillDataModel() {}

void AutofillDataModel::FillSelectControl(const AutofillType& type,
                                          const std::string& app_locale,
                                          FormFieldData* field) const {
  DCHECK(field);
  DCHECK_EQ("select-one", field->form_control_type);
  DCHECK_EQ(field->option_values.size(), field->option_contents.size());

  base::string16 field_text = GetInfo(type, app_locale);
  base::string16 field_text_lower = StringToLowerASCII(field_text);
  if (field_text.empty())
    return;

  base::string16 value;
  for (size_t i = 0; i < field->option_values.size(); ++i) {
    if (field_text == field->option_values[i] ||
        field_text == field->option_contents[i]) {
      // An exact match, use it.
      value = field->option_values[i];
      break;
    }

    if (field_text_lower == StringToLowerASCII(field->option_values[i]) ||
        field_text_lower == StringToLowerASCII(field->option_contents[i])) {
      // A match, but not in the same case. Save it in case an exact match is
      // not found.
      value = field->option_values[i];
    }
  }

  if (!value.empty()) {
    field->value = value;
    return;
  }

  ServerFieldType storable_type = type.GetStorableType();
  if (storable_type == ADDRESS_HOME_STATE) {
    FillStateSelectControl(field_text, field);
  } else if (storable_type == ADDRESS_HOME_COUNTRY) {
    FillCountrySelectControl(app_locale, field);
  } else if (storable_type == CREDIT_CARD_EXP_MONTH) {
    FillExpirationMonthSelectControl(field_text, field);
  } else if (storable_type == CREDIT_CARD_EXP_4_DIGIT_YEAR) {
    // Attempt to fill the year as a 2-digit year.  This compensates for the
    // fact that our heuristics do not always correctly detect when a website
    // requests a 2-digit rather than a 4-digit year.
    FillSelectControl(AutofillType(CREDIT_CARD_EXP_2_DIGIT_YEAR), app_locale,
                      field);
  } else if (storable_type == CREDIT_CARD_TYPE) {
    FillCreditCardTypeSelectControl(field_text, field);
  }
}

bool AutofillDataModel::FillCountrySelectControl(
    const std::string& app_locale,
    FormFieldData* field_data) const {
  return false;
}

bool AutofillDataModel::IsVerified() const {
  return !origin_.empty() && !GURL(origin_).is_valid();
}

}  // namespace autofill
