Ошибка означает, что значение CategoryList
равно нулю (и в результате метод DropDownListFor()
ожидает, что первый параметр имеет тип IEnumerable
).
Вы не генерируете вход для каждого свойства каждого SelectListItem
в CategoryList
(и не должен), поэтому никакие значения для SelectList
не отправляются в метод контроллера, и поэтому значение model.CategoryList
в методе POST равно null
, Если вы вернете представление, вы должны сначала переназначить значение CategoryList
, как и в методе GET.
public ActionResult Create(ProjectVM model)
{
if (!ModelState.IsValid)
{
model.CategoryList = new SelectList(db.Categories, "ID", "Name"); // add this
return View(model);
}
// Save and redirect
}
Чтобы объяснить внутреннюю работу (исходный код может быть см. здесь )
Каждая перегрузка DropDownList()
и DropDownListFor()
в конечном итоге вызывает следующий метод
private static MvcHtmlString SelectInternal(this HtmlHelper htmlHelper, ModelMetadata metadata,
string optionLabel, string name, IEnumerable selectList, bool allowMultiple,
IDictionary htmlAttributes)
, который проверяет, есть ли selectList
(второй параметр из @Html.DropDownListFor()
) является null
// If we got a null selectList, try to use ViewData to get the list of items.
if (selectList == null)
{
selectList = htmlHelper.GetSelectData(name);
usedViewData = true;
}
, который, в свою очередь, вызывает
private static IEnumerable GetSelectData(this HtmlHelper htmlHelper, string name)
, который оценивает первый параметр @Html.DropDownListFor()
(в данном случае CategoryID
)
....
o = htmlHelper.ViewData.Eval(name);
....
IEnumerable selectList = o as IEnumerable;
if (selectList == null)
{
throw new InvalidOperationException(String.Format(CultureInfo.CurrentCulture,
MvcResources.HtmlHelper_WrongSelectDataType,
name, o.GetType().FullName, "IEnumerable"));
}
Поскольку свойство CategoryID
является typeof int
, оно не может быть передано в IEnumerable
, и генерируется исключение (которое определено в файле MvcResources.resx
как)
The ViewData item that has the key '{0}' is of type '{1}' but must be of type '{2}'.
из python docs :
Когда вы запустите модуль Python с
python fibo.py
, код в модуле будет выполняется, как если бы вы его импортировали, но с
__ name __
, установленным на«__ main __»
. Это означает, что добавив этот код в конце вашего модуля:
if __name__ == '__main__':
# Running as a script
вы можете сделать файл пригодным для использования как сценарий, а также как импортируемый модуль, потому что код, который анализирует командную строку, запускается только в том случае, если модуль выполняется как «главный» файл
Как указано @bobince:
Вы также будете
__main__
, если Вы будете модулем, вызваннымpython -m somemodule
, Давайте предположим, что у Вас есть файл bar.py
Python и пустое __init__.py
, обе внутренней части папка, названная foo
:
$ tree
.
└── foo
├── __init__.py
└── bar.py
$ cat foo/__init__.py
блоки кода Python ниже являются содержанием [1 112].
print('Code executed as a %s' % 'script' if __name__ == '__main__' else 'module')
Это произведет:
$ python foo/bar.py
Code executed as a script
$ python -m foo.bar
Code executed as a script
vars()
и sys.modules
import sys
mod_name = vars(sys.modules[__name__])['__package__']
print('Code executed as a ' + ('module named %s' % mod_name if mod_name else 'script'))
Это произведет:
$ python foo/bar.py
Code executed as a module named foo
$ python -m foo.bar
Code executed as a script
import sys
try:
import foo
print('Code executed as a module')
except ImportError:
print('Code executed as a script')
# Code will fail here, but you can still print a comprehensive error message before exiting:
print('Usage: python -m foo.bar')
sys.exit()
Это произведет:
$ python foo/bar.py
Code executed as a module
$ python -m foo.bar
Code executed as a script
Usage: python -m foo.bar