0

インスタンス EP1、EP2、または EP1 の値を持つことができるプロパティ System を持つ serviceEntryFilter という名前のフィルターがあり、このフィルターが null になる場合があります。複数の値または単一の値がある場合、クエリ (IN) 句は正常に実行されます。フィルター値が null の場合、次のエラーが発生します。

タイプ 'System.String[]' の定数値を作成できません。このコンテキストでは、プリミティブ型 (Int32、String、および Guid など) のみがサポートされます。

[HttpPost]
        public ActionResult List(string ServiceEntryStatus, string ServiceEntryReconciled, string ServiceEntryReliabilityRecord, string ActiveServiceEntry,
                                    int PageNo, ServiceEntryFilter serviceEntryFilter = null)
        {


           string[] systems = null;


        var list = (from se in db.ServiceEntry
                    join r in db.RunLogEntry on se.RunLogEntryID equals r.ID into joinRunLogEntry
                    from r2 in joinRunLogEntry.DefaultIfEmpty()
                    join u in db.User on se.TechnicianID equals u.ID
                    join s in db.System1 on se.SystemID equals s.ID
                    where (
                        ((se.RunLogEntryID == 0 || se.RunLogEntryID != null))
                             && ((serviceEntryFilter.ID.HasValue == false) || (se.ID == serviceEntryFilter.ID.Value && serviceEntryFilter.ID.HasValue == true))
                            && ((serviceEntryFilter.ServiceDateTime.HasValue == false) || (EntityFunctions.TruncateTime(se.ServiceDateTime) == EntityFunctions.TruncateTime(serviceEntryFilter.ServiceDateTime) && serviceEntryFilter.ServiceDateTime.HasValue == true))
                            && ((serviceEntryFilter.RunDate.HasValue == false) || (EntityFunctions.TruncateTime(r2.RunDate) == EntityFunctions.TruncateTime(serviceEntryFilter.RunDate) && serviceEntryFilter.RunDate.HasValue == true))
                            && ((serviceEntryFilter.Technician == null) || (u.FullName.Contains(serviceEntryFilter.Technician.Trim()) && serviceEntryFilter.Technician != null))
                            && (
                                    ((ServiceEntryStatus == "O" && se.ServiceRequestClosed == false) ||
                                      (ServiceEntryStatus == "C" && se.ServiceRequestClosed == true) ||
                                      (ServiceEntryStatus == "A")
                                    )
                               )
                                   && (
                                    ((ServiceEntryReliabilityRecord == null) ||
                                     (ServiceEntryReliabilityRecord == "N" && se.ReliabilityRecord == false) ||
                                      (ServiceEntryReliabilityRecord == "Y" && se.ReliabilityRecord == true) ||
                                      (ServiceEntryReliabilityRecord == "A")
                                    )
                                )
                            && (
                                    ((ServiceEntryReconciled == null) ||
                                     (ServiceEntryReconciled == "N" && se.Reconciled == false) ||
                                      (ServiceEntryReconciled == "Y" && se.Reconciled == true) ||
                                      (ServiceEntryReconciled == "A")
                                    )
                                )
                                         && (
                                    ((ActiveServiceEntry == null) ||
                                     (ActiveServiceEntry == "N" && se.Active == false) ||
                                      (ActiveServiceEntry == "Y" && se.Active == true) ||
                                      (ActiveServiceEntry == "A")
                                    )
                                )

                                    && (
                                  (s.PlatformID == platformID) || (platformID == 0)
                               )
                        && ((serviceEntryFilter.System == null) || ((serviceEntryFilter.System != null) && systems.Contains(s.SystemFullName)))
                       )
                    orderby se.ID descending
                    select new ServiceSearchEntry()
                    {
                        ID = se.ID,
                        ServiceDateTime = se.ServiceDateTime,
                        Technician = u.FullName,
                        System = s.SystemFullName,
                        ReasonForFailure = se.ReasonForFailure,
                        RunDate = (r2 == null ? (DateTime?)null : r2.RunDate)
                    });

        var listData = list.Skip((page - 1) * PageSize).Take(PageSize);

        ServiceEntriesListViewModel viewModel = new ServiceEntriesListViewModel()
        {
            ServiceSearchEntry = listData,
            PagingInfo = new PagingInfo
            {
                CurrentPage = page,
                ItemsPerPage = PageSize,
                TotalItems = list.Count()
            }
        };



}

問題:

SystemFilter.System が NULL の場合、次の句はエラーをスローします。ユーザーが値を選択しない場合は null になります。サンプル値は次のとおりです。

EP1、EP2 EP1 TP2、TP3、TP4

&& ((serviceEntryFilter.System == null) || ((serviceEntryFilter.System != null) && systems.Contains(s.SystemFullName)))

値がある場合は、それを配列に入れると、それが魅力のように機能し、null のときだけです。

4

2 に答える 2

1

問題は、LINQ ステートメント内のすべてが SQL に変換されることです。私がここで見た「実際にnullの場合は、この配列フィルターを追加しようとしないでください」という条件ステートメントは実際にはありません。

systems配列を長さゼロの配列に初期化し、filter.Systemsnull でない場合は上書きしてから、次のように linq ステートメントを作成します。

systems.Contains(s.SystemFullName)

期待どおりの動作をしていないため、LINQ ステートメント内に null チェックを含めないでください。

条件付き LINQ ステートメントを作成するには、PredicateBuilder を参照してください: http://www.albahari.com/nutshell/predicatebuilder.aspx

于 2013-06-28T15:23:41.140 に答える