странная ошибка нулевой ссылки на foreach при отображении представления - PullRequest
7 голосов
/ 23 декабря 2010

Эта ошибка настолько странная, что я просто не могу понять, что на самом деле не так!

В UserController у меня есть

public virtual ActionResult Index()
{
    var usersmdl = from u in RepositoryFactory.GetUserRepo().GetAll()
                   select new UserViewModel
                   {
                       ID = u.ID,
                       UserName = u.Username,
                       UserGroupName = u.UserGroupMain.GroupName,
                       BranchName = u.Branch.BranchName,
                       Password = u.Password,
                       Ace = u.ACE,
                       CIF = u.CIF,
                       PF = u.PF
                   };
    if (usersmdl != null)
    {
        return View(usersmdl.AsEnumerable());
    }
    return View();
}

Мой вид имеет тип @model IEnumerable<UserViewModel> наtop.
Вот что происходит:

alt text

Где и что именно НУЛЬ !?

Я создаю пользователей из поддельного репозитория с moq .Я также написал модульные тесты, которые проходят, чтобы гарантировать возвращение нужного количества поддельных пользователей.

Может быть, кто-то может указать мне правильное направление здесь?Вершина трассировки стека:

at lambda_method(Closure , User )
   at System.Linq.Enumerable.WhereSelectArrayIterator`2.MoveNext()
   at ASP.Index_cshtml.Execute() 

Это как-то связано с linq здесь?Скажите, если мне нужно включить полную трассировку стека.


Редактировать
<BangsHeadOnWall /> Ого, я не могу поверить, что это было u.UserGroupMain.GroupName спасибо @ Lunivore .
Это было репозиторий макетов, и у меня был модульный тест, чтобы проверить, имел ли пользователь макет репо макет экземпляр UserGroupMain, но я не утверждал, что свойство wee GroupNameбыло установлено!

Спасибо @ RPM1984 вы предлагаете получить код для взлома самого контроллера.Кроме того, я узнал что-то новое.

Спасибо @ Микаэль , впервые я использовал окно немедленного вау круто!= D

Угадай, живи, код и учись!

Ответы [ 3 ]

6 голосов
/ 23 декабря 2010

Да, это как-то связано с linq.Linq не выполняет запрос до того, как вы его используете.Поэтому, когда вы зацикливаетесь на нем, запрос запускается и по какой-то причине он падает.

Что возвращает GetAll?Одна вещь, которую вы могли бы сделать, это поместить точку останова в Index (), и, когда она прервется, напишите об этом в ближайшем окне.

>RepositoryFactory.GetUserRepo().GetAll().ToList()

Если вы не можете найти окно Immediate, вы можете открыть его, написав

>immed

в поле поиска (в верхней части VS)

Если это не приводит к сбою, проблема, вероятно, в linq внутри Index ().Из того, что я вижу, я бы заподозрил, что u.UserGroupMain или u.Branch имеет значение null.Но трудно сказать без дополнительной информации.

5 голосов
/ 23 декабря 2010

Изменить эту строку:

return View(usersmdl.AsEnumerable());

На это:

return View(usersmdl.ToList());

Почему?

От MSDN:

AsEnumerable(Of TSource) (IEnumerable (Of TSource)) не имеет никакого другого эффекта, кроме как изменить тип источника времени компиляции с типа, который реализует IEnumerable (Of T) на сам IEnumerable (Of T).

На английском - потому что .AsEnumerable() преобразуется в IEnumerable<T>, но IQueryable<T> уже реализует IEnumerable<T>, поэтому запрос не материализуется - и лениво оценивается в представлении, когда выперечислите пункты в foreach.Классический трюк с отложенным выполнением LINQ.

Вот почему я люблю Resharper - он скажет вам, что вызов AsEnumerable() является избыточным - тогда станет намного очевиднее, что ваш запрос откладывается.

.ToList() запустит запрос до того, как он попадет в представление, и все еще реализует IEnumerable<T>, поэтому привязка модели не требуется.

1 голос
/ 23 декабря 2010

Убедитесь, что UserGroupMain и Branch, которые вы настроили в своих пользователях, не равны нулю:

                   UserGroupName = u.UserGroupMain.GroupName,
                   BranchName = u.Branch.BranchName,

Если это решит вашу проблему, ответ Микаэля объясняет, почему это происходит там, а не дальше в запросе.

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