1

I am currently facing an issue that debugging (VS2022) does not seem to solve for whatever reason.

In the below code, I am using the Gmail API package for .NET, where I'm able to extract out an email subject (string) and the email address (not included/relevant) from a given email.

var subject = m.Payload.Headers.Where(x => x.Name == "Subject").First().Value;

I then search via LINQ through a mapping table in my SQL database (EmailSubjectMappings) using EntityFramework Core to find the respective row that fulfills the below condition (if my self-entried "pattern" string is a substring of the main subject string)

var subjectMapping = context.EmailSubjectMappings.AsEnumerable().Where(x => (subject.Contains(x.EmailSubject))).FirstOrDefault();

In the case of subject containing no single quotes, this works fine. For example:

  • input

    • subject = "Fwd: Your Order was Shipped"

    • x.EmailSubject = "Your Order was Shipped"

  • Expected result: subjectMapping.EmailShippingStatus = "Order Delayed"

  • Actual result: subjectMapping.EmailShippingStatus = "Order Delayed"

However, in the case of single quotes:

  • input:

    • subject = "Fwd: Your Order Couldn't Be Delivered"

    • x.EmailSubject = "Your Order Couldn't Be Delivered"

  • Expected result: subjectMapping.EmailShippingStatus = "Order Not Delivered"

  • Actual result: subjectMapping.EmailShippingStatus = null

I went into the debugger, and checked each variable in the watch window to see what the root cause was:

  1. context.EmailSubjectMappings.ToList().FirstOrDefault(x=> subject.Contains("Your Order Couldn't Be Delivered")) -> null (not expected)

  2. context.EmailSubjectMappings.ToList().FirstOrDefault(x=>"Fwd: Your Order Couldn't Be Delivered".Contains(x.EmailSubject)) -> "Order Not Delivered" (expected)

  3. context.EmailSubjectMappings.ToList().FirstOrDefault(x=>"Fwd: Your Order Couldn't Be Delivered".Contains("Your Order Couldn't Be Delivered")) -> "Order Not Delivered" (expected)

So through transition, it looks that the variable subject is the issue, and inputting that in the watch window shows also the expected string : "Fwd: Your Couldn't Be Delivered"

I've also tried removing all possible hidden characters using Regex

string output = Regex.Replace(subject, "[^\u0021-\u007E]", "");

and even using IndexOf() instead of .Contains.

So I'm stumped. Is there some sort of memory issue going on causing my subject variable to change? Is it some property of LINQ or EF Core? I appreciate any help!

Chris Y
  • 11
  • 1
  • Could there be a case-sensitivity issue? [Entity Framework core - Contains is case sensitive or case insensitive?](https://stackoverflow.com/questions/43277868/entity-framework-core-contains-is-case-sensitive-or-case-insensitive) – Andrew Morton Mar 23 '23 at 20:33
  • Could you provide a [mcve] rather than these individual bits and pieces? (Just use hard-coded data - you shouldn't need any reference Gmail.) – Jon Skeet Mar 23 '23 at 20:37
  • My guess would be that original sender is using a different single quote by default than you are expecting. Did you check the value of the quote character in the subject as you got it from gmail? The ASCII/normal (code) single quote (U+0027 or 39 decimal) is also used as an apostrophe, but the proper apostrophe is the Right Single Quotation Mark or U+2019. – NetMage Mar 23 '23 at 21:20
  • @NetMage I don't know why I didn't bother checking the ASCII values.. this was absolutely correct. For my usecase, removing the quotes using Regex did the trick. Jon, I'll make sure to provide a MRE next time for sure! – Chris Y Mar 23 '23 at 21:42
  • I would also highly recommend removing the `AsEnumerable()` from the query. This will be loading ***all*** emails into memory. I would suspect that developers went and substituted single quotes in strings rather than escaping them to avoid running into escaping issues when building queries since many languages use single quotes as a string delimiter, or they wanted to prevent SQL injection preventing users from typing single-quote characters and substituted them rather than relying on parameterized queries. If they are substituted, then you can continue to replace them in the search text. – Steve Py Mar 23 '23 at 22:30
  • @StevePy Actually, it will just be loading all subject patterns and their corresponding email shipping status, which I assume is a small table. – NetMage Mar 23 '23 at 23:44

0 Answers0