Проверка срока действия кредитной карты Linq C # - PullRequest
0 голосов
/ 02 марта 2019

Мое приложение автоматически выставляет счета подписанным клиентам, используя поставщика обработки платежей.Я храню только информацию о дате истечения срока действия карты и номер ссылки поставщиков для автоматического выставления счетов.Каждый день я хочу проверять участников, чьи карты истекают в течение 30 дней.Я запускаю фоновый процесс для отправки напоминаний по электронной почте.Я изо всех сил пытаюсь заставить Linq принять мой запрос.Дата истечения срока хранения сохраняется в базе данных в виде строки, например, 0319 за март 2019 года. Мне интересно, есть ли у меня шанс заставить это работать.Пожалуйста, помогите, если можете.Мое последнее прибежище может заключаться в том, чтобы форматировать даты истечения срока действия, которые в настоящее время хранятся в виде строк mmyy в базе данных, к точным датам.

int mon = DateTime.Now.Month;
int yr = DateTime.Now.Year;
int days = DateTime.DaysInMonth(yr, mon);
int dy = DateTime.Now.Day;
var allCardExpiring = db.DirectDebits.Include(i => i.Customer).Where(a =>a.DdOk && a.Customer.PassOk &&  DateTime.DaysInMonth(Convert.ToInt32(a.DateExpiry.Substring(2, 4)), Convert.ToInt32(a.DateExpiry.Substring(0, 2)))+days-dy < 30).Select(a => a.DirectDebitId).Distinct().ToList();

1 Ответ

0 голосов
/ 04 марта 2019

Это хороший пример, который показывает, что вам не следует формировать базу данных в формате, который операторы используют для ввода своих данных.Если бы ваша база данных имела бы ExpiryDate как DateTime, у вас не было бы этой проблемы.Конечно, с учетом того, что когда операторы вводят дату истечения срока действия, вам придется конвертировать ее в DateTime, но (1) это проще, чем обратное преобразование, и (2) Что вы чаще делаете: запрашиваете ExpiryDate или обновляете его?

Если вы застряли в этой базе данных, то я бы посоветовал создать запрос, в котором вы разделите свое свойство MonthYear на Month и Year, используя DbFunctions.Left и DbFunctions.Right , затем преобразуйте его в своем запросе в правильный DateTime, используя DbFunctions.CreateDateTime

Если вам нужно это преобразование для других функций, рассмотрите возможность создания отдельного IQueryableфункции для этого, так что вы можете использовать его повторно.

В качестве функции расширения для вашего DirectDebit, который принимает входную последовательность DirectDebits и возвращает последовательность DateTimeDirectDebit:

public static IQueryable<DateTimeDirectDebit> ToDateTimeDirectDebits(
    this IQueryable<DirectDebit> directDebits)
{
    return directDebits.Select(directDebit => new
    {
        // split ExpiryDate into a Month and a Year
        ExpiryDate = new
        {
            Month = DbFunctions.Left(directDebit.DateExpire, 2),
            Year = DbFunctions.Right(directDebit.DateExpire, 2),
        }
        DirectDebit = directDebit,
    })
    .Select(directDebit => new DateTimeDirectDebit
    {
         // create the ExpiryDate as DateTime
         ExpiryDate = DbFunctions.CreateDateTime(
            directDebit.ExpiryDate.Year,
            directDebit.ExpiryDate.Mnth,
            1,                                // first day of the month
            ...),
         DirectDebit = directDebit.DirectDebit,
    });
}

Вам также нуженфункция, которая возвращает DateTimeDirectDebits, срок действия которых истекает в течение определенного количества дней.Опять же, как метод расширения:

public static IQueryable<DateTimeDirectDebit> WhereExpiresWithinDays(
   this IQueryable<DateTimeDirectDebit> source,
   int nrOfDays)
{
    DateTime now = DateTime.now;
    DateTime limitDate = now.AddDays(nrOfDays);
    return source.Where(directDebit => directDebit.ExpiryDate < limitDate);
}

Аналогично, вы можете захотеть, чтобы функция, которая возвращает все directDebits, срок действия которых истекает в следующем месяце, использует для этого DbFunctions.DiffMonths.

Использование:

using (var dbContext = new ...)
{
    var directDebitsThatExpireNextMonth = dbContext.DirectDebits
        .ToDateTimeDirectDebits
        .WhereExpiresWithinDays(30)
        .Select(...);
}

Приятно то, что используя эти LINQ-подобные методы расширения, вы можете скрыть, как структурирована ваша база данных, особенно части, которые вас не устраивают.Таким образом, ваш код не должен быть так сильно реструктурирован, если ваша база данных изменяется внутренне, особенно те функции, которые не используют эти изменения.

Конечно, для правильного сокрытия структуры базы данных, класс DateTimeDirectDebitsне следует выставлять свойство DirectDebits, а только свойства, которые вы хотите показать внешнему миру.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...