пятница, 19 марта 2010 г.

MVC. Html.DropDownList

Эта тема перекликается с описанной в прошлом посте. Но теперь хочется, чтобы при редактировании и добавлении новой записи, вместо идентификаторов-ссылок на первичные ключи был выбор ввиде выпадающего списка. То есть вместо Html.TextBox используем Html.DropDownList. Вот код в контроллере:

Function CreateSpecific() As ActionResult
Dim Datacontext As New PrintModelDataContext
Dim PrinterList As IList
PrinterList = (From p In Datacontext.Printer Select ID = p.Id, Naim = _ p.Naim).ToList
ViewData("PrinterList") = New SelectList(PrinterList, "ID", "Naim")
Return View()
End Function

А теперь используем список всех принтеров для выбора поля ID_Printer в таблице Specific в представлении:

<%=Html.DropDownList("Id_printer", CType(ViewData("PrinterList"), SelectList)%>

Если у нас есть логическое поле в таблице, то для него тоже можно использовать HTML.DropDownList.
Например в контроллере создаем список:

Dim YesNo As New List(Of SelectListItem)
YesNo.Add(New SelectListItem With {.Value = Boolean.Parse("True"), _
.Text = "ДА",  .Selected = Boolean.Parse("True")})
YesNo.Add(New SelectListItem With {.Value = Boolean.Parse("False"),_
.Text = "НЕТ", .Selected = Boolean.Parse("True")})
ViewData("YesNo") = New SelectList(YesNo, "Value", "Text")

А в представлении код тот же:

<%=Html.DropDownList("Boolean", CType(ViewData("YesNo"), SelectList)) %>
 

MVC. Выводим в представлениях вместо ID - наименования.

Продолжаем работать над MVC приложением. Конечно при отображении значений полей в записи таблицы,  хотелось бы видеть не идентификаторы-ссылки на другую таблицу ,связанную отношениями, а их смысловые значения. Допустим есть  первичная таблица Printer (Это таблица моделей принтеров).  Вот как выглядит контроллер для отображения этой таблицы .

Function Printer() As ActionResult
Dim Datacontext As New PrintModelDataContext
Dim List = From p In Datacontext.Printer Select p
Return View(List.ToList)
End Function

Потом в одноименном представлении (строго-типизированном) мы в цикле выводим колонки записи таблицы.

<%For Each item In Model%>
<%= Html.Encode(item.Naim) %>
<%= Html.Encode(item.Part_number) %>
<%= Html.Encode(item.Manufactory) %>
<%Next%>

А вот выводим дочернюю таблицу Specific:

Function Specific() As ActionResult
  Dim Datacontext As New PrintModelDataContext
  ViewData("Specific") = _
  From s In Datacontext.Specific, _
    p In Datacontext.Printer, _
    f In Datacontext.Filial _
   Where s.Id_Printer = p.Id And s.Id_Filial = f.Id _
   Select s.Id, s.Inv, s.SN, NaimPrinter = p.Naim,_
    NaimFilial = f.Naim
   Return View()
End Function

В представлении мы уж используем Viewdata("Specific") вместо Model.
В этом случае Intellisense уже вам не подскажет.

<%For Each item In ViewData("Specific")%>
<%=Html.Encode(item.NaimPrinter)%>
<%= Html.Encode(item.SN)%>
<%= Html.Encode(item.Inv)%>
<%=Html.Encode(item.NaimFilial)%>
<% Next%>

Вместо поля числового поля ID_printer Выводиться NaimPrinter из таблицы Printer, вместо ID_Filial - NaimFilial

среда, 17 марта 2010 г.

MVC Repository pattern VB

Вот такие ключевые слова мне понадобились для работы над моим первым MVC проектом. Начал я с изучения проекта Nerddinner http://nerddinnerbook.s3.amazonaws.com/Intro.htm Именно там и используется Repository. То есть набор методов над LINQ to SQL для работы с базой данных. Вот пример добавления строки в таблицу dinner:

public void Add(Dinner dinner) {
db.Dinners.InsertOnSubmit(dinner);
}


Вот пример поиска по ID в таблице dinner:

public Dinner GetDinner(int id) {
return db.Dinners.SingleOrDefault(d => d.DinnerID == id);
}


Так как в проекте Nerddinner используется только одна таблица, то это разработчиков устраивает. Но в моей базе данных 7 таблиц, и видимо есть способ не писать один и тот же код для всех таблиц. И вот в инете нахожу ссылку на универсальный Repository.
http://mikehadlow.blogspot.com/2008/03/using-irepository-pattern-with-linq-to.html
Только мне нужен на VB.
И вот предлагаю небольшую адаптацию написанную на VB.
Добавление записи в таблицу:

Public Sub Add(Of T)(ByRef Tab As T)
dc.GetTable(GetType(T)).InsertOnSubmit(Tab)
End Sub

Action метод для создания записи в таблице Printer будет такой:

Function CreatePrinter(ByVal Row As Printer) As ActionResult
Try
Datawork.Add(Of Printer)(Row)
Datawork.Save()
Return RedirectToAction("Printer")
Catch
Return View()
End Try
End Function


Удаление делается аналогично:

Public Sub Delete(Of T)(ByRef Tab As T)
dc.GetTable(GetType(T)).DeleteOnSubmit(Tab)
End Sub

А вот универсальный поиск по ID оказался для меня сложнее.

Public Function GetbyID(Of T)(ByVal ID As Int32) As T
Dim NameOfTable As ParameterExpression = Expression.Parameter(GetType(T), "x")
Dim lambda1 As Expression(Of Func(Of T, Boolean)) = _
Expression.Lambda(Of Func(Of T, Boolean))( _
Expression.Equal(Expression.Property(NameOfTable, "ID"), Expression.Constant(ID, GetType(Integer))), _
New ParameterExpression() {NameOfTable})
Return CType(dc.GetTable(GetType(T)), IQueryable(Of T)).SingleOrDefault(lambda1)
End Function

Для понимания Lambda Expression рекомендую ссылку http://chakkaradeep.wordpress.com/2008/04/14/c-30-language-enhancements-for-linq-part-3-expression-trees/ . Мне она очень помогла.

пятница, 5 марта 2010 г.

QNAP TS-219P не подсоединяется к домену Windows 2003

Вот уж где не ожидал наткнуться на проблему. Казалось бы ничего сложного нет, просто нужно ввести в окно настроек параметры подключения к домену:
имя сервера контроллера домена, имя домена, имя администратора и пароль. И в итоге получаю ошибку "Microsoft network settings failed " и трачу несколько часов на ее решение.

Вот, наконец-то, в инете нашел ответ.
http://forum.qnap.com/viewtopic.php?f=20&t=12033&start=20
Оказывается нужно было догадаться, что параметр WORKGROUP  устанавливается в короткое имя домена.
Настройка подключения выглядит следующим образом:



Обратите внимание на WORKGROUP . Нет ничего похожего в справке об этой проблеме.

среда, 17 февраля 2010 г.

Проблема с Microsoft Office 2003 (Не запускается,не удаляется,не устанавливается)

Проблема указана в заголовке. Выглядит это вот так:

 
Началось с того, что я удалил Офис, потом его установил. А затем сделал восстановление системы на контрольную точку, где офис уже стоял. После этого случается такая засада. Ни запустить, ни удалить, ни переустановить не могу - вылетает ошибка. Ищу в инете решение. "Office install problem" - вот строка поиска. И одна найденная страничка  отправила меня вот сюда : kb290301 . Windows Installer CleanUp - средство для решения таких проблем.

понедельник, 25 января 2010 г.

Новый принтер HP P4515x выдает ошибку 49.4С27

Пришли два новых принтера HP P4515x. Один пришел в ноябре, другой - в декабре. Абсолютно одинаковые принтера, а работают по разному. Так вот, первый принтер выдает постоянно ошибку 49.4С27, независимо от интерфейса подключения. Оказывается куплены принтера с разницой в месяц,а  firmware у них разный. Тут и гадать не пришлось в чем дело. Иду на сайт HP http://h20000.www2.hp.com/bizsupport/TechSupport/SoftwareDescription.jsp?lang=en&cc=us&prodTypeId=18972&prodSeriesId=3558888&prodNameId=3558895&swEnvOID=54&swLang=33&mode=2&taskId=135&swItem=hv-61299-5 и качаю прошивку ) 04.049.3. Старая прошивка была 04.48.4. Вот так покупаешь новый принтер и уже голову ломаешь над ошибками.
Несколько замечаний по эксплуатации HP P4515.
Термоузел на одном принтере заменил на 400000 пробеге, на другом 225000. Второй принтер выдал ошибку 50.4 и отказался дальше  печатать пока не заменил термоузел (CB389-67901 Ремкомплект LJ P4014/4015/P4515 CB389A).
Так как  замечено, картриджи для HP P4515 выдают меньше копий, чем картриджи для HP 4350, попробывал в драйверах выставить Econome mode. Качество копий в таком режиме меня устраивает. Экономию нужно еще посчитать.
Добавляю вдогонку. В Econom mode существенно экономит тонер. С 15000 страниц до 20000. Советую пользоваться. Качество документов - приемлимое.

среда, 20 января 2010 г.

Удаление стандартных игр WIndows XP

Много есть вариантов в инете. Но я реализовал вот этот, вот по этой ссылке:
http://www.tek-tips.com/viewthread.cfm?qid=1070019&page=14.
Итак, идея проста,  для удаления воспользоваться утилиткой sysocmgr.

Dim Fso : Set Fso = CreateObject("Scripting.FileSystemObject")
Set WshShell = WScript.CreateObject("WScript.Shell")
sPrograms = WshShell.SpecialFolders("AllUsersPrograms")
If (Fso.FolderExists(sPrograms & "\Игры")) Then ' Create file for uninstalling games
Set f = Fso.CreateTextFile("c:\windows\inf\wmdtocm.txt", True)
f.WriteLine("[Components]")
f.WriteLine("freecell=off")
f.WriteLine("hearts=off")
f.WriteLine("minesweeper=off")
f.WriteLine("msnexplr=off")
f.WriteLine("pinball=off")
f.WriteLine("solitaire=off")
f.WriteLine("spider=off")
f.WriteLine("zonegames=off")
f.Close
WshShell.Run "sysocmgr.exe /i:c:\windows\inf\sysoc.inf /u:""c:\windows\inf\wmdtocm.txt"" /q", 1, True
Fso.DeleteFolder(sPrograms & "\Игры"), True
End If


Код практически такой же, как в оригинале, только изменена папка, где хранятся игры. В русской версии WindowsXP - это "\Игры".
Этот код сохраните в файл с расширением ".vbs". Допустим remove_games.vbs
Для того чтобы удалить игры со всех компьютеров домена, можно использовать групповую политику. Я включил этот скрипт в автозагрузку.
"Конфигурация компьютера->Конфигурация Windows->Сценарии (запуск завершение)->Автозагрузка." Это работает и можно использовать